PDF ファイルから
テキストを抜き出す

まずは、テキストを抜き出してみたかったので、そのメモから。

テキストの埋め込んである PDF からテキストを抜き出したい場合は、PDFDocument.alloc.initWithURL(url) というメソッドを使う。これは、url にある PDF ファイルの内容で PDFDocument オブジェクトをつくる。 url は NSURL オブジェクトじゃないといけないので、ファイルへのパスから fileURLWithPath(path) というメソッドを使って NSURL オブジェクトをつくる。

url = NSURL.fileURLWithPath(filePath)

pdfDocument = PDFDocument.alloc.initWithURL(url)

これで、pdfDocument という PDFDocument オブジェクトができたわけだけど、埋め込まれたテキストを取り出すには、string というメソッドを使う。ただ、これだと、NSString オブジェクトなので、Ruby で扱える String オブジェクトにするためには、to_s をくっつける。match とかを使わなければ NSString のままでも問題はあまりない。

content = pdfDocument.string.to_s

これらを組み合わせて、Ruby スクリプトを保存したフォルダにある sample.pdf というテキストの埋め込まれた PDF ファイルからテキストを抜き出して表示するには、次のようなスクリプトを書けばいけるはず。

require 'osx/cocoa'

include OSX

require_framework 'Quartz'

content = PDFDocument.alloc.initWithURL(NSURL.fileURLWithPath("sample.pdf")).string.to_s

print content

RubyCocoa のアプリケーションとして作る場合、表示させるのは Text View になる(そうじゃなくてもいいんだろうけど)。そこで、PDF ファイルを読み込んで、そのテキストを Text View に表示させるようにしてみる。基本的なアプリケーションの作り方は、RubyCocoa 入門かこのサイトの基本のページを参照。

AppController のファイルに ib_outlet として textView を追加して、Interface Builder で Text View をウィンドウに配置して、それを textView の outlet と結びつけておく。

上の例の場合は、次のように書いて、Text View に抜き出したテキストを表示する。

@textView.setString(content)

ここまでの例の場合だと、文字列を抜き出しているだけで、文字情報はすべて失われている。文字情報を保持する場合は、少し違った操作をする。単に Ruby スクリプトとして扱わないので、アプリケーションで Open パネルを使ってファイル名を得たことにする。詳しいことは、このサイトの Open パネルのページを参照。

まずは、上で説明したように、PDF の書類から PDFDocument オブジェクトを作る。

pdfDocument = PDFDocument.alloc.initWithURL(NSURL.fileURLWithPath(panel.filename))

次に、selectionForEntireDocument というメソッドで、PDF ファイルのテキスト全体を選択して、attributedString で選択箇所のテキストを NSMutableAttributedString オブジェクトとして得る。

pdfSelection = pdfDocument.selectionForEntireDocument.attributedString

NSMutableAttributedString オブジェクトは、ただの String ではなく、いろいろな文字情報を保持して、しかも編集可能なもので、setString で Text View に書き込めないので、insertText という別のメソッドを使う。ただ、これは、カーソルのある位置にテキストを挿入するので、既にテキストが表示されている場合はそのテキスト内のカーソルがあるところに読み込んだテキストが挿入されてしまう。それで、まず、setString(string) で "" にして Text View を空っぽにする。もしくは setSelectedRange(range) で全部を選択する。

@textView.setString('')

もしくは、

@textView.setSelectedRange([0,@textView.string.length])

それから、attributed string を挿入する。

@textView.insertText(pdfSelection)

これだと、カーソル位置が最後にくるので、表示はテキストの一番最後になってしまう。それでは、見栄えがちょっと、ということで、scrollRangeToVisible(range) という Text View のメソッドを使う。NSRange でカーソルの場所を指定してそこを表示するという形なので、(0,0) で一番先頭に持ってくる。。

@textView.scrollRangeToVisible(NSRange.new(0,0))

これで、フォントや文字情報を保持したまま、Text View に抜き出したテキストが表示されるはず。