تبدیل صفحات یک فایل PDF به تصویر، با استفاده از Acrobat SDK
نویسنده: وحید نصیری
تاریخ: ۱۳۹۱/۰۸/۱۲ ۰:۱۰
آدرس: www.dntips.ir
| مطالب | ۳۶۹۴ |
| نویسندگان | ۲۷۶ |
| گروههای مطالب | ۱۰۲۴ |
| نقشههای راه | ۱۱۹ |
| دورهها | ۱۴ |
| اشتراکها | ۱۷۹۱۴ |
using System;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Imaging;
using System.IO;
using System.Runtime.InteropServices;
using System.Threading;
using System.Windows.Forms;
using Acrobat; //Add a Com Object ref. to "Adobe Acrobat 10.0 Type Library" => Program Files\Adobe\Acrobat 10.0\Acrobat\acrobat.tlb
using Microsoft.Win32;
namespace PdfThumbnail.Lib
{
public static class PdfToImage
{
const string AdobeObjectsErrorMessage = "Failed to create the PDF object.";
const string BadFileErrorMessage = "Failed to open the PDF file.";
const string ClipboardError = "Failed to get the image from clipboard.";
const string SdkError = "This operation needs the Acrobat SDK(http://www.adobe.com/devnet/acrobat/downloads.html), which is combined with the full version of Adobe Acrobat.";
public static byte[] PdfPageToPng(string pdfFilePath, int thumbWidth = 600, int thumbHeight = 750, int pageNumber = 0)
{
byte[] imageData = null;
runJob((pdfDoc, pdfRect) =>
{
imageData = pdfPageToPng(thumbWidth, thumbHeight, pageNumber, pdfDoc, pdfRect);
}, pdfFilePath);
return imageData;
}
public static void AllPdfPagesToPng(Action<byte[], int, int> dataCallback, string pdfFilePath, int thumbWidth = 600, int thumbHeight = 750)
{
runJob((pdfDoc, pdfRect) =>
{
var numPages = pdfDoc.GetNumPages();
for (var pageNumber = 0; pageNumber < numPages; pageNumber++)
{
var imageData = pdfPageToPng(thumbWidth, thumbHeight, pageNumber, pdfDoc, pdfRect);
dataCallback(imageData, pageNumber + 1, numPages);
}
}, pdfFilePath);
}
static void runJob(Action<CAcroPDDoc, CAcroRect> job, string pdfFilePath)
{
if (!File.Exists(pdfFilePath))
throw new InvalidOperationException(BadFileErrorMessage);
var acrobatPdfDocType = Type.GetTypeFromProgID("AcroExch.PDDoc");
if (acrobatPdfDocType == null || !isAdobeSdkInstalled)
throw new InvalidOperationException(SdkError);
var pdfDoc = (CAcroPDDoc)Activator.CreateInstance(acrobatPdfDocType);
if (pdfDoc == null)
throw new InvalidOperationException(AdobeObjectsErrorMessage);
var acrobatPdfRectType = Type.GetTypeFromProgID("AcroExch.Rect");
var pdfRect = (CAcroRect)Activator.CreateInstance(acrobatPdfRectType);
var result = pdfDoc.Open(pdfFilePath);
if (!result)
throw new InvalidOperationException(BadFileErrorMessage);
job(pdfDoc, pdfRect);
releaseComObjects(pdfDoc, pdfRect);
}
public static byte[] ResizeImage(this Image image, int thumbWidth, int thumbHeight)
{
var srcWidth = image.Width;
var srcHeight = image.Height;
using (var bmp = new Bitmap(thumbWidth, thumbHeight, PixelFormat.Format32bppArgb))
{
using (var gr = Graphics.FromImage(bmp))
{
gr.SmoothingMode = SmoothingMode.HighQuality;
gr.PixelOffsetMode = PixelOffsetMode.HighQuality;
gr.CompositingQuality = CompositingQuality.HighQuality;
gr.InterpolationMode = InterpolationMode.High;
var rectDestination = new Rectangle(0, 0, thumbWidth, thumbHeight);
gr.DrawImage(image, rectDestination, 0, 0, srcWidth, srcHeight, GraphicsUnit.Pixel);
using (var memStream = new MemoryStream())
{
bmp.Save(memStream, ImageFormat.Png);
return memStream.ToArray();
}
}
}
}
static bool isAdobeSdkInstalled
{
get
{
return Registry.ClassesRoot.OpenSubKey("AcroExch.PDDoc", writable: false) != null;
}
}
private static Bitmap pdfPageToBitmap(int pageNumber, CAcroPDDoc pdfDoc, CAcroRect pdfRect)
{
var pdfPage = (CAcroPDPage)pdfDoc.AcquirePage(pageNumber);
if (pdfPage == null)
throw new InvalidOperationException(BadFileErrorMessage);
var pdfPoint = (CAcroPoint)pdfPage.GetSize();
pdfRect.Left = 0;
pdfRect.right = pdfPoint.x;
pdfRect.Top = 0;
pdfRect.bottom = pdfPoint.y;
pdfPage.CopyToClipboard(pdfRect, 0, 0, 100);
Bitmap pdfBitmap = null;
var thread = new Thread(() =>
{
var data = Clipboard.GetDataObject();
if (data != null && data.GetDataPresent(DataFormats.Bitmap))
pdfBitmap = (Bitmap)data.GetData(DataFormats.Bitmap);
});
thread.SetApartmentState(ApartmentState.STA);
thread.Start();
thread.Join();
Marshal.ReleaseComObject(pdfPage);
return pdfBitmap;
}
private static byte[] pdfPageToPng(int thumbWidth, int thumbHeight, int pageNumber, CAcroPDDoc pdfDoc, CAcroRect pdfRect)
{
var pdfBitmap = pdfPageToBitmap(pageNumber, pdfDoc, pdfRect);
if (pdfBitmap == null)
throw new InvalidOperationException(ClipboardError);
var pdfImage = pdfBitmap.GetThumbnailImage(thumbWidth, thumbHeight, null, IntPtr.Zero);
// (+ 7 for template border)
var imageData = pdfImage.ResizeImage(thumbWidth + 7, thumbHeight + 7);
return imageData;
}
private static void releaseComObjects(CAcroPDDoc pdfDoc, CAcroRect pdfRect)
{
pdfDoc.Close();
Marshal.ReleaseComObject(pdfRect);
Marshal.ReleaseComObject(pdfDoc);
}
}
}
using System;
using System.IO;
using System.Windows.Forms;
using PdfThumbnail.Lib;
namespace PdfThumbnail
{
class Program
{
static void Main(string[] args)
{
var pdfPath = Application.StartupPath + @"\test.pdf";
PdfToImage.AllPdfPagesToPng((pageImageData, pageNumber, numPages) =>
{
Console.WriteLine("Page {0}/{1}", pageNumber, numPages);
File.WriteAllBytes(string.Format("{0}\\page-{1}.png", Application.StartupPath, pageNumber), pageImageData);
}, pdfPath);
}
}
}
gs -dNOPAUSE -q -sDEVICE=pnggray -r500 -dBATCH -dFirstPage=2 -dLastPage=2 -sOutputFile=test.png test.pdf
string destinationFilePath = ("d:\\temp\\1.jpg");
GhostscriptWrapper.GenerateOutput("d:\\temp\\1.pdf", destinationFilePath,
new GhostscriptSettings
{
Device = GhostscriptDevices.jpeg,
Page = new GhostscriptPages
{
Start = 1,
End = 1,
AllPages = true,
},
Resolution = new Size
{
Height = 150,
Width = 150
},
Size = new GhostscriptPageSize
{
Native = GhostscriptPageSizes.a4
}
}); public static class Cmd
{
public static int Execute(string filename, string arguments)
{
var startInfo = new ProcessStartInfo
{
CreateNoWindow = true,
FileName = filename,
Arguments = arguments,
};
using (var process = new Process { StartInfo = startInfo })
{
try
{
process.Start();
process.WaitForExit(30000);
return process.ExitCode;
}
catch (Exception exception)
{
if (!process.HasExited)
{
process.Kill();
}
return (int)ExitCode.Exception;
}
}
}
}