/// <summary> /// Метод уменьшает размер картинок в одной папке и выдает результирующие файлы в другой /// </summary> /// <param name="inPath">Папка, содержащая файлы изображений для сжатия</param> /// <param name="outPath">Папка, куда необходимо поместить уменьшенные файлы изображений</param> /// <param name="logWriter">Интерфейс для записи логов работы программы</param> /// <param name="ignoringFiles">Строковой массив с именами файлов, которые необходимо игнорировать (не уменьшать и не удалять по завершении)</param> public static void Resize(string inPath, string outPath, ILogWriter logWriter, params string[] ignoringFiles) { long limit = 1048576; // размер в байтах. если файл меньше указанного размера, уменьшение не происходит // предварительное создание папок, если их не существует if (!Directory.Exists(inPath)) { Directory.CreateDirectory(inPath); } if (!Directory.Exists(outPath)) { Directory.CreateDirectory(outPath); } DirectoryInfo inDirectory = new DirectoryInfo(inPath); DirectoryInfo outDirectory = new DirectoryInfo(outPath); // Удаление файлов в результирующей папке foreach (var file in outDirectory.GetFiles()) { file.Delete(); } FileInfo[] myFiles = inDirectory.GetFiles("*.*", SearchOption.AllDirectories); // проверка совпадений переданных для игнорирования имен файлов и имен файлов в исходной папке var query = from x in myFiles join y in ignoringFiles on x.Name equals y select y; // завершение работы метода, в случае, если кроме игнорируемых файлов в исходной папке больше ничего нет if (myFiles.Length == query.Count()) { MessageManager.WriteErrorMessage($"В папке {inPath} нечего обрабатывать"); logWriter.WriteLogText($"В папке {inPath} нечего обрабатывать"); return; } foreach (FileInfo oldFile in myFiles) { // Если текущий файл в списке игнорируемых - переход на следующую итерацию if (ignoringFiles.Contains(oldFile.Name)) { continue; } ; // Если файл весит меньше лимита, выводится сообщение и переходим к следующей итерации if (oldFile.Length < limit) { string logSmallFile = $"Файл {oldFile.Name} весит {oldFile.Length / 1024}кб. Не обработан."; MessageManager.WriteWarningMessage(logSmallFile); logWriter.WriteLogText(logSmallFile); File.Move(oldFile.FullName, $"{outPath}\\{oldFile.Name}"); // перемещение файла в новую папку. continue; } Bitmap oldImage = null; try { oldImage = new Bitmap(oldFile.FullName); // попытка опознать текущий файл, как изображение } catch (Exception ex) { string logError = $"Файл \"{oldFile.Name}\" не получилось обработать, ошибка: {ex.Message}"; MessageManager.WriteErrorMessage(logError); logWriter.WriteLogText(logError); File.Move(oldFile.FullName, $"{outPath}\\{oldFile.Name}"); // перемещение файла в новую папку. continue; } int height = oldImage.Height; int width = oldImage.Width; // в зависимости от размера файла, получаем для него новые ширину и высоту, уменьшенные на соответствующую величину if (oldFile.Length < 2 * limit) { DecreaceSize(ref height, ref width, 2); } else if (oldFile.Length < 3 * limit) { DecreaceSize(ref height, ref width, 2.20); } else if (oldFile.Length < 5 * limit) { DecreaceSize(ref height, ref width, 2.50); } else if (oldFile.Length < 15 * limit) { DecreaceSize(ref height, ref width, 2.7); } else { DecreaceSize(ref height, ref width, 3); } // изменение разрешения картинки отменяем //float hor = oldImage.HorizontalResolution; //float vert = oldImage.VerticalResolution; //oldImage.SetResolution(hor / 2f, vert / 2f); Size mySize = new Size(width, height); Bitmap newImageFile = new Bitmap(oldImage, mySize); // создание нового изображения на основании старого с новыми шириной и высотой string oldFileReplaced = oldFile.Name.Replace(oldFile.Extension, ".JPEG"); string newFile = $"{outPath}\\{oldFileReplaced}"; newImageFile.Save(newFile, ImageFormat.Jpeg); FileInfo fileJustSaved = new FileInfo(newFile); oldImage.Dispose(); string logSuccess = $"Файл \"{oldFile.Name}\" обработан. " + $"Было {oldFile.Length / 1024}кб, стало {fileJustSaved.Length / 1024}кб"; MessageManager.WriteOkMessage(logSuccess); logWriter.WriteLogText(logSuccess); } // в конце удалаем все файлы из исходной папки, кроме игнорируемых foreach (FileInfo oldFile in myFiles) { if (!ignoringFiles.Contains(oldFile.Name)) { oldFile.Delete(); } } DirectoryInfo[] oldDirs = inDirectory.GetDirectories("*", SearchOption.AllDirectories); foreach (var dir in oldDirs) { if (dir.Exists) { try { dir.Delete(true); } catch (Exception) // в случае, когда пользователь не вышел из удаляемой папки - пропустить ошибку. { } } } }