Tana Gone
Tana Gone
1 min read

Categories

Rubyのpdf-reader GemだとJPXの日報からTextを取り出せるのに、SwiftのPDFKitでは問題が発生する。 表からTextの取り出しは出来るのだが、レイアウトが酷く壊れてしまうのだ。しかもその壊れ方に規則性を見いだせずにいる。そこでpdfのファイル構造を調べ始めた。 独自Text Extractorを実装する第一歩は、圧縮されたStream(FlateDecoder)からPDFオペレーターとオペランドを抜き出すことだ。

  • Editorで開くと
  %PDF-1.3
  %Äåòåë§ó ÐÄÆ
  4 0 obj
  << /Filter /FlateDecode /Length 10687 >>
  stream
  x½}Ë®‘å>¾"~@Æ(ԢՃÆh'(Y4f‘y4T=PkÑ¿?ÇhvŒtw#Ýý¦¦Z¨Îk÷ƒ‡FÚãÐèô¿_ÿrýûµÃÿúþÕ_ŸÓpý¯ëÿºþçõú}
  ...続く
  endstream
  endobj
  2 0 obj
  << /Type /Page /Parent 3 0 R /Resources 5 0 R /Contents 4 0 R /MediaBox [0 0 1191 842]
  /Rotate 0 >>
  endobj
  5 0 obj
  ...続く
  xref
  0 26
  0000000000 65535 f 
  0000098994 00000 n 
  ...続く
  trailer
  << /Size 26 /Root 14 0 R /Info 25 0 R /ID [ <735725ed4cc592daa990ec90c33352b6>
  <735725ed4cc592daa990ec90c33352b6> ] >>
  startxref
  419644
  %%EOF
  • バイナリーマーカー 圧縮されたsteamを持ってる事を示す。値はPDF作成ソフトにより異なる。Textが圧縮されているのではなくPDFオペレーターとオペランドの列が得られる。

    %Äåòåë§ó ÐÄÆ
    
  • PDFオペレーターとオペランド

    BT                           % Begin Text
    /F1 12 Tf                   % Font F1, size 12
    100 700 Td                  % Move to position (100, 700)
    (Hello World) Tj            % Show text "Hello World"
    150 -20 Td                  % Move 150 right, 20 down
    (Next line) Tj              % Show text "Next line"
    ET                           % End Text
    
  • 座標とテキスト情報

    q                           % Save graphics state
    1 0 0 1 50 750 cm          % Transformation matrix (移動)
    BT                         % Begin Text
    /F1 14 Tf                  % Font: F1, Size: 14pt
    0 0 Td                     % Text position: (0,0) - 変換後は(50,750)
    [(Hello) -200 (World)] TJ   % "Hello World" with kerning adjustment
    0 -18 Td                   % Move down 18pt
    (Second line) Tj           % Show "Second line"
    ET                         % End Text
    Q                          % Restore graphics state
    
  • PDFオペレータの詳細

    %テキスト関連オペレータ
    BT/ET     - テキストブロック開始/終了
    Tf        - フォントとサイズ設定
    Td/TD     - テキスト位置移動
    Tj        - 単純テキスト表示
    TJ        - カーニング調整付きテキスト表示
    Tm        - テキスト変換マトリクス設定
    %座標・変換オペレータ
    cm        - 変換マトリクス適用
    q/Q       - グラフィック状態保存/復元
    w         - 線幅設定
    RG/rg     - 色設定
    
  • PDFオブジェクト 1 0 obj1番目のオブジェクト、0番目のジェネレーション番号のPDFオブジェクトである事を示している。PDFオブジェクトは親子構造を持ち、下記の場合、2番目Resource属性のPagesの子を従えている。

    # PDFファイルは以下のような構造になっている
    # %PDF-1.4
    # 1 0 obj
    # 
    # /Type /Catalog
    # /Pages 2 0 R
    # >>
    # endobj
    
  • 調査方法 Cloude Desktopに次のようなPromptを投げると教えてくれる。

    Rubyにはpdf-reader GemがありPDFファイル内の文字列を取り出す事ができます。どのような仕組みなのですか?
    

    とか、

    macOSで動作するpdfファイルの構造を解析できる無料ソフトを紹介して下さい
    
  • Online PDF Inspect Tool Inspect PDF Online - PDFCrowd
    Claude share
    僕「PDFとは何か知りたい」 #PDF - Qiita
    PDF Dictionary 解説
    Exploring PDF — Basic Object. PDF is composed of basic objects… | by Kunho Lee | Medium
    PDF辞書とは何ですか?