KaTeXとは、数式をWebページ上で綺麗に表示するためのJavaScriptライブラリである。TeXという文字のレイアウト用のプログラミング言語を模倣したもので、カーンアカデミーによって開発された。

発音は明示されていないが、同じくTeXを元に開発されたLaTeXは"Lah-tech"あるいは"Lay-tech"と発音するそうである。カテック、あるいはケイテックのどちらかで呼びたいところだが、TeXは、ギリシア語風にテフと発音する("ch"を"bach"的に発音する)らしい。もうわからないので、好きなように呼べばいいと思う。

ちなみにカーアンアカデミーは、「誰にでも,どこにでも無料で世界クラスの教育を提供する」ことを使命とし、オンラインで数学をはじめとするさまざまなコンテンツを配信している。素敵である。

WebページにKaTeXをインストールする

KaTeXの最も簡単な導入方法はCDNである。公式サイトでは、以下のようにjsDelivrから読み込む方法がアナウンスされている。

html
<!DOCTYPE html>
<!-- KaTeX requires the use of the HTML5 doctype. Without it, KaTeX may not render properly -->
<html>
  <head>
    <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/katex@0.16.8/dist/katex.min.css" integrity="sha384-GvrOXuhMATgEsSwCs4smul74iXGOixntILdUW9XmUC6+HX0sLNAK3q71HotJqlAn" crossorigin="anonymous">

    <!-- The loading of KaTeX is deferred to speed up page rendering -->
    <script defer src="https://cdn.jsdelivr.net/npm/katex@0.16.8/dist/katex.min.js" integrity="sha384-cpW21h6RZv/phavutF+AuVYrr+dA8xD9zs6FwLpaCct6O9ctzYFfFr4dgmgccOTx" crossorigin="anonymous"></script>

    <!-- To automatically render math in text elements, include the auto-render extension: -->
    <script defer src="https://cdn.jsdelivr.net/npm/katex@0.16.8/dist/contrib/auto-render.min.js" integrity="sha384-+VBxd3r6XgURycqtZ117nYw44OOcIax56Z4dCRWbxyPt0Koah1uHoK0o4+/RRE05" crossorigin="anonymous"
        onload="renderMathInElement(document.body);"></script>
  </head>
  <body>\[ c = \pm\sqrt{a^2 + b^2} \]</body>
</html>

上記のHTMLでは、以下の3つのファイルが読み込まれている。

ファイル名 概要
auto-render.min.js 与えられた要素から、所定の区切り文字に囲まれた数式を自動的に検出し、レンダリング担当(この場合はkatex.min.js内のAPI)に渡すためのJavaScript。
katex.min.js 与えられた文字列から数式を解析し、マークアップするためのJavaScript。
katex.min.css KaTeXによってマークアップされた数式をスタイリングするためのCSS。

ちなみにkatex.min.jsを読み込むと、katexオブジェクトがグローバルオブジェクトに追加される。これを用いて任意の文字列をマークアップすることもできる。

html
<!DOCTYPE html>
<html>
  <head>
    <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/katex@0.16.8/dist/katex.min.css" integrity="sha384-GvrOXuhMATgEsSwCs4smul74iXGOixntILdUW9XmUC6+HX0sLNAK3q71HotJqlAn" crossorigin="anonymous">
    <script defer src="https://cdn.jsdelivr.net/npm/katex@0.16.8/dist/katex.min.js" integrity="sha384-cpW21h6RZv/phavutF+AuVYrr+dA8xD9zs6FwLpaCct6O9ctzYFfFr4dgmgccOTx" crossorigin="anonymous"></script>
  </head>
  <body>
    <script>
    addEventListener("DOMContentLoaded", (event) => {
      // String.rawはエスケープせずに文字列を返すメソッド
      const expr = String.raw`c = \pm\sqrt{a^2 + b^2}`;
      katex.render(expr, document.body, {
        displayMode:true,
        throwOnError: false
      });
    });
    </script>
  </body>
