Beamerより簡単＆速い！Marp + KaTeXでスマートにスライド作成

# Marp と KaTeX で手軽に数式スライドを作る

## はじめに
プレゼンテーション用のスライドを作成する際、LaTeX の Beamer を使うことが多いと思います。しかし、
1. コンパイルに時間がかかる
2. LaTeX 環境のセットアップが面倒
3. Beamer自体が難しく、なぜかコンパイルが回らない
といった問題があります。

そこでおすすめなのが、Marp + KaTeX の組み合わせです！
Marp は Markdown ベース でスライドを作成できるツールで、KaTeX を使うことで LaTeX の数式 も簡単に扱えます。

この記事では、主に以下の二つの問題に解決法を与えます。
| 問題| 原因 | 解決法 |
|:-:|:-:|:-:|
|`\newcommand` が使えない	|KaTeX にグローバルなコマンド定義の仕組みがない|	`\global\def` を使う   |  
|  HTML タグ内で数式がレンダリングされない	|KaTeX の処理順の関係で HTML 内の数式を認識しない	|引用ブロック (`>`) を使う

**最後にコピペで使えるmarkdownとcssのコードを配置しています。**
GitHubの[レポジトリ](https://github.com/tom1999-303/beamerlike-template)でも公開しています。


## Marp + KaTeX の利点
Marp でスライドを作るメリットは次のとおりです：
1. Markdown で手軽に書ける（Beamerを使うための呪文を理解する必要がない）
2. コンパイルが高速
3. ほとんどの TeX 数式コマンドが使える（一部制約はあるが、基本的な数式は問題なし）
4. CSS でデザインを自由にカスタマイズ可能（Beamer 風のスタイルも実現できる）

Beamer風のスタイルで次のようなスライドが作れます。
![base-1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3600491/29932d2f-2856-4353-8f75-4d39a6d3fafc.png)
![base-2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3600491/4456978a-77c7-4c2f-bb78-3261f3c1ee3a.png)



コードは以下です（ただし、プリアンプルなどは省略）。
~~~ 
/* 省略 */
<!-- _class: title -->
# Marp+KaTeXのすすめ
<br>

**marp太郎**
所属学科
所属大学

---
# Introduction (Marp+KaTeXの定理環境)
<br>

>Theorem
>
>成り立つこと
> $$a^2 + b^2 = c^2$$
> $$\int_{-\infty}^{\infty} e^{-x^2} dx = \sqrt{\pi}$$  

>予想
>
>予想してること
> $$ \dD^b(\Coh(X)) \simeq \mathrm{Fuk}(\hat{X})$$
~~~




# KaTeX の高度な使い方と注意点

Marp + KaTeX は手軽に数式スライドを作成できる便利な組み合わせですが、いくつかの 注意点 があります。特に、次の2つの問題に気をつける必要があります。

1. `\newcommand`が使えない
2. HTML タグ内で数式がレンダリングされない
それぞれの原因と解決策を解説します。

## `\newcommand` が使えない
通常の LaTeX では、\newcommand を使ってカスタムコマンドを定義できます。例えば、

~~~tex
\newcommand{\RR}{\mathbb{R}}
~~~
と書けば、`\RR` で 
```math
\mathbb{R}
```
を簡単に出力できます。

しかし、KaTeX では `\newcommand` がサポートされていません。これは、KaTeX が クライアントサイド（ブラウザ上）で数式をレンダリングするため、グローバルなコマンド定義を保持する仕組みがない からです。

:::note info
**解決策：`\global\def` を使う**
KaTeX では、`\global\def` を使うことでカスタムコマンドを定義できます。
:::

~~~tex
$$
\global\def\RR{\mathbb{R}}
$$
~~~
このようにすれば、\RR を スライド内の他の数式でも利用可能 になります。

## HTML タグ内で数式がレンダリングされない
Marp では、スライドの一部に HTML タグ（`<div>` や `<span>` など）を使うことができます。しかし、KaTeX は HTML タグ内では数式を正しくレンダリングできません。

例えば、以下のように書くと 意図した表示になりません。

~~~markdown
<div>
  $$ E = mc^2 $$
</div>
~~~
HTML タグ内の数式は KaTeX に認識されず、適切に変換されません。



::: note info
**解決策：引用ブロック (>) を使う**
Marp では 引用ブロック（>）の中では KaTeX が正しく動作 するため、以下のように記述することで回避できます。
:::

~~~markdown
> $$
> E = mc^2
> $$
~~~
この方法を使えば、定理環境風のレイアウトにも応用できます。
具体的なcssの設定については次の章で解説します。





# Beamer 風のスライドデザイン

Marp では CSS をカスタマイズすることで、スライドのデザインを自由に変更できます。本章では、LaTeX の Beamer 風のデザインを再現する方法 を紹介します。
本記事では、オリジナルの "beam" テーマをベースに改良を加えています。
元の CSS は GNU GPLv3 ライセンス のもとで公開されているため、改良版も同じ GPLv3 ライセンスで公開しています。

このコードを使うためには、`.vscode/beamer.css`と`.vscode/setting.json`が必要です。
実際のmarkdownのコードは`base.md`にあります。


~~~css:.vscode/beamer.css

/* Modified version of "beam" theme from rnd195/my-marp-themes */
/* Original license: GNU GPLv3 https://github.com/rnd195/my-marp-themes/blob/live/licenses/LICENSE_beam */
/* Modified by @TomoK303 */
/* License of beamer which inspired this theme - GNU GPLv2 https://github.com/rnd195/my-marp-themes/blob/live/licenses/LICENSE_GPLv2 */

@import "default";

:root {
  font-family: "CMU Sans Serif", "Segoe UI", Helvetica, sans-serif;
  --main: #0e1d6d;
  --secondary: #141414;
}

section {
  background-color: #ffffff;
  /* bottom two-coloured bar in base64 svg */
  background-image:
    url(data:image/svg+xml;base64,PD94bWwgdmVyc2lvbj0iMS4wIiBlbmNvZGluZz0iVVRGLTgiPz4KPHN2ZyB3aWR0aD0iMjUwbW0iIGhlaWdodD0iNS4zNTQ2bW0iIHZlcnNpb249IjEuMSIgdmlld0JveD0iMCAwIDI1MCA1LjM1NDYiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyI+CjxnIHRyYW5zZm9ybT0idHJhbnNsYXRlKC0yMC4zNDcgLTkxLjAyOCkiPgo8cmVjdCB4PSIyMC4zNDciIHk9IjkxLjAyOCIgd2lkdGg9IjEyNSIgaGVpZ2h0PSI1LjM1NDYiIGZpbGw9IiMxNDE0MTQiIGZpbGwtcnVsZT0iZXZlbm9kZCIgc3Ryb2tlLXdpZHRoPSIwIi8+CjxwYXRoIGQ9Im0xNDUuMzUgOTMuNzA1di0yLjY3NzNoMTI1djUuMzU0NmgtMTI1eiIgZmlsbD0iIzFmMzhjNSIgc3Ryb2tlLXdpZHRoPSIwIi8+CjwvZz4KPC9zdmc+);
  background-repeat: no-repeat;
  background-position: center bottom;
  background-size: 150% 1em;
  padding: 2em;
}

header {
  font-size: 0.6em;
  /* this text-align is important */
  text-align: right;
  /* I don't like this absolute positioning, but it works */
  position: absolute;
  top: 96.2%;
  width: 100%;
  right: 0;
  left: -51%;
  color: white;
}

footer {
  font-size: 0.6em;
  position: absolute;
  /* this text-align is important */
  text-align: left;
  top: 96.2%;
  width: 100%;
  right: 0;
  left: 50.8%;
  color: white;
}

h1,
h2,
h3,
h4,
h5,
h6 {
  color: #141414;
}

/* only apply to the first occurrence of h1 */
h1:nth-of-type(1) {
  font-family: "CMU Bright", "Segoe UI Semibold";
  color: #ffffff;
  background-color: var(--main);
  border-top: 0.3em solid var(--main);
  padding: 0;
  position: absolute;
  top: 0;
  right: 0;
  width: 100%;
  height: 1.5em;
  text-indent: 0.5em;
}



code {
  background-color: rgba(100, 100, 100, 0.2);
}

mark {
  background-color: #f5db7e;
}

/* formatting page numbers  */
section::after {
  font-size: 0.6em;
  /* https://github.com/yhatt/marp/issues/263 */
  content: attr(data-marpit-pagination) " / " attr(data-marpit-pagination-total);
  position: absolute;
  text-align: right;
  top: 96.2%;
  width: 100%;
  right: 0;
  left: -0.5em;
  color: white;
}

/* inline math was too large wrt text */
.katex {
  font: normal 1.05em KaTeX_Main, "Times New Roman", serif
}

/* the "center" keyword centers the image - may break, careful */
/* https://github.com/marp-team/marpit/issues/141#issuecomment-473204518 */
img[alt~="center"] {
  display: block;
  margin: 0 auto;
}

/* || SECTION CLASS: title */
/* title page - only to be used as for a single slide */
/* <!-- _class: title --> */
section.title>h1 {
  font-family: "CMU Bright", "Segoe UI Semibold";
  color: #ffffff;
  background-color: var(--main);
  border-radius: 25px;
  text-align: center;
  top: 25%;
  left: 0;
  right: 0;
  margin-left: auto;
  margin-right: auto;
  width: 80%;
  padding-bottom: 0.1em;
  height: auto;
}

/* remake this to be positioned with respect to h1 */
section.title>p {
  position: relative;
  text-align: center;
  top: 35px;
}

/* || SECTION CLASS: tinytext */
/* new class that makes p, ul, and blockquote text smaller */
/* might be useful for the References slide, use <!-- _class: tinytext --> */
section.tinytext>p,
section.tinytext>ul,
section.tinytext>blockquote {
  font-size: 0.65em;
}
.center-large {
  text-align: center;
  font-size: 3em;
}


.question {
  border: 2px solid red;
  background-color: #fae0e0;
  font-size: 1.2em;
  /*padding: 1em;*/
  margin: 1em 0;
  padding: 0.3em; 
  border-radius: 5px;
  box-shadow: 2px 2px 5px rgba(0, 0, 0, 0.3);

}

.question-title {
  font-weight: bold;
  margin-bottom: 0.1em;
  color: white;
  background-color: red;
  padding-left: 0.5em;
}

blockquote {
  border: 2px solid #a2d2ff;
  background-color: #e0f7fa;
  margin: 1em 0;
  color:  black;
  padding: 0.3em;                      /* 内側の余白を追加 */
  border-radius: 5px;
  box-shadow: 2px 2px 5px rgba(0, 0, 0, 0.3); /* ドロップシャドウ */
}

blockquote p:first-child {
  font-weight: bold;
  margin-bottom: 0.05em;
  padding-left: 0.5em;
  color: white;
  background-color: var(--main);
}

~~~


~~~json:setting.json
{
    "markdown.marp.themes": [
        ".vscode/beam.css"
    ]
}
~~~

~~~ markdown
---
marp: true
theme: beam
math: katex

paginate: true
footer: "marpのすすめ（marp太郎）"

---
$$
\global\def\aA{\mathcal{A}}
\global\def\bB{\mathcal{B}}
\global\def\cC{\mathcal{C}}
\global\def\dD{\mathcal{D}}
\global\def\eE{\mathcal{E}}
\global\def\fF{\mathcal{F}}

$$

<!-- _class: title -->
# Marp+KaTeXのすすめ


<br>

**marp太郎**
所属学科
所属大学
---
# Introduction (Marp+KaTeXの定理環境)
<br>



>Theorem
>
>成り立つこと
> $$a^2 + b^2 = c^2$$
> $$\int_{-\infty}^{\infty} e^{-x^2} dx = \sqrt{\pi}$$  

>予想
>
>予想してること
> $$ \dD^b(\Coh(X)) \simeq \mathrm{Fuk}(\hat{X})$$
> 
---

<div class = "center-large">
おわり
</div>

~~~