示例#1
0
        private static Bitmap PdfImageToBitmap(PdfDictionary image)
        {
            string filter = image.Elements.GetName(PdfDictionary.PdfStream.Keys.Filter);

            switch (filter)
            {
            case "/DCTDecode":
                byte[] stream = image.Stream.Value;
                return(new Bitmap(new MemoryStream(stream)));

            //Thanks to VacentViscera - https://forum.pdfsharp.net/viewtopic.php?f=8&t=3801
            case "/FlateDecode":
                int width            = image.Elements.GetInteger(PdfImage.Keys.Width);
                int height           = image.Elements.GetInteger(PdfImage.Keys.Height);
                int bitsPerComponent = image.Elements.GetInteger(PdfImage.Keys.BitsPerComponent);

                FlateDecode flate     = new FlateDecode();
                byte[]      imageData = flate.Decode(image.Stream.Value);

                PixelFormat pixelFormat;

                switch (bitsPerComponent)
                {
                case 1:
                    pixelFormat = PixelFormat.Format1bppIndexed;
                    break;

                case 8:
                    pixelFormat = PixelFormat.Format8bppIndexed;
                    break;

                case 24:
                    pixelFormat = PixelFormat.Format24bppRgb;
                    break;

                default:
                    throw new Exception("Unknown pixel format: " + bitsPerComponent);
                }

                Bitmap bitmap  = new Bitmap(width, height, pixelFormat);
                var    bmpData = bitmap.LockBits(new Rectangle(0, 0, width, height), ImageLockMode.WriteOnly, pixelFormat);
                int    length  = (int)Math.Ceiling(width * bitsPerComponent / 8.0);

                for (int i = 0; i < height; i++)
                {
                    Marshal.Copy(imageData, i * length, new IntPtr(bmpData.Scan0.ToInt32() + i * bmpData.Stride), length);
                }

                bitmap.UnlockBits(bmpData);
                return(bitmap);

            default:
                return(null);
            }
        }
        private static PdfDictionary ProcessFilters(PdfDictionary dictionary)
        {
            PdfDictionary result;

            // Create a dictionary mapping (i.e. switch statement) to process the expected filters.
            var map = new Dictionary <string, Func <byte[], byte[]> >()
            {
                { "/FlateDecode", (d) => {
                      var decoder = new FlateDecode();
                      return(decoder.Decode(d));
                  } }
            };

            // Get all of the filters.
            var filters = ((PdfArray)dictionary.Elements["/Filter"])
                          .Elements.Where(e => e.IsName())
                          .Select(e => ((PdfName)e).Value)
                          .ToList();

            // If only one filter in array. Just rewrite the /Filter
            if (filters.Count == 1)
            {
                result = dictionary.Clone();
                result.Elements["/Filter"] = new PdfName(filters[0]);
                return(result);
            }

            // Process each filter in order. The last filter should be the actual encoded image.
            byte[] data = dictionary.Stream.Value;
            for (int index = 0; index < (filters.Count - 1); index++)
            {
                if (!map.ContainsKey(filters[index]))
                {
                    throw new NotSupportedException(String.Format("Encountered embedded image with multiple filters: \"{0}\". Unable to process the filter: \"{1}\".",
                                                                  String.Join(",", filters), filters[index]));
                }
                data = map[filters[index]].Invoke(data);
            }

            result = new PdfDictionary();
            result.Elements.Add("/Filter", new PdfName(filters.Last()));
            foreach (var element in dictionary.Elements.Where(e => !String.Equals(e.Key, "/Filter", StringComparison.OrdinalIgnoreCase)))
            {
                result.Elements.Add(element.Key, element.Value);
            }
            result.CreateStream(data);

            return(result);
        }