diff --git a/Code/Cupscale.csproj b/Code/Cupscale.csproj index f8b31f9..b92ba39 100644 --- a/Code/Cupscale.csproj +++ b/Code/Cupscale.csproj @@ -35,10 +35,8 @@ all runtime; build; native; contentfiles; analyzers; buildtransitive - + - - @@ -107,4 +105,7 @@ + + + \ No newline at end of file diff --git a/Code/FFmpeg/FFmpeg.cs b/Code/FFmpeg/FFmpeg.cs index c3ce76a..d92f02a 100644 --- a/Code/FFmpeg/FFmpeg.cs +++ b/Code/FFmpeg/FFmpeg.cs @@ -38,6 +38,33 @@ static void OutputHandler(object sendingProcess, DataReceivedEventArgs outLine) Logger.Log("[FFmpeg] " + outLine.Data); } + public static async Task RunGifski (string args) + { + Process ffmpeg = new Process(); + ffmpeg.StartInfo.UseShellExecute = false; + ffmpeg.StartInfo.RedirectStandardOutput = true; + ffmpeg.StartInfo.RedirectStandardError = true; + ffmpeg.StartInfo.CreateNoWindow = true; + ffmpeg.StartInfo.FileName = "cmd.exe"; + ffmpeg.StartInfo.Arguments = "/C cd /D " + Paths.esrganPath.WrapPath() + + " & gifski.exe " + args; + Logger.Log("Running gifski..."); + Logger.Log("cmd.exe " + ffmpeg.StartInfo.Arguments); + ffmpeg.OutputDataReceived += new DataReceivedEventHandler(OutputHandlerGifski); + ffmpeg.ErrorDataReceived += new DataReceivedEventHandler(OutputHandlerGifski); + ffmpeg.Start(); + ffmpeg.BeginOutputReadLine(); + ffmpeg.BeginErrorReadLine(); + while (!ffmpeg.HasExited) + await Task.Delay(100); + Logger.Log("Done running gifski."); + } + + static void OutputHandlerGifski (object sendingProcess, DataReceivedEventArgs outLine) + { + Logger.Log("[gifski] " + outLine.Data); + } + /* public static string RunAndGetOutput (string args) { diff --git a/Code/Forms/SettingsForm.Designer.cs b/Code/Forms/SettingsForm.Designer.cs index 2161a0c..e0c096a 100644 --- a/Code/Forms/SettingsForm.Designer.cs +++ b/Code/Forms/SettingsForm.Designer.cs @@ -60,9 +60,8 @@ private void InitializeComponent() this.formatsPage = new Cyotek.Windows.Forms.TabListPage(); this.tableLayoutPanel1 = new System.Windows.Forms.TableLayoutPanel(); this.panel1 = new System.Windows.Forms.Panel(); - this.label14 = new System.Windows.Forms.Label(); - this.ddsUseDxt = new System.Windows.Forms.CheckBox(); - this.ddsMipsAmount = new System.Windows.Forms.TextBox(); + this.dxtMode = new System.Windows.Forms.ComboBox(); + this.ddsEnableMips = new System.Windows.Forms.CheckBox(); this.label13 = new System.Windows.Forms.Label(); this.label3 = new System.Windows.Forms.Label(); this.webpQ = new System.Windows.Forms.TextBox(); @@ -434,9 +433,8 @@ private void InitializeComponent() | System.Windows.Forms.AnchorStyles.Left) | System.Windows.Forms.AnchorStyles.Right))); this.panel1.BorderStyle = System.Windows.Forms.BorderStyle.FixedSingle; - this.panel1.Controls.Add(this.label14); - this.panel1.Controls.Add(this.ddsUseDxt); - this.panel1.Controls.Add(this.ddsMipsAmount); + this.panel1.Controls.Add(this.dxtMode); + this.panel1.Controls.Add(this.ddsEnableMips); this.panel1.Controls.Add(this.label13); this.panel1.Controls.Add(this.label3); this.panel1.Controls.Add(this.webpQ); @@ -449,33 +447,35 @@ private void InitializeComponent() this.panel1.Size = new System.Drawing.Size(407, 463); this.panel1.TabIndex = 4; // - // label14 + // dxtMode // - this.label14.AutoSize = true; - this.label14.ForeColor = System.Drawing.Color.Silver; - this.label14.Location = new System.Drawing.Point(252, 170); - this.label14.Name = "label14"; - this.label14.Size = new System.Drawing.Size(127, 13); - this.label14.TabIndex = 18; - this.label14.Text = "Use 0 to disable mipmaps"; - // - // ddsUseDxt - // - this.ddsUseDxt.AutoSize = true; - this.ddsUseDxt.Location = new System.Drawing.Point(180, 140); - this.ddsUseDxt.Name = "ddsUseDxt"; - this.ddsUseDxt.Size = new System.Drawing.Size(15, 14); - this.ddsUseDxt.TabIndex = 17; - this.ddsUseDxt.UseVisualStyleBackColor = true; - // - // ddsMipsAmount - // - this.ddsMipsAmount.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64))))); - this.ddsMipsAmount.ForeColor = System.Drawing.Color.White; - this.ddsMipsAmount.Location = new System.Drawing.Point(180, 167); - this.ddsMipsAmount.Name = "ddsMipsAmount"; - this.ddsMipsAmount.Size = new System.Drawing.Size(66, 20); - this.ddsMipsAmount.TabIndex = 16; + this.dxtMode.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left) + | System.Windows.Forms.AnchorStyles.Right))); + this.dxtMode.BackColor = System.Drawing.Color.FromArgb(((int)(((byte)(64)))), ((int)(((byte)(64)))), ((int)(((byte)(64))))); + this.dxtMode.FlatStyle = System.Windows.Forms.FlatStyle.Flat; + this.dxtMode.ForeColor = System.Drawing.Color.White; + this.dxtMode.FormattingEnabled = true; + this.dxtMode.Items.AddRange(new object[] { + "Off", + "BC1 (DXT1)", + "BC2 (DXT3)", + "BC3 (DXT5)", + "BC4 ", + "BC5"}); + this.dxtMode.Location = new System.Drawing.Point(180, 137); + this.dxtMode.Margin = new System.Windows.Forms.Padding(8); + this.dxtMode.Name = "dxtMode"; + this.dxtMode.Size = new System.Drawing.Size(66, 21); + this.dxtMode.TabIndex = 18; + // + // ddsEnableMips + // + this.ddsEnableMips.AutoSize = true; + this.ddsEnableMips.Location = new System.Drawing.Point(180, 169); + this.ddsEnableMips.Name = "ddsEnableMips"; + this.ddsEnableMips.Size = new System.Drawing.Size(15, 14); + this.ddsEnableMips.TabIndex = 17; + this.ddsEnableMips.UseVisualStyleBackColor = true; // // label13 // @@ -491,9 +491,9 @@ private void InitializeComponent() this.label3.AutoSize = true; this.label3.Location = new System.Drawing.Point(6, 140); this.label3.Name = "label3"; - this.label3.Size = new System.Drawing.Size(143, 13); + this.label3.Size = new System.Drawing.Size(151, 13); this.label3.TabIndex = 14; - this.label3.Text = "DDS: Use DXT Compression"; + this.label3.Text = "DDS: DXT Compression Mode"; // // webpQ // @@ -640,9 +640,7 @@ private void InitializeComponent() private System.Windows.Forms.Label label11; private System.Windows.Forms.Label label12; private System.Windows.Forms.Panel panel2; - private System.Windows.Forms.Label label14; - private System.Windows.Forms.CheckBox ddsUseDxt; - private System.Windows.Forms.TextBox ddsMipsAmount; + private System.Windows.Forms.CheckBox ddsEnableMips; private System.Windows.Forms.Label label13; private System.Windows.Forms.Label label3; private System.Windows.Forms.PictureBox pictureBox1; @@ -653,5 +651,6 @@ private void InitializeComponent() private System.Windows.Forms.ComboBox esrganVersion; private System.Windows.Forms.PictureBox pictureBox2; private System.Windows.Forms.PictureBox pictureBox3; + private System.Windows.Forms.ComboBox dxtMode; } } \ No newline at end of file diff --git a/Code/Forms/SettingsForm.cs b/Code/Forms/SettingsForm.cs index 8c6d3a0..5c5a94d 100644 --- a/Code/Forms/SettingsForm.cs +++ b/Code/Forms/SettingsForm.cs @@ -48,8 +48,8 @@ void LoadSettings() Config.LoadGuiElement(jpegQ); Config.LoadGuiElement(webpQ); - Config.LoadGuiElement(ddsUseDxt); - Config.LoadGuiElement(ddsMipsAmount); + Config.LoadGuiElement(dxtMode); + Config.LoadGuiElement(ddsEnableMips); } private void SettingsForm_FormClosing(object sender, FormClosingEventArgs e) @@ -71,8 +71,8 @@ void SaveSettings() Config.SaveGuiElement(jpegQ); Config.SaveGuiElement(webpQ); - Config.SaveGuiElement(ddsUseDxt); - Config.SaveGuiElement(ddsMipsAmount); + Config.SaveGuiElement(dxtMode); + Config.SaveGuiElement(ddsEnableMips); } private void confAlphaBgColorBtn_Click(object sender, EventArgs e) diff --git a/Code/IO/Config.cs b/Code/IO/Config.cs index 7483765..7921056 100644 --- a/Code/IO/Config.cs +++ b/Code/IO/Config.cs @@ -82,8 +82,8 @@ private static string WriteDefaultValIfExists(string key) "useNcnn" => WriteDefault("useNcnn", "False"), "jpegQ" => WriteDefault("jpegQ", "95"), "webpQ" => WriteDefault("webpQ", "95"), - "ddsUseDxt" => WriteDefault("ddsUseDxt", "True"), - "ddsMipsAmount" => WriteDefault("ddsMipsAmount", "0"), + "dxtMode" => WriteDefault("dxtMode", "BC1 (DXT1)"), + "ddsEnableMips" => WriteDefault("ddsEnableMips", "True"), _ => null, }; } diff --git a/Code/IO/IOUtils.cs b/Code/IO/IOUtils.cs index 37b7f3d..3613098 100644 --- a/Code/IO/IOUtils.cs +++ b/Code/IO/IOUtils.cs @@ -31,62 +31,6 @@ public static string GetExeDir() return AppDomain.CurrentDomain.BaseDirectory; } - public static Image GetImage(string path) - { - Logger.Log("IOUtils.GetImage: Reading Image from " + path); - using MemoryStream stream = new MemoryStream(File.ReadAllBytes(path)); - Image img = Image.FromStream(stream); - Logger.Log("[OK]", true, true); - return img; - } - - public static MagickImage GetMagickImage (string path) - { - Logger.Log("IOUtils.GetMagickImage: Reading Image from " + path); - MagickImage image; - if (Path.GetExtension(path).ToLower() == ".dds") - { - try - { - image = new MagickImage(path); // Try reading DDS with IM, fall back to DdsFileTypePlusHack if it fails - } - catch - { - Logger.Log("Failed to read DDS using Mackig.NET - Trying DdsFileTypePlusHack"); - try - { - Surface surface = DdsFile.Load(path); - image = ConvertToMagickImage(surface); - image.HasAlpha = DdsFile.HasTransparency(surface); - } - catch (Exception e) - { - MessageBox.Show("This DDS format is incompatible.\n\n" + e.Message); - return null; - } - } - } - else - { - image = new MagickImage(path); - } - Logger.Log("[OK]", true, true); - return image; - } - - public static MagickImage ConvertToMagickImage(Surface surface) - { - MagickImage result; - Bitmap bitmap = surface.CreateAliasedBitmap(); - using (MemoryStream memoryStream = new MemoryStream()) - { - bitmap.Save(memoryStream, System.Drawing.Imaging.ImageFormat.Png); - memoryStream.Position = 0; - result = new MagickImage(memoryStream, new MagickReadSettings() { Format = MagickFormat.Png00 }); - } - return result; - } - public static string[] ReadLines(string path) { List lines = new List(); @@ -174,6 +118,8 @@ private static void CopyWork(DirectoryInfo source, DirectoryInfo target, string public static void DeleteContentsOfDir(string path) { + if (!Directory.Exists(path)) + return; Logger.Log("Clearing " + path); DirectoryInfo directoryInfo = new DirectoryInfo(path); FileInfo[] files = directoryInfo.GetFiles(); @@ -382,5 +328,11 @@ public static int GetFilenameCounterLength(string file, string prefixToRemove = string onlyNumbersFilename = Regex.Replace(filenameNoExt, "[^.0-9]", ""); return onlyNumbersFilename.Length; } + + public static void DeleteIfExists (string path) + { + if (File.Exists(path)) + File.Delete(path); + } } } diff --git a/Code/IO/Paths.cs b/Code/IO/Paths.cs index 0c22f25..4ce92bd 100644 --- a/Code/IO/Paths.cs +++ b/Code/IO/Paths.cs @@ -12,6 +12,7 @@ internal class Paths public static string imgOutPath; public static string tempImgPath; public static string clipboardFolderPath; + //public static string convertTempPath; public static string progressLogfile; public static void Init() @@ -21,6 +22,7 @@ public static void Init() previewOutPath = Path.Combine(IOUtils.GetAppDataDir(), "preview-out"); imgInPath = Path.Combine(IOUtils.GetAppDataDir(), "img-in"); imgOutPath = Path.Combine(IOUtils.GetAppDataDir(), "img-out"); + //convertTempPath = Path.Combine(IOUtils.GetAppDataDir(), "convert-temp"); tempImgPath = Path.Combine(IOUtils.GetAppDataDir(), "loaded-img", "temp.png"); clipboardFolderPath = Path.Combine(IOUtils.GetAppDataDir(), "clipboard"); progressLogfile = Path.Combine(esrganPath, "prog"); diff --git a/Code/IO/ShippedEsrgan.cs b/Code/IO/ShippedEsrgan.cs index 9591e67..f3527e0 100644 --- a/Code/IO/ShippedEsrgan.cs +++ b/Code/IO/ShippedEsrgan.cs @@ -39,8 +39,11 @@ public static bool InstallationIsValid () requiredFiles.Add(Path.Combine(path, "ffmpeg.exe")); requiredFiles.Add(Path.Combine(path, "esrgan-ncnn-vulkan.exe")); requiredFiles.Add(Path.Combine(path, "pth2ncnn.exe")); + requiredFiles.Add(Path.Combine(path, "nvcompress.exe")); + requiredFiles.Add(Path.Combine(path, "nvtt.dll")); + requiredFiles.Add(Path.Combine(path, "gifski.exe")); - foreach(string dir in requiredDirs) + foreach (string dir in requiredDirs) { if (!Directory.Exists(dir)) { @@ -79,6 +82,8 @@ public static async Task Install () path7za = Path.Combine(path, "7za.exe"); File.WriteAllBytes(path7za, Resources.x64_7za); + File.WriteAllBytes(Path.Combine(path, "nvcompress.exe"), Resources.nvcompress); + File.WriteAllBytes(Path.Combine(path, "nvtt.dll"), Resources.nvtt); File.WriteAllBytes(Path.Combine(IOUtils.GetAppDataDir(), "esrgan.7z"), Resources.esrgan); File.WriteAllBytes(Path.Combine(IOUtils.GetAppDataDir(), "ncnn.7z"), Resources.esrgan_ncnn); File.WriteAllBytes(Path.Combine(IOUtils.GetAppDataDir(), "ffmpeg.7z"), Resources.ffmpeg); diff --git a/Code/ImageUtils/ImageProcessing.cs b/Code/ImageUtils/ImageProcessing.cs index 50c8573..2943bf5 100644 --- a/Code/ImageUtils/ImageProcessing.cs +++ b/Code/ImageUtils/ImageProcessing.cs @@ -4,6 +4,7 @@ using System.Threading.Tasks; using System.Windows.Forms; using Cupscale.Cupscale; +using Cupscale.ImageUtils; using Cupscale.IO; using Cupscale.Main; using Cupscale.UI; @@ -141,7 +142,7 @@ public static async Task ConvertImages(string path, Format format, bool removeAl public static async Task ConvertImage(string path, Format format, bool fillAlpha, bool keepExtension, bool deleteSource = true, string overrideOutPath = "") { - MagickImage img = IOUtils.GetMagickImage(path); + MagickImage img = ImgUtils.GetMagickImage(path); Logger.Log("Converting " + path + " - Target Format: " + format.ToString() + " - DeleteSource: " + deleteSource + " - FillAlpha: " + fillAlpha + " - KeepExt: " + keepExtension); string ext = "png"; if (format == Format.PngOpti) @@ -242,7 +243,7 @@ public static async Task PostProcess (string path, Format format) public static async Task PostProcessImage (string path, Format format, bool batchProcessing = false) { Logger.Log("PostProcess: Loading MagickImage from " + path); - MagickImage img = IOUtils.GetMagickImage(path); + MagickImage img = ImgUtils.GetMagickImage(path); string ext = "png"; if (format == Format.Source) ext = Path.GetExtension(path).Replace(".",""); @@ -278,16 +279,6 @@ public static async Task PostProcessImage (string path, Format format, bool batc img.Format = MagickFormat.Tga; ext = "tga"; } - if (format == Format.DDS) - { - img.Format = MagickFormat.Dds; - ext = "dds"; - DdsCompression comp = DdsCompression.None; - if (Config.GetBool("ddsUseDxt")) - comp = DdsCompression.Dxt1; - DdsWriteDefines ddsDefines = new DdsWriteDefines { Compression = comp, Mipmaps = Config.GetInt("ddsMipsAmount") }; - img.Settings.SetDefines(ddsDefines); - } if (!(currentScaleMode == Upscale.ScaleMode.Percent && currentScaleValue == 100)) // Skip if target scale is 100% img = ResizeImage(img, currentScaleValue, currentScaleMode, currentFilter, onlyDownscale); @@ -309,6 +300,35 @@ public static async Task PostProcessImage (string path, Format format, bool batc } } + public static async Task PostProcessDDS (string path) + { + Logger.Log("PostProcess: Loading MagickImage from " + path); + MagickImage img = ImgUtils.GetMagickImage(path); + string ext = "dds"; + + if (!(currentScaleMode == Upscale.ScaleMode.Percent && currentScaleValue == 100)) // Skip if target scale is 100% + img = ResizeImage(img, currentScaleValue, currentScaleMode, currentFilter, onlyDownscale); + + img.Format = MagickFormat.Png00; + img.Write(path); + + string outPath = Path.ChangeExtension(img.FileName, ext); + + await NvCompress.SaveDds(path, outPath); + + if (Upscale.currentMode == Upscale.UpscaleMode.Batch) + PostProcessingQueue.lastOutfile = outPath; + + if (Upscale.currentMode == Upscale.UpscaleMode.Single) + MainUIHelper.lastOutfile = outPath; + + if (outPath != path) + { + Logger.Log("Deleting source file: " + path); + File.Delete(path); + } + } + public static MagickImage ResizeImage (MagickImage img, int scaleValue, Upscale.ScaleMode scaleMode, Upscale.Filter filter, bool onlyDownscale) { img.FilterType = FilterType.Mitchell; diff --git a/Code/ImageUtils/ImgUtils.cs b/Code/ImageUtils/ImgUtils.cs index bac7268..654333c 100644 --- a/Code/ImageUtils/ImgUtils.cs +++ b/Code/ImageUtils/ImgUtils.cs @@ -1,15 +1,76 @@ -using System; +using DdsFileTypePlus; +using ImageMagick; +using PaintDotNet; +using System; using System.Collections.Generic; using System.Drawing; +using System.IO; using System.Linq; using System.Text; using System.Threading.Tasks; +using System.Windows.Forms; namespace Cupscale.ImageUtils { class ImgUtils { - public static int GetScale (Image imgFrom, Image imgTo) + public static Image GetImage(string path) + { + Logger.Log("IOUtils.GetImage: Reading Image from " + path); + using MemoryStream stream = new MemoryStream(File.ReadAllBytes(path)); + Image img = Image.FromStream(stream); + Logger.Log("[OK]", true, true); + return img; + } + + public static MagickImage GetMagickImage(string path) + { + Logger.Log("IOUtils.GetMagickImage: Reading Image from " + path); + MagickImage image; + if (Path.GetExtension(path).ToLower() == ".dds") + { + try + { + image = new MagickImage(path); // Try reading DDS with IM, fall back to DdsFileTypePlusHack if it fails + } + catch + { + Logger.Log("Failed to read DDS using Mackig.NET - Trying DdsFileTypePlusHack"); + try + { + Surface surface = DdsFile.Load(path); + image = ConvertToMagickImage(surface); + image.HasAlpha = DdsFile.HasTransparency(surface); + } + catch (Exception e) + { + MessageBox.Show("This DDS format is incompatible.\n\n" + e.Message); + return null; + } + } + } + else + { + image = new MagickImage(path); + } + Logger.Log("[OK]", true, true); + return image; + } + + public static MagickImage ConvertToMagickImage(Surface surface) + { + MagickImage result; + Bitmap bitmap = surface.CreateAliasedBitmap(); + using (MemoryStream memoryStream = new MemoryStream()) + { + bitmap.Save(memoryStream, System.Drawing.Imaging.ImageFormat.Png); + memoryStream.Position = 0; + result = new MagickImage(memoryStream, new MagickReadSettings() { Format = MagickFormat.Png00 }); + } + return result; + } + + public static int GetScale (Image imgFrom, Image imgTo) { return (int)Math.Round(GetScaleFloat(imgFrom, imgTo)); } @@ -18,5 +79,7 @@ public static float GetScaleFloat(Image imgFrom, Image imgTo) { return (float)imgTo.Width / (float)imgFrom.Width; } + + } } diff --git a/Code/ImageUtils/NvCompress.cs b/Code/ImageUtils/NvCompress.cs new file mode 100644 index 0000000..30747d9 --- /dev/null +++ b/Code/ImageUtils/NvCompress.cs @@ -0,0 +1,69 @@ +using Cupscale.UI; +using System; +using System.Collections.Generic; +using System.Diagnostics; +using System.IO; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace Cupscale.ImageUtils +{ + class NvCompress + { + static Process currentProcess; + + public static async Task SaveDds (string inputFile, string outputPath) + { + string dxtString = Config.Get("dxtMode").ToLower().Replace("off", "rgb"); + if (dxtString.Contains(" ")) + dxtString = dxtString.Split(' ')[0]; + await Run(inputFile, outputPath, dxtString, Config.GetBool("alpha"), Config.GetBool("ddsEnableMips")); + + } + + public static async Task Run(string inpath, string outpath, string dxtMode, bool alpha, bool enableMips) + { + inpath = inpath.WrapPath(true, true); + outpath = outpath.WrapPath(true, false); + + string alphaStr = ""; + if (alpha) + alphaStr = " -alpha "; + + string mipStr = " -nomips "; + if (enableMips) + mipStr = ""; + + string cmd2 = "/C cd /D " + Config.Get("esrganPath").WrapPath() + + " & nvcompress.exe -" + dxtMode + alphaStr + mipStr + inpath + outpath; + Logger.Log("CMD: " + cmd2); + Process nvCompress = new Process(); + nvCompress.StartInfo.UseShellExecute = false; + nvCompress.StartInfo.RedirectStandardOutput = true; + nvCompress.StartInfo.RedirectStandardError = true; + nvCompress.StartInfo.CreateNoWindow = true; + nvCompress.StartInfo.FileName = "cmd.exe"; + nvCompress.StartInfo.Arguments = cmd2; + nvCompress.OutputDataReceived += OutputHandler; + nvCompress.ErrorDataReceived += OutputHandler; + currentProcess = nvCompress; + nvCompress.Start(); + nvCompress.BeginOutputReadLine(); + nvCompress.BeginErrorReadLine(); + while (!nvCompress.HasExited) + await Task.Delay(50); + } + + private static void OutputHandler(object sendingProcess, DataReceivedEventArgs output) + { + if (output == null || output.Data == null) + return; + + string data = output.Data; + + if(data.Length >= 5) + Logger.Log("[NVCOMPRESS] " + data.Replace("\n", " ").Replace("\r", " ")); + } + } +} diff --git a/Code/Main/Logger.cs b/Code/Main/Logger.cs index 2aa24bd..6458692 100644 --- a/Code/Main/Logger.cs +++ b/Code/Main/Logger.cs @@ -35,7 +35,7 @@ public static void Log(string s, bool logToFile = true, bool noLineBreak = false public static void LogToFile(string s, bool noLineBreak) { if (string.IsNullOrWhiteSpace(logFile)) - logFile = Path.Combine(IOUtils.GetAppDataDir(), "log.txt"); + logFile = Path.Combine(IOUtils.GetAppDataDir(), "sessionlog.txt"); string time = DT.Now.Month + "-" + DT.Now.Day + "-" + DT.Now.Year + " " + DT.Now.Hour + ":" + DT.Now.Minute + ":" + DT.Now.Second; try diff --git a/Code/Main/MainForm.Designer.cs b/Code/Main/MainForm.Designer.cs index 0d6b94c..91487e4 100644 --- a/Code/Main/MainForm.Designer.cs +++ b/Code/Main/MainForm.Designer.cs @@ -3,10 +3,6 @@ using System.Drawing; using System.Windows.Forms; using Cupscale.UI; -using Cyotek.Windows.Forms; -using Manina.Windows.Forms; -using TabControl = Manina.Windows.Forms.TabControl; -using Tab = Manina.Windows.Forms.Tab; using ImageBox = Cyotek.Windows.Forms.ImageBox; using Cupscale.Properties; using System.Drawing.Drawing2D; diff --git a/Code/Main/MainForm.cs b/Code/Main/MainForm.cs index 8ba83e5..26352f1 100644 --- a/Code/Main/MainForm.cs +++ b/Code/Main/MainForm.cs @@ -4,9 +4,6 @@ using System.Windows.Forms; using Cupscale.UI; using Cyotek.Windows.Forms; -using Manina.Windows.Forms; -using TabControl = Manina.Windows.Forms.TabControl; -using Tab = Manina.Windows.Forms.Tab; using ImageBox = Cyotek.Windows.Forms.ImageBox; using Cupscale.Properties; using System.Drawing.Drawing2D; @@ -17,6 +14,7 @@ using Cupscale.IO; using Cupscale.Cupscale; using Win32Interop.Structs; +using Cupscale.ImageUtils; namespace Cupscale { @@ -218,6 +216,7 @@ private void batchTab_DragDrop(object sender, DragEventArgs e) async Task DragNDrop (string [] files) { Logger.Log("Dropped " + files.Length + " file(s), files[0] = " + files[0]); + IOUtils.DeleteContentsOfDir(Paths.tempImgPath.GetParentDir()); string path = files[0]; DialogForm loadingDialogForm = null; if (IOUtils.IsPathDirectory(path)) @@ -256,7 +255,7 @@ async Task DragNDrop (string [] files) bool fillAlpha = !bool.Parse(Config.Get("alpha")); await ImageProcessing.ConvertImage(path, ImageProcessing.Format.PngRaw, fillAlpha, false, false, Paths.tempImgPath); Logger.Log("Done Preprocessing"); - previewImg.Image = IOUtils.GetImage(Paths.tempImgPath); + previewImg.Image = ImgUtils.GetImage(Paths.tempImgPath); Program.lastFilename = path; MainUIHelper.currentScale = 1; previewImg.ZoomToFit(); diff --git a/Code/Main/PostProcessingQueue.cs b/Code/Main/PostProcessingQueue.cs index 3e35406..fafc783 100644 --- a/Code/Main/PostProcessingQueue.cs +++ b/Code/Main/PostProcessingQueue.cs @@ -70,7 +70,6 @@ public static async Task ProcessQueue () Logger.Log("[Queue] Post-Processing " + Path.GetFileName(file)); sw.Restart(); await Upscale.PostprocessingSingle(file, true); - Logger.Log("changing outfilename (not)"); string outFilename = Upscale.FilenamePostprocessingSingle(lastOutfile); outputFiles.Add(outFilename); Logger.Log("[Queue] Done Post-Processing " + Path.GetFileName(file) + " in " + sw.ElapsedMilliseconds + "ms"); diff --git a/Code/Main/Program.cs b/Code/Main/Program.cs index acc51b8..f152003 100644 --- a/Code/Main/Program.cs +++ b/Code/Main/Program.cs @@ -4,6 +4,7 @@ using System.Threading.Tasks; using System.Windows.Forms; using Cupscale.Forms; +using Cupscale.ImageUtils; using Cupscale.IO; using Cupscale.UI; using ImageMagick; @@ -32,6 +33,7 @@ private static void Main() Application.SetCompatibleTextRenderingDefault(defaultValue: false); Application.EnableVisualStyles(); Console.WriteLine("Main()"); + IOUtils.DeleteIfExists(Path.Combine(IOUtils.GetAppDataDir(), "sessionlog.txt")); Config.Init(); Paths.Init(); EsrganData.CheckModelDir(); diff --git a/Code/Main/Upscale.cs b/Code/Main/Upscale.cs index 57ede84..1315ba3 100644 --- a/Code/Main/Upscale.cs +++ b/Code/Main/Upscale.cs @@ -136,7 +136,7 @@ public static async Task PostprocessingSingle (string path, bool batchProcessing if (outputFormat.Text == ExportFormats.TGA.ToStringTitleCase()) await ImageProcessing.PostProcessImage(path, ImageProcessing.Format.TGA, batchProcessing); if (outputFormat.Text == ExportFormats.DDS.ToStringTitleCase()) - await ImageProcessing.PostProcessImage(path, ImageProcessing.Format.DDS, batchProcessing); + await ImageProcessing.PostProcessDDS(path); } public static async Task FilenamePostprocessing () diff --git a/Code/OS/ESRGAN.cs b/Code/OS/ESRGAN.cs index a72b0d3..8bd8172 100644 --- a/Code/OS/ESRGAN.cs +++ b/Code/OS/ESRGAN.cs @@ -51,8 +51,8 @@ public static async Task UpscaleBasic(string inpath, string outpath, ModelData m { Program.mainForm.SetProgress(100f, "Merging into preview..."); await Program.PutTaskDelay(); - Image outImg = IOUtils.GetImage(Path.Combine(Paths.previewOutPath, "preview.png.tmp")); - Image inputImg = IOUtils.GetImage(Paths.tempImgPath); + Image outImg = ImgUtils.GetImage(Path.Combine(Paths.previewOutPath, "preview.png.tmp")); + Image inputImg = ImgUtils.GetImage(Paths.tempImgPath); MainUIHelper.previewImg.Image = outImg; MainUIHelper.currentOriginal = inputImg; MainUIHelper.currentOutput = outImg; diff --git a/Code/Preview/ClipboardPreview.cs b/Code/Preview/ClipboardPreview.cs index 4162dfa..0576411 100644 --- a/Code/Preview/ClipboardPreview.cs +++ b/Code/Preview/ClipboardPreview.cs @@ -1,4 +1,5 @@ using Cupscale.Forms; +using Cupscale.ImageUtils; using Cupscale.UI; using ImageMagick; using System; @@ -29,13 +30,13 @@ public static async void CopyToClipboardSideBySide(bool saveToFile, bool fullIma { if (fullImage) { - originalPreview = new Bitmap(IOUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview-input-scaled.png"))); - resultPreview = new Bitmap(IOUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview-merged.png"))); + originalPreview = new Bitmap(ImgUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview-input-scaled.png"))); + resultPreview = new Bitmap(ImgUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview-merged.png"))); } else { - originalPreview = new Bitmap(IOUtils.GetImage(Path.Combine(IO.Paths.previewPath, "preview.png"))); - resultPreview = new Bitmap(IOUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview.png.tmp"))); + originalPreview = new Bitmap(ImgUtils.GetImage(Path.Combine(IO.Paths.previewPath, "preview.png"))); + resultPreview = new Bitmap(ImgUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview.png.tmp"))); } } catch @@ -129,13 +130,13 @@ public static async void CopyToClipboardSlider(bool saveToFile, bool fullImage = { if (fullImage) { - originalPreview = new Bitmap(IOUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview-input-scaled.png"))); - resultPreview = new Bitmap(IOUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview-merged.png"))); + originalPreview = new Bitmap(ImgUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview-input-scaled.png"))); + resultPreview = new Bitmap(ImgUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview-merged.png"))); } else { - originalPreview = new Bitmap(IOUtils.GetImage(Path.Combine(IO.Paths.previewPath, "preview.png"))); - resultPreview = new Bitmap(IOUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview.png.tmp"))); + originalPreview = new Bitmap(ImgUtils.GetImage(Path.Combine(IO.Paths.previewPath, "preview.png"))); + resultPreview = new Bitmap(ImgUtils.GetImage(Path.Combine(IO.Paths.previewOutPath, "preview.png.tmp"))); } } catch @@ -264,8 +265,8 @@ public static async void BeforeAfterAnim (bool save, bool h264) string img1 = Path.Combine(IO.Paths.previewPath, "preview.png"); string img2 = Path.Combine(IO.Paths.previewOutPath, "preview.png.tmp"); - Image image1 = IOUtils.GetImage(img1); - Image image2 = IOUtils.GetImage(img2); + Image image1 = ImgUtils.GetImage(img1); + Image image2 = ImgUtils.GetImage(img2); float scale = (float)image2.Width / (float)image1.Width; Logger.Log("Scale for animation: " + scale); @@ -273,17 +274,17 @@ public static async void BeforeAfterAnim (bool save, bool h264) if (image2.Width <= 2048 && image2.Height <= 2048) { - IOUtils.GetImage(img1).Scale(scale, InterpolationMode.NearestNeighbor).Save(Path.Combine(framesPath, "0.png")); + ImgUtils.GetImage(img1).Scale(scale, InterpolationMode.NearestNeighbor).Save(Path.Combine(framesPath, "0.png")); File.Copy(img2, Path.Combine(framesPath, "1.png"), true); if (h264) { await FFmpegCommands.FramesToOneFpsMp4(framesPath, false, 14, 9, "", false); + File.Move(Path.Combine(tempPath, "frames." + ext), outpath); } else { - await FFmpegCommands.FramesToGif(framesPath, false, 1, "", false); + await FFmpeg.RunGifski(" -r 1 -W 2048 -q -o " + outpath.WrapPath() + " \"" + framesPath + "/\"*.\"png\""); } - File.Move(Path.Combine(tempPath, "frames." + ext), outpath); if (save) { diff --git a/Code/Preview/PreviewMerger.cs b/Code/Preview/PreviewMerger.cs index f864203..a2fe94f 100644 --- a/Code/Preview/PreviewMerger.cs +++ b/Code/Preview/PreviewMerger.cs @@ -28,7 +28,7 @@ public static void Merge () outputCutoutPath = Path.Combine(Paths.previewOutPath, "preview.png.tmp"); //MagickImage sourceImg = IOUtils.GetMagickImage(Paths.tempImgPath); - Image sourceImg = IOUtils.GetImage(Paths.tempImgPath); + Image sourceImg = ImgUtils.GetImage(Paths.tempImgPath); int scale = GetScale(); if (sourceImg.Width * scale > 6000 || sourceImg.Height * scale > 6000) { @@ -51,17 +51,17 @@ static void MergeScrollable () string scaledPrevPath = Path.Combine(Paths.previewOutPath, "preview-input-scaled.png"); //Image image = MergeOnDisk(scale, scaledPrevPath); Image image = MergeInMemory(scale); - MainUIHelper.currentOriginal = IOUtils.GetImage(Paths.tempImgPath); + MainUIHelper.currentOriginal = ImgUtils.GetImage(Paths.tempImgPath); MainUIHelper.currentOutput = image; - MainUIHelper.currentScale = ImgUtils.GetScale(IOUtils.GetImage(inputCutoutPath), IOUtils.GetImage(outputCutoutPath)); + MainUIHelper.currentScale = ImgUtils.GetScale(ImgUtils.GetImage(inputCutoutPath), ImgUtils.GetImage(outputCutoutPath)); UIHelpers.ReplaceImageAtSameScale(MainUIHelper.previewImg, image); Program.mainForm.SetProgress(0f, "Done."); } public static Image MergeInMemory(int scale) { - Image sourceImg = IOUtils.GetImage(Paths.tempImgPath); - Image cutout = IOUtils.GetImage(outputCutoutPath); + Image sourceImg = ImgUtils.GetImage(Paths.tempImgPath); + Image cutout = ImgUtils.GetImage(outputCutoutPath); if (sourceImg.Width * scale == cutout.Width && sourceImg.Height * scale == cutout.Height) { @@ -90,8 +90,8 @@ public static Image MergeInMemory(int scale) public static Image MergeOnDisk (int scale, string scaledPrevPath) { - MagickImage sourceImg = IOUtils.GetMagickImage(Paths.tempImgPath); - MagickImage cutout = IOUtils.GetMagickImage(outputCutoutPath); + MagickImage sourceImg = ImgUtils.GetMagickImage(Paths.tempImgPath); + MagickImage cutout = ImgUtils.GetMagickImage(outputCutoutPath); sourceImg.FilterType = Program.currentFilter; sourceImg.Resize(new Percentage(scale * 100)); sourceImg.Format = MagickFormat.Png; @@ -100,14 +100,14 @@ public static Image MergeOnDisk (int scale, string scaledPrevPath) sourceImg.Composite(cutout, (Gravity)1, new PointD(offsetX, offsetY), CompositeOperator.Replace); string mergedPreviewPath = Path.Combine(Paths.previewOutPath, "preview-merged.png"); sourceImg.Write(mergedPreviewPath); - return IOUtils.GetImage(mergedPreviewPath); + return ImgUtils.GetImage(mergedPreviewPath); } static void MergeOnlyCutout () { int scale = GetScale(); - MagickImage originalCutout = IOUtils.GetMagickImage(inputCutoutPath); + MagickImage originalCutout = ImgUtils.GetMagickImage(inputCutoutPath); originalCutout.FilterType = Program.currentFilter; originalCutout.Resize(new Percentage(scale * 100)); string scaledCutoutPath = Path.Combine(Paths.previewOutPath, "preview-input-scaled.png"); @@ -115,8 +115,8 @@ static void MergeOnlyCutout () originalCutout.Quality = 0; // Save preview as uncompressed PNG for max speed originalCutout.Write(scaledCutoutPath); - MainUIHelper.currentOriginal = IOUtils.GetImage(scaledCutoutPath); - MainUIHelper.currentOutput = IOUtils.GetImage(outputCutoutPath); + MainUIHelper.currentOriginal = ImgUtils.GetImage(scaledCutoutPath); + MainUIHelper.currentOutput = ImgUtils.GetImage(outputCutoutPath); MainUIHelper.previewImg.Image = MainUIHelper.currentOutput; MainUIHelper.previewImg.ZoomToFit(); @@ -127,8 +127,8 @@ static void MergeOnlyCutout () private static int GetScale() { - MagickImage val = IOUtils.GetMagickImage(inputCutoutPath); - MagickImage val2 = IOUtils.GetMagickImage(outputCutoutPath); + MagickImage val = ImgUtils.GetMagickImage(inputCutoutPath); + MagickImage val2 = ImgUtils.GetMagickImage(outputCutoutPath); int result = (int)Math.Round((float)val2.Width / (float)val.Width); return result; } diff --git a/Code/Properties/Resources.Designer.cs b/Code/Properties/Resources.Designer.cs index ea127b7..f0837b8 100644 --- a/Code/Properties/Resources.Designer.cs +++ b/Code/Properties/Resources.Designer.cs @@ -110,6 +110,26 @@ public static byte[] ffmpeg { } } + /// + /// Looks up a localized resource of type System.Byte[]. + /// + public static byte[] nvcompress { + get { + object obj = ResourceManager.GetObject("nvcompress", resourceCulture); + return ((byte[])(obj)); + } + } + + /// + /// Looks up a localized resource of type System.Byte[]. + /// + public static byte[] nvtt { + get { + object obj = ResourceManager.GetObject("nvtt", resourceCulture); + return ((byte[])(obj)); + } + } + /// /// Looks up a localized resource of type System.Drawing.Bitmap. /// diff --git a/Code/Properties/Resources.resx b/Code/Properties/Resources.resx index 26adeee..80d1b16 100644 --- a/Code/Properties/Resources.resx +++ b/Code/Properties/Resources.resx @@ -2470,6 +2470,12 @@ ..\Resources\ffmpeg.7z;System.Byte[], mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + ..\Resources\nvcompress.exe;System.Byte[], mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + ..\Resources\nvtt.dll;System.Byte[], mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + ..\Resources\questmark.png;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a diff --git a/Code/Resources/ffmpeg.7z b/Code/Resources/ffmpeg.7z index b5ed5ac..e41cf44 100644 Binary files a/Code/Resources/ffmpeg.7z and b/Code/Resources/ffmpeg.7z differ diff --git a/Code/Resources/nvcompress.exe b/Code/Resources/nvcompress.exe new file mode 100644 index 0000000..a6a2ba7 Binary files /dev/null and b/Code/Resources/nvcompress.exe differ diff --git a/Code/Resources/nvtt.dll b/Code/Resources/nvtt.dll new file mode 100644 index 0000000..32c07f8 Binary files /dev/null and b/Code/Resources/nvtt.dll differ diff --git a/Code/UI/ExtensionMethods.cs b/Code/UI/ExtensionMethods.cs index 07997e4..42cfcf9 100644 --- a/Code/UI/ExtensionMethods.cs +++ b/Code/UI/ExtensionMethods.cs @@ -56,9 +56,14 @@ public static string ToStringTitleCase(this Enum en) return en.ToString().TitleCase(); } - public static string WrapPath (this string path) + public static string WrapPath (this string path, bool addSpaceFront = false, bool addSpaceEnd = false) { - return "\"" + path + "\""; + string s = "\"" + path + "\""; + if (addSpaceFront) + s = " " + s; + if (addSpaceEnd) + s = s + " "; + return s; } public static string ReplaceInFilename (this string path, string textToFind, string textToReplace, bool includeExtension = true) diff --git a/Code/UI/MainUIHelper.cs b/Code/UI/MainUIHelper.cs index 6363266..b1f5f57 100644 --- a/Code/UI/MainUIHelper.cs +++ b/Code/UI/MainUIHelper.cs @@ -7,6 +7,7 @@ using System.Security.AccessControl; using System.Threading.Tasks; using System.Windows.Forms; +using Cupscale.ImageUtils; using Cupscale.IO; using Cupscale.Main; using Cupscale.OS; @@ -169,7 +170,7 @@ public static async void UpscalePreview(bool fullImage = false) public static void SaveCurrentCutout() { - UIHelpers.ReplaceImageAtSameScale(previewImg, IOUtils.GetImage(Paths.tempImgPath)); + UIHelpers.ReplaceImageAtSameScale(previewImg, ImgUtils.GetImage(Paths.tempImgPath)); string path = Path.Combine(Paths.previewPath, "preview.png"); Directory.CreateDirectory(Path.GetDirectoryName(path)); GetCurrentRegion().Save(path); @@ -239,7 +240,7 @@ public static bool DroppedImageIsValid(string path) { try { - MagickImage img = IOUtils.GetMagickImage(path); + MagickImage img = ImgUtils.GetMagickImage(path); if (img.Width > 4096 || img.Height > 4096) { MessageBox.Show("Image is too big for the preview!\nPlease use images with less than 4096 pixels on either side.", "Error");