</html>

katex.min.jsは277KBある。ページの表示速度を上げるためにも、defer属性を使って遅延ロードが推奨される。そのため別のJavaScriptからkatexオブジェクトを利用する場合、DOMContentLoadedイベントの完了を待つ必要がある。

また、katex.render(tex, element, options)メソッドにTeX記法(\コマンド名{引数}みたいな記法)で書かれた文字列を渡し、数式をレンダリングしている。

KaTeXでは、このほかに渡したTeX記法で書かれた文字列をマークアップして返すkatex.renderToString(tex, options)メソッドがある。

KaTeXで、開発者に使ってもらう前提で用意されているAPIはこの2つだけである。

APIに渡すオプションについて

render()メソッドとrenderToString()メソッドの最後の引数に渡すオプションオブジェクトには、以下のような項目を設定できる。

キー名 概要
displayMode 真偽値。trueだとディスプレイモード、falseだとインラインモードが適用される。デフォルトはfalse
output 文字列。出力するマークアップ言語を決める。htmlmathmlhtmlAndMathmlのいずれか。デフォルトはhtmlAndMathml
leqno 真偽値。leqnoは"Left Equation Numbers"の略。ディスプレイモードで、\tag(数式につけるラベルや番号)を左側にレンダリングする。
fleqn 真偽値。fleqnは"Flush Left Equations"の略。ディスプレイモードで左に2emのマージンがある左揃えになる。
throwOnError 真偽値。サポートされていないコマンドや無効なLaTeXを受け取った場合、ParseErrorを投げる。デフォルトはtruefalseにすると、エラーがerrorColorで指定された色でレンダリングされる。
errorColor 文字列。throwOnErrorfalseの場合に表示されるエラーメッセージの色。#xxxまたは#xxxxxx形式で指定する。デフォルトは#cc0000
macros オブジェクト。カスタムマクロのコレクション。オブジェクトのキーは新しいコマンド名、値はマクロを展開した文字列。
minRuleThickness 数値。分数の線や平方根の上部の線など、数学記号の線の太さをem単位で指定。デフォルトは0.04
colorIsTextColor 真偽値。文字色の指定を\colorコマンドで行うかスイッチで行うか。コマンドにしたいならtrueを指定。
maxSize 数値。ユーザが指定できる文字の最大値をem単位で指定。デフォルトはInfinity。ユーザは要素やスペースを任意に大きくできる。
maxExpand 数値。マクロを展開できる上限の回数。デフォルトは1000
strict 真偽値または文字列。falseまたは"ignore"で、LaTeXにない書式を許可する。trueまたは"error"だとエラーを投げる。デフォルトは"warn"で、console.warnでエラーを出力する。
trust 真偽値または関数。デフォルトはfalse。リスクのあるコマンドは、errorColorでレンダリングする。trueを指定した場合、すべてを許可する。また、真偽値を返す関数を渡すと、実行するコマンドを制御できる。その関数が受け取る引数は、コマンドとその引数を格納した変数である。例えば以下のように指定する:{trust: (context) => context.protocol === 'http'}
globalGroup 真偽値。\def\newcommandで定義したKaTeXコードをグローバルグループで実行する。普通、KaTeXで定義したコードは\begin{}$$の中のローカルスコープでしか使えない。デフォルトはfalse

node_modulesにKaTeXをインストールする

JavaScirptファイルにKaTeXを読み込みたいときは、以下の手順で普通にパッケージをインストールすれば良い。

bash
npm i katex

あとはkatexオブジェクトをインポートするだけである。

js
import katex from "katex";

あるいは

js
const katex = require("katex");

ここから先述のkatex.render(tex, element, options)メソッドとkatex.renderToString(tex, options)メソッドを使って必要な処理を行うのが、基本的な使い方である。

KaTeXとTeX/LaTeXの違い

