压缩图片或pdf
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
{ /// <summary> /// 压缩图片或pdf大小的Level /// </summary> public enum ReduceSizeLevel { Small, //文件(小) Middle, //文件 (中) Large, //文件 (大) None //不压缩 } public static class ReduceSizeHelper { #region 变量 /// <summary> /// 图片的大小 /// </summary> private static int[] Pix = new int[] { 1024, 1440, 1920 }; /// <summary> /// 图片最小要求 /// </summary> private static int[] PixMin = new int[] { 800, 1024, 1440 }; /// <summary> /// 图片的质量 /// </summary> private static int[] PicQuantity = new int[] { 90, 93, 96 }; /// <summary> /// 调整后的文件大小 /// </summary> private static int[] NewFileSize = new int[] { 204800, 409600, 614400 }; #endregion #region 公共方法 /// <summary> /// 压缩图片大小 /// </summary> /// <param name="info"></param> /// <param name="ext"></param> public static void ReduceImageSize(VMCustLoanDocInfo info, string ext, ReduceSizeLevel level) { if (level == ReduceSizeLevel.None) return; int maxPix = 2400; //压缩后的尺寸 int minPix = 800; //最小尺寸 int quantity = 95; //质量百分比 int maxFileSize = 204800; //压缩后的文件大小 switch (level) { case ReduceSizeLevel.Small: maxPix = Pix[0]; minPix = PixMin[0]; quantity = PicQuantity[0]; maxFileSize = NewFileSize[0]; break; case ReduceSizeLevel.Middle: maxPix = Pix[1]; minPix = PixMin[1]; quantity = PicQuantity[1]; maxFileSize = NewFileSize[1]; break; case ReduceSizeLevel.Large: maxPix = Pix[2]; minPix = PixMin[2]; quantity = PicQuantity[2]; maxFileSize = NewFileSize[2]; break; default: break; } FileInfo fileInfo = new FileInfo(info.DocName); if (fileInfo.Length <= maxFileSize) return; IList<string> tmpFileNames = new List<string>(); //临时文件 using (System.Drawing.Image img = ImageHelper.ResizeImage(System.Drawing.Image.FromFile(info.DocName), maxPix, maxPix)) { info.TmpFileName = Environment.GetFolderPath(Environment.SpecialFolder.InternetCache).TrimEnd('\\') + "\\" + Util.GetGuid() + ext; img.Save(info.TmpFileName); tmpFileNames.Add(info.TmpFileName); } string tmpFileName = info.TmpFileName; info.TmpFileName = reduceLoop(maxPix, minPix, quantity, maxFileSize, ref tmpFileNames, tmpFileName, ext); //删除临时文件 foreach (string fileName in tmpFileNames) { if (fileName == info.TmpFileName) continue; try { File.Delete(fileName); } catch { } } } /// <summary> /// 调整pdf里图片的大小 /// </summary> /// <param name="info"></param> /// <param name="level"></param> public static void ReducePDFSize(VMCustLoanDocInfo info, ReduceSizeLevel level) { if (level == ReduceSizeLevel.None) return; int maxPix = 2400; //压缩后的尺寸 int minPix = 800; //最小尺寸 int quantity = 95; //质量百分比 int maxFileSize = 204800; //压缩后的文件大小 switch (level) { case ReduceSizeLevel.Small: maxPix = Pix[0]; minPix = PixMin[0]; quantity = PicQuantity[0]; maxFileSize = NewFileSize[0]; break; case ReduceSizeLevel.Middle: maxPix = Pix[1]; minPix = PixMin[1]; quantity = PicQuantity[1]; maxFileSize = NewFileSize[1]; break; case ReduceSizeLevel.Large: maxPix = Pix[2]; minPix = PixMin[2]; quantity = PicQuantity[2]; maxFileSize = NewFileSize[2]; break; default: break; } FileInfo fileInfo = new FileInfo(info.DocName); if (fileInfo.Length <= maxFileSize) return; IList<string> tmpFileNames = new List<string>(); //临时文件 string imgExt = ".jpg"; using (Aspose.Pdf.Document document = new Aspose.Pdf.Document(info.DocName)) { if (fileInfo.Length <= maxFileSize * document.Pages.Count) return; foreach (Aspose.Pdf.Page page in document.Pages) { int idx = 1; foreach (Aspose.Pdf.XImage image in page.Resources.Images) { using (var imageStream = new MemoryStream()) { // To compress images change the image type and resolution image.Save(imageStream); imageStream.Seek(0, SeekOrigin.Begin); //// Control image quality for better compression string tmpFileName = Environment.GetFolderPath(Environment.SpecialFolder.InternetCache).TrimEnd('\\') + "\\" + Util.GetGuid() + imgExt; tmpFileNames.Add(tmpFileName); using (System.Drawing.Image img = System.Drawing.Image.FromStream(imageStream)) { JXJR.CMS.Utility.ImageHelper.SaveJpeg(tmpFileName, img, 95); } tmpFileName = reduceLoop(maxPix, minPix, quantity, maxFileSize, ref tmpFileNames, tmpFileName, imgExt); tmpFileNames.Add(tmpFileName); using (FileStream newStream = new FileStream(tmpFileName, FileMode.Open)) { page.Resources.Images.Replace(idx, newStream); } } idx = idx + 1; } } document.OptimizeResources(); // save the updated file info.TmpFileName = Environment.GetFolderPath(Environment.SpecialFolder.InternetCache).TrimEnd('\\') + "\\" + Util.GetGuid() + ".pdf"; document.Save(info.TmpFileName); fileInfo = new FileInfo(info.DocName); long size1 = fileInfo.Length; fileInfo = new FileInfo(info.TmpFileName); long size2 = fileInfo.Length; if (size2 > size1) { info.TmpFileName = info.DocName; } } } /// <summary> /// 把一个pdf分割成多个pdf /// </summary> /// <param name="pdfFileName">原始pdf文件名</param> /// <param name="newFileNamePrex">新pdf文件名的前面部分(后面部分是页码)</param> /// <param name="oneFilePageCount">分割后每个pdf文件包含的页数</param> /// <returns></returns> public static List<string> SplitPDFBarCode(string pdfFileName, string newFileNamePrex, int oneFilePageCount) { bool includeFirstPage = false; //分割后的存放路径 List<string> tmpFileNames = new List<string>(); if (!pdfFileName.ToLower().EndsWith(".pdf")) return tmpFileNames; using (Aspose.Pdf.Document pdfDocument = new Aspose.Pdf.Document(pdfFileName)) { FileInfo fileInfo = new FileInfo(pdfFileName); if (!fileInfo.Exists) return tmpFileNames; newFileNamePrex = fileInfo.DirectoryName.EndsWith(@"\") ? fileInfo.DirectoryName + newFileNamePrex : fileInfo.DirectoryName + @"\" + newFileNamePrex; int i = includeFirstPage ? 1 : 2; //includeFirstPage是false时 不含首页(可能是条形码页面) while (i <= pdfDocument.Pages.Count) { int pageCount = 1; using (Aspose.Pdf.Document newDocument = new Aspose.Pdf.Document()) { int iFrom = i; while (i <= pdfDocument.Pages.Count && pageCount <= oneFilePageCount) { Aspose.Pdf.Page pdfPage = pdfDocument.Pages[i]; newDocument.Pages.Add(pdfPage); pageCount++; i++; } string newFileName = newFileNamePrex; if (pdfDocument.Pages.Count <= oneFilePageCount) { //不需要用页码标识 newFileName = newFileName + ".pdf"; } else { if (includeFirstPage) { newFileName = oneFilePageCount > 1 ? newFileName + "_" + iFrom + "-" + (i - 1) + ".pdf" : newFileName + "_" + (i - 1) + ".pdf"; } else { newFileName = oneFilePageCount > 1 ? newFileName + "_" + (iFrom - 1) + "-" + (i - 2) + ".pdf" : newFileName + "_" + (i - 2) + ".pdf"; } } if (File.Exists(newFileName)) { try { File.Delete(newFileName); } catch { MyMessageBox.Warning("无法删除" + newFileName + ",文件可能已经被打开,请先关闭该文件"); return new List<string>(); } } newDocument.Save(newFileName); tmpFileNames.Add(newFileName); } } return tmpFileNames; }//using } /// <summary> /// 把一个pdf分割成多个pdf /// </summary> /// <param name="pdfFileName">原始pdf文件名</param> /// <param name="oneFilePageCount">分割后每个pdf文件包含的页数</param> /// <returns></returns> public static List<string> SplitPDF(string pdfFileName, int oneFilePageCount) { bool includeFirstPage = true; //分割后的存放路径 List<string> tmpFileNames = new List<string>(); if (!pdfFileName.ToLower().EndsWith(".pdf")) return tmpFileNames; using (Aspose.Pdf.Document pdfDocument = new Aspose.Pdf.Document(pdfFileName)) { if (pdfDocument.Pages.Count <= oneFilePageCount) { tmpFileNames.Add(pdfFileName); return tmpFileNames; } FileInfo fileInfo = new FileInfo(pdfFileName); if (!fileInfo.Exists) return tmpFileNames; string newFileNamePrex = ""; //新pdf文件名的前面部分(后面部分是页码) newFileNamePrex = fileInfo.Name.Substring(0, fileInfo.Name.Length - fileInfo.Extension.Length); newFileNamePrex = fileInfo.DirectoryName.EndsWith(@"\") ? fileInfo.DirectoryName + newFileNamePrex : fileInfo.DirectoryName + @"\" + newFileNamePrex; int i = includeFirstPage ? 1 : 2; //includeFirstPage是false时 不含首页(可能是条形码页面) while (i <= pdfDocument.Pages.Count) { int pageCount = 1; using (Aspose.Pdf.Document newDocument = new Aspose.Pdf.Document()) { int iFrom = i; while (i <= pdfDocument.Pages.Count && pageCount <= oneFilePageCount) { Aspose.Pdf.Page pdfPage = pdfDocument.Pages[i]; newDocument.Pages.Add(pdfPage); pageCount++; i++; } string newFileName = newFileNamePrex; if (includeFirstPage) { newFileName = oneFilePageCount > 1 ? newFileName + "_" + iFrom + "-" + (i - 1) + ".pdf" : newFileName + "_" + (i - 1) + ".pdf"; } else { newFileName = oneFilePageCount > 1 ? newFileName + "_" + (iFrom - 1) + "-" + (i - 2) + ".pdf" : newFileName + "_" + (i - 2) + ".pdf"; } if (File.Exists(newFileName)) { try { File.Delete(newFileName); } catch { MyMessageBox.Warning("无法删除" + newFileName + ",文件可能已经被打开,请先关闭该文件"); return new List<string>(); } } newDocument.Save(newFileName); tmpFileNames.Add(newFileName); } } return tmpFileNames; }//using } #endregion #region 私有方法 /// <summary> /// 循环调整图片直到满足要求 /// </summary> /// <param name="maxPix">最大分辨率</param> /// <param name="minPix">最小分辨率</param> /// <param name="quantity">图片质量百分比</param> /// <param name="maxFileSize">最大文件大小</param> /// <param name="tmpFileNames">调整过程中产生的临时文件</param> /// <param name="tmpFileName">初始文件名</param> /// <param name="ext">文件后缀名</param> /// <returns></returns> private static string reduceLoop(int maxPix, int minPix, int quantity, int maxFileSize, ref IList<string> tmpFileNames, string tmpFileName, string ext) { FileInfo fileInfo = new FileInfo(tmpFileName); while (fileInfo.Length > maxFileSize) //循环,直到满足要求 { if ((int)(maxPix * 0.9) > minPix) maxPix = (int)(maxPix * 0.9); //继续调整大小 using (System.Drawing.Image img2 = ImageHelper.ResizeImage(System.Drawing.Image.FromFile(tmpFileName), maxPix, maxPix)) { tmpFileName = Environment.GetFolderPath(Environment.SpecialFolder.InternetCache).TrimEnd('\\') + "\\" + Util.GetGuid() + ext; img2.Save(tmpFileName); tmpFileNames.Add(tmpFileName); fileInfo = new FileInfo(tmpFileName); if (fileInfo.Length > maxFileSize) { tmpFileName = Environment.GetFolderPath(Environment.SpecialFolder.InternetCache).TrimEnd('\\') + "\\" + Util.GetGuid() + ext; ImageHelper.SaveJpeg(tmpFileName, img2, quantity); tmpFileNames.Add(tmpFileName); fileInfo = new FileInfo(tmpFileName); quantity -= 5; //再降低质量 } }//using img2 }//while return tmpFileName; } ///// <summary> ///// 复制pdf文件 ///// </summary> ///// <param name="docName"></param> ///// <param name="newFileNamePrex">pdf文件名(不含".pdf")</param> ///// <returns></returns> //public static string CopyPDF(string docName, string newFileNamePrex) //{ // FileInfo fileInfo = new FileInfo(docName); // newFileNamePrex = fileInfo.DirectoryName.EndsWith(@"\") ? fileInfo.DirectoryName + newFileNamePrex : fileInfo.DirectoryName + @"\" + newFileNamePrex; // newFileNamePrex += ".pdf"; // File.Copy(docName, newFileNamePrex, true); // return newFileNamePrex; //} #endregion } }