マクロツイーター

はてダから移行した記事の表示が崩れてますが、そのうちに直せればいいのに(えっ)

TeX せずに Lua する LuaTeX の話(1)

LuaTeX は「Lua できる TeX エンジン」でありその入力は普通は TeX 文書である。しかし、実は LuaTeX は Lua インタプリタとしても使用できる。

LuaTeX で Lua(だけ)してみる

例えば、次のような Lua ソースファイルを用意する。

[hello.lua]
print("Hello Lua world!")

LuaTeX がインストールされた環境で、この hello.lua があるディレクトリにおいて、次のコマンドを実行する。

[コマンド]
texlua hello.lua

すると次の出力が得られる。何の変わったところもなく、普通に Lua プログラムが実行されていることが判る。

[出力]
Hello Lua world!

この「texlua」は LuaTeX を Lua インタプリタとして実行する場合のコマンド名である。*1この名前で呼び出された場合は、最初の引数のファイル名を TeX 文書でなく Lua スクリプトのファイルだと解釈する。

※ただし実は、最初の引数が末尾に「.lua」をもつ場合は、コマンド名に関わらず Lua インタプリタのモードで起動する。だから先の例は「luatex hello.lua」でも「lualatex hello.lua」でも同じ結果になる。

※この記事では、「Lua インタプリタモードの LuaTeX」のことを「texlua」と呼ぶことにする。

texlua でどこまで Lua できるか

基本的に、標準の Lua の機能は全て使える(若干拡張されている部分がある)。コマンドラインの引数の扱いも、普通のスタンドアロンLua インタプリタと同じである。

[hello2.lua]
print("Hello, "..(arg[1] or "friend").."!")
[コマンド]
texlua hello2.lua comedian
[出力]
Hello, comedian!

texlua では、標準のライブラリの他にも、以下のライブラリを組込でもっている。

  • unicode (slnunicode)
  • zip (LuaZip)
  • lfs (LuaFileSystem)
  • lpeg (LPeg)
  • zlib (lzlib)
  • md5
  • socket (LuaSocket)

これらは普通に require() で読み込むことができる。*2

lfs = require "lfs"

※現状では起動時に既に読み込まれた(グローバル変数 lfs が最初からある)状態になっているが、この仕様は将来廃止予定である。

通常の Lua インタプリタと同様に、追加の外部ライブラリを読み込むこともできるが、これには注意すべき点がある(今は詳細は省略する)。

texlua 特有のライブラリ

LuaTeX は組版ソフトであるので、それに関わる独自のライブラリも持っている。その多くは「TeX が行う組版を制御するためのもの」であって、texlua としては使用できない。しかし一部のライブラリは“TeX の機能”とは無関係に動作するもので、これらは texlua でも利用できる。((これらのライブラリも require() で読み込んで使用する。現在は「最初から読み込まれている」が、この仕様は廃止予定である。))これらはスタンドアロンのライブラリとしては(まだ)提供されていないので、LuaTeX でしか使うことができないものである。

  • epdf : PDF を操作する。poppler の Lua ラッパーである。
  • fontloader : OpenType 等のフォントの情報を読み出す。FontForge のコードに基づく。

epdf の使用例として、PDF のページ数を調べるプログラムを示す。*3

[pagecount.lua]
epdf = require "epdf"
local num = epdf.open(arg[1]):getNumPages()
print("This document has "..num.." page(s).")
[実行例](luatexref-t.pdf は LuaTeX(v0.80.0)のマニュアル)
texlua pagecount.lua luatexref-t.pdf
[出力]
This document has 210 page(s).

*1:従って、UNIX 的環境では texlua は luatex 実行ファイルへのシンボリックリンクになっている。これは lualatex が luatex のシンボリックリンクであるのと同様である。

*2:もちろん、ローカル変数に読み込むこともできる。

*3:もちろん実用にするにはエラーチェックなどを入れる必要がある。