GetImageProperties.cs
// 
// このコードは、DioDocs for PDF のサンプルの一部として提供されています。
// © MESCIUS inc. All rights reserved.
// 
using System;
using System.IO;
using System.Drawing;
using System.Collections.Generic;
using GrapeCity.Documents.Pdf;
using GrapeCity.Documents.Pdf.Graphics.Images;
using GrapeCity.Documents.Pdf.Spec;
using GrapeCity.Documents.Text;
using GrapeCity.Documents.Drawing;

namespace DsPdfWeb.Demos
{
    // このサンプルでは、PDF内の画像オブジェクトのID、画像の保存に使用されたフィルタ、
    // デコーダーのパラメータ、PdfImage辞書の内容など、PDFファイル内に存在する画像に関する
    // 低レベルの情報を取得する方法を紹介しています。
    // なお、このサンプルでは、参照のために読み込み元のPDFを結果のPDFの最後に出力しています。
    public class GetImageProperties
    {
        public int CreatePDF(Stream stream)
        {
            using var fs = File.OpenRead(Path.Combine("Resources", "PDFs", "Wetlands.pdf"));
            var docSrc = new GcPdfDocument();
            docSrc.Load(fs);

            // 読み込んだPDF内の画像を取得し、その情報を結果のPDFに出力します。
            var imageInfos = docSrc.GetImages();

            // 結果を出力するPDFです。
            var doc = new GcPdfDocument();
            var page = doc.NewPage();
            // 結果のテキストのためのTextLayoutを設定します。
            var tl = page.Graphics.CreateTextLayout();
            tl.DefaultFormat.Font = Common.Util.getFont();
            tl.DefaultFormat.FontSize = 14;
            tl.MaxWidth = doc.PageSize.Width;
            tl.MaxHeight = doc.PageSize.Height;
            tl.MarginAll = tl.Resolution;
            var captionFmt = new TextFormat(tl.DefaultFormat) { Font = StandardFonts.CourierBold, FontSize = tl.DefaultFormat.FontSize + 2 };

            int i = 0;
            foreach (var imageInfo in imageInfos)
            {
                tl.AppendLine($"画像 {++i}", captionFmt);

                // PdfImageBaseクラスは、読み込んだPDFファイル内の画像を表します。
                PdfImageBase img = imageInfo.Image;

                tl.AppendLine($"PdfImageBase.ObjID:{img.ObjID}");
                // PdfImageBaseクラスはPdfDictWrapperクラスから派生したもので、
                // 基となるPDFのストリームオブジェクトのプロパティ/データに
                // アクセスできるメソッドを持っています。
                using (PdfStreamInfo psi = img.GetPdfStreamInfo())
                {
                    tl.AppendLine($"PdfStreamInfo.Stream.Length:{psi.Stream.Length}");
                    tl.AppendLine($"PdfStreamInfo.ImageFilterName:{psi.ImageFilterName}");
                    tl.AppendLine($"PdfStreamInfo.ImageFilterDecodeParams:{psi.ImageFilterDecodeParams}");
                    // ImageFilterDecodeParamsが存在すれば、その詳細な内容を取得します。
                    if (psi.ImageFilterDecodeParams != null)
                    {
                        foreach (var kvp in psi.ImageFilterDecodeParams.Dict)
                        {
                            tl.AppendLine($"{kvp.Key}:{kvp.Value}");
                        }
                        // BlackIs1の値を取得する方法の例です。
                        var blackIs1 = psi.ImageFilterDecodeParams.GetBool(PdfName.Std.BlackIs1, null);
                        tl.AppendLine($"BlackIs1:{blackIs1}");
                    }
                }
                // PdfImage辞書のプロパティを取得します。
                tl.AppendLine();
                tl.AppendLine("PdfImage辞書のプロパティ:");
                foreach (KeyValuePair<PdfName, IPdfObject> kvp in img.PdfDict.Dict)
                {
                    tl.AppendLine($"{kvp.Key}:{kvp.Value}");
                }
                
                var cs = img.Get<IPdfObject>(PdfName.Std.ColorSpace);
                tl.AppendLine($"ColorSpace:{cs.GetType().Name} {cs}");
                var bpc = img.Get<IPdfObject>(PdfName.Std.BitsPerComponent);
                tl.AppendLine($"BitsPerComponent:{bpc?.GetType().Name} {bpc}");
                tl.AppendLine();
            }

            // 結果のテキストを描画します。
            tl.PerformLayout(true);
            while (true)
            {
                var splitResult = tl.Split(null, out TextLayout rest);
                page.Graphics.DrawTextLayout(tl, PointF.Empty);
                if (splitResult != SplitResult.Split)
                    break;
                tl = rest;
                tl.MarginTop = tl.Resolution;
                page = doc.Pages.Add();
            }

            // 参照のために読み込み元のPDFを結果のPDFに追加します。
            doc.MergeWithDocument(docSrc);

            // PDF ドキュメントを保存します。
            doc.Save(stream);
            return doc.Pages.Count;
        }
    }
}