TeXは、ドナルド・アーヴィン・クヌース博士によって、文書(特に数学分野の文書)の組版を意図して開発されたプログラミング言語である。

LaTeXは、TeXのアルゴリズムを用いつつ、それをさらに使いやすく抽象化した。ざっくり言えばHTMLみたいなマークアップ言語に近づけた。

HTMLはタグでマークアップするが、TeX/LaTeXではコマンドと呼ばれる\コマンド名{引数名}のような形でレイアウトを指示する。

TeX/LaTeXは、数学文書以外の組版もサポートしている。そのため、数式のある箇所を明示するための区切り文字が用意されている。この区切り文字には、文中で使う数式(=インライン数式)と、ブロックとして文章とは独立して使う数式(ディスプレイ数式)の2種類がある。

また、インライン数式には2種類、ディスプレイ数式には3種類の書き方がある。

インライン数式 ディスプレイ数式
$…$ $$…$$
\[…\] \(…\)
\begin…\end

TeX/LaTeXは文書のレイアウトを幅広く扱うのに対し、KaTeXは数学記号のみに特化している。

また、TeX/LaTeXは独自にコンパイラを持っており、PDFや中間ファイルを出力できる。KaTeXはHTML中のテキストを読み込み、インタプリタによってHTMLでマークアップしたテキストデータを出力する(したがってスタイリングのためのCSSが必須である)。

KaTeXでHTMLの中に埋め込まれた数式を処理するには、スクリプトを書いて数式を取り出し、katex.render(tex, element, options)メソッドとkatex.renderToString(tex, options)メソッドなどを使う。

WebページにKaTeXをインストールするサンプルで使ったauto-render.min.jsは、この数式を取り出す部分を担当するAuto-renderという拡張機能である。

拡張機能 Auto-renderについて

Auto-renderは、katexパッケージには含まれないが、公式の拡張機能である。

この拡張機能はrenderMathInElement(element, options)という関数を1つだけ公開している。elementは、数式が含まれている要素のDOMオブジェクトである。関数は渡されたDOMのテキストノードを再帰的に検索し、数式をレンダリングする。

optionsは、以下のような設定項目を持つオブジェクトである。

キー名 概要
delimiters オブジェクト。leftに開始の区切り文字、rightに終了の区切り文字、displayにディスプレイモードか数式モードかを真偽値で指定する。
ignoredTags 再帰時に無視するHTMLタグの配列。デフォルトでは以下の値が設定されている:["script", "noscript", "style", "textarea", "pre", "code", "option"]
ignoredClassess 再帰時に無視するクラス名の配列。デフォルト値はなし。
errorCallback レンダリング中にエラーが発生した際に、メッセージとエラースタックを返すコールバック。デフォルトではconsole.error
preProcess レンダリング前に数式を処理するためのコールバック。(math: string) => stringのように、最終的に文字列を返す形で指定。

ちなみにデフォルトの区切り文字は以下のように設定されている。

js
[
  { left: "$$", right: "$$", display: true },
  { left: "\\(", right: "\\)", display: false },
  { left: "\\begin{equation}", right: "\\end{equation}", display: true },
  { left: "\\begin{align}", right: "\\end{align}", display: true },
  { left: "\\begin{alignat}", right: "\\end{alignat}", display: true },
  { left: "\\begin{gather}", right: "\\end{gather}", display: true },
  { left: "\\begin{CD}", right: "\\end{CD}", display: true },
  { left: "\\[", right: "\\]", display: true },
];

TeX/LaTeXでサポートされているインライン数式の区切り文字$...$が、デフォルトではサポートされていない点に注意が必要である。

プロパーなKaTeXが数式のレイアウトに特化しているぶん、Auto-renderのほかにも拡張機能やサードパーティライブラリはたくさん存在する。必要に応じて検索すると良い。

KaTeXでサポートされている数式表現

長くなってしまったし、ここからさらに長くなりそうなのでKaTeXがサポートする数式は別のページでまとめることにする。

参考資料