public static BitmapSource Render(this PdfDocumentWrapper doc, int page, double factor, bool fixDpi = true) { var scale = DpiHelper.GetCurrentScaleFactor(); var dpiX = fixDpi ? scale.Horizontal * DpiHelper.DefaultDpi : 96; var dpiY = fixDpi ? scale.Vertical * DpiHelper.DefaultDpi : 96; Bitmap bitmap; lock (LockObj) { var size = doc.PdfDocument.PageSizes[page]; var realWidth = (int)Math.Round(size.Width * scale.Horizontal * factor); var realHeight = (int)Math.Round(size.Height * scale.Vertical * factor); bitmap = doc.PdfDocument.Render(page, realWidth, realHeight, dpiX, dpiY, PdfRenderFlags.LimitImageCacheSize | PdfRenderFlags.LcdText | PdfRenderFlags.Annotations | PdfRenderFlags.ForPrinting) as Bitmap; } var bs = bitmap?.ToBitmapSource(); bitmap?.Dispose(); bs?.Freeze(); return(bs); }
public static BitmapSource Render(this PdfPage page, double factor, bool fixDpi = true) { var scale = DpiHelper.GetCurrentScaleFactor(); var dpiX = fixDpi ? scale.Horizontal * DpiHelper.DefaultDpi : 96; var dpiY = fixDpi ? scale.Vertical * DpiHelper.DefaultDpi : 96; var realWidth = (int)Math.Round(page.Width * scale.Horizontal * factor); var realHeight = (int)Math.Round(page.Height * scale.Vertical * factor); var bitmap = new WriteableBitmap(realWidth, realHeight, dpiX, dpiY, PixelFormats.Bgr24, null); page.Render(bitmap, flags: RenderingFlags.LimitImageCache | RenderingFlags.Annotations | RenderingFlags.DontCatch | RenderingFlags.LcdText); bitmap.Freeze(); return(bitmap); }
public static Bitmap RenderPage(IntPtr context, IntPtr document, IntPtr page, double zoomFactor) { var pageBound = new Rectangle(); var ctm = new Matrix(); var pix = IntPtr.Zero; var dev = IntPtr.Zero; if (App.Is64Bit) { NativeMethods.BoundPage_64(document, page, ref pageBound); } else { NativeMethods.BoundPage_32(document, page, ref pageBound); } var scale = DpiHelper.GetCurrentScaleFactor(); var zoomX = zoomFactor * scale.Horizontal; var zoomY = zoomFactor * scale.Vertical; // gets the size of the page and multiplies it with zoom factors var width = (int)(pageBound.Width * zoomX); var height = (int)(pageBound.Height * zoomY); // sets the matrix as a scaling matrix (zoomX,0,0,zoomY,0,0) ctm.A = (float)zoomX; ctm.D = (float)zoomY; // creates a pixmap the same size as the width and height of the page if (App.Is64Bit) { pix = NativeMethods.NewPixmap_64(context, NativeMethods.LookupDeviceColorSpace_64(context, "DeviceRGB"), width, height); } else { pix = NativeMethods.NewPixmap_32(context, NativeMethods.LookupDeviceColorSpace_32(context, "DeviceRGB"), width, height); } // sets white color as the background color of the pixmap if (App.Is64Bit) { NativeMethods.ClearPixmap_64(context, pix, 0xFF); } else { NativeMethods.ClearPixmap_32(context, pix, 0xFF); } // creates a drawing device dev = App.Is64Bit ? NativeMethods.NewDrawDevice_64(context, pix) : NativeMethods.NewDrawDevice_32(context, pix); // draws the page on the device created from the pixmap if (App.Is64Bit) { NativeMethods.RunPage_64(document, page, dev, ref ctm, IntPtr.Zero); } else { NativeMethods.RunPage_32(document, page, dev, ref ctm, IntPtr.Zero); } if (App.Is64Bit) { NativeMethods.FreeDevice_64(dev); // frees the resources consumed by the device } else { NativeMethods.FreeDevice_32(dev); // frees the resources consumed by the device } dev = IntPtr.Zero; // creates a colorful bitmap of the same size of the pixmap var bmp = new Bitmap(width, height, PixelFormat.Format24bppRgb); var imageData = bmp.LockBits(new System.Drawing.Rectangle(0, 0, width, height), ImageLockMode.ReadWrite, bmp.PixelFormat); unsafe { // converts the pixmap data to Bitmap data byte *ptrSrcOrigin; if (App.Is64Bit) { ptrSrcOrigin = (byte *)NativeMethods.GetSamples_64(context, pix); // gets the rendered data from the pixmap } else { ptrSrcOrigin = (byte *)NativeMethods .GetSamples_32(context, pix); // gets the rendered data from the pixmap } var ptrDestOrigin = (byte *)imageData.Scan0; Parallel.For(0, height, y => { var ptrDest = ptrDestOrigin + imageData.Stride * y; var ptrSrc = ptrSrcOrigin + width * 4 * y; Parallel.For(0, width, x => { var pl = ptrDest + 3 * x; var sl = ptrSrc + 4 * x; //Swap these here instead of in MuPDF because most pdf images will be rgb or cmyk. //Since we are going through the pixels one by one anyway swap here to save a conversion from rgb to bgr. pl[2] = sl[0]; //b-r pl[1] = sl[1]; //g-g pl[0] = sl[2]; //r-b //sl[3] is the alpha channel, we will skip it here }); }); /*for (var y = 0; y < height; y++) * { * var pl = ptrDestOrigin; * var sl = ptrSrcOrigin; * for (var x = 0; x < width; x++) * { * //S these here instead of in MuPDF because most pdf images will be rgb or cmyk. * //Since we are going through the pixels one by one anyway swap here to save a conversion from rgb to bgr. * pl[2] = sl[0]; //b-r * pl[1] = sl[1]; //g-g * pl[0] = sl[2]; //r-b * //sl[3] is the alpha channel, we will skip it here * pl += 3; * sl += 4; * } * ptrDestOrigin += imageData.Stride; * ptrSrcOrigin += width * 4; * }*/ } bmp.UnlockBits(imageData); if (App.Is64Bit) { NativeMethods.DropPixmap_64(context, pix); } else { NativeMethods.DropPixmap_32(context, pix); } bmp.SetResolution(scale.Horizontal * DpiHelper.DefaultDpi, scale.Vertical * DpiHelper.DefaultDpi); return(bmp); }