mdBook固有の機能

コード行を非表示にする

mdBookには、行の先頭へ特定の接頭辞を付けて、コード行を非表示にする機能があります。

Rustでは、Rustdocと同様に、行の先頭へ# (#の後に空白)を付けると非表示にできます。この接頭辞は##でエスケープできます。文字列# で始まる行を、そのまま表示したい場合に使います(詳しくはRustdocの文書を参照してください)。

# fn main() {
    let x = 5;
    let y = 6;

    println!("{}", x + y);
# }

次のように表示されます。

fn main() {
    let x = 5;
    let y = 6;

    println!("{}", x + y);
}

コードブロックをタップしたり、マウスを重ねたりすると、非表示の行の表示を切り替える、目のアイコン()が現れます。

既定では、rustと注釈を付けたコード例だけで使えます。ほかの言語では、book.tomlへ言語名と接頭辞の文字を指定し、コード行を非表示にする独自の接頭辞を定義できます。

[output.html.code.hidelines]
python = "~"

指定した接頭辞で始まる行が非表示になります。上のPythonの接頭辞を使うと、次のコードは、

~hidden()
nothidden():
~    hidden()
    ~hidden()
    nothidden()

次のように表示されます。

hidden()
nothidden():
    hidden()
    hidden()
    nothidden()

個々のコードで別の接頭辞を指定して、上書きできます。次の例は、上と同じ結果になります。

```python,hidelines=!!!
!!!hidden()
nothidden():
!!!    hidden()
    !!!hidden()
    nothidden()
```

Rust Playground

Rustのコードブロックには、コードを実行して結果を直下へ表示する、再生ボタン()が自動で付きます。コードをRust Playgroundへ送る仕組みです。

#![allow(unused)]
fn main() {
println!("Hello, World!");
}

main関数がない場合、コードは自動でその中へ包まれます。

コードブロックの再生ボタンを無効にしたい場合は、次のようにnoplaygroundを指定できます。

```rust,noplayground
let mut name = String::new();
std::io::stdin().read_line(&mut name).expect("failed to read line");
println!("Hello {}!", name);
```

本のすべてのコードブロックで再生ボタンを無効にするには、次の設定をbook.tomlへ書けます。

[output.html.playground]
runnable = false

Rustのコードブロック属性

Rustのコードブロックでは、言語名の直後に、カンマ、空白、タブで区切って属性を追加できます。例を示します。

```rust,ignore
# This example won't be tested.
panic!("oops!");
```

これらの属性は、mdbook testでRustの例をテストする際に特に重要です。rustdocの属性と同じ属性を使い、いくつか追加されています。

  • editable — エディターを有効にします。
  • noplayground — 再生ボタンを取り除きますが、テストは行います。
  • mdbook-runnable — 再生ボタンを必ず表示します。テストはせずに、読者が実行できるようにしたい例で、ignore属性と組み合わせるためのものです。
  • ignore — テストを行わず、再生ボタンも表示しません。ただし、Rustの構文としてハイライトします。
  • should_panic — 実行するとpanicを起こすべきコードです。
  • no_run — テスト時にコンパイルしますが、実行しません。再生ボタンも表示しません。
  • compile_fail — コンパイルが失敗するべきコードです。
  • edition2015、edition2018、edition2021、edition2024 — 特定のRustエディションを指定します。本全体へ設定するには、rust.editionを参照してください。

ファイルを取り込む

次の構文で、ファイルを本へ取り込めます。

{{#include file.rs}}

ファイルのパスは、現在のソースファイルからの相対パスで指定します。

mdBookは、取り込んだファイルをMarkdownとして解釈します。includeコマンドは、コードや例を挿入するためによく使われるため、解釈せずにファイルの内容を表示するには、通常、コマンドを```で囲みます。

```
{{#include file.rs}}
```

ファイルの一部を取り込む

例に必要な行など、ファイルの一部だけが必要な場合があります。部分的な取り込みには、4つの方法があります。

{{#include file.rs:2}}
{{#include file.rs::10}}
{{#include file.rs:2:}}
{{#include file.rs:2:10}}

最初のコマンドは、file.rsの2行目だけを取り込みます。2番目は10行目までを取り込み、11行目から末尾までは除きます。3番目は2行目以降を取り込み、1行目を除きます。最後はfile.rsの2〜10行目を取り込みます。

取り込むファイルを変更したときに本が壊れないように、行番号の代わりにアンカーを使って、特定の節を取り込むこともできます。アンカーは、対応する2行の組です。開始行は正規表現ANCHOR:\s*[\w_-]+、終了行はANCHOR_END:\s*[\w_-]+に一致する必要があります。どのような形式のコメント行にも、アンカーを置けます。

取り込むファイルとして、次の例を考えます。

/* ANCHOR: all */

// ANCHOR: component
struct Paddle {
    hello: f32,
}
// ANCHOR_END: component

////////// ANCHOR: system
impl System for MySystem { ... }
////////// ANCHOR_END: system

/* ANCHOR_END: all */

本の中では、次のように書くだけです。

Here is a component:
```rust,no_run,noplayground
{{#include file.rs:component}}
```

Here is a system:
```rust,no_run,noplayground
{{#include file.rs:system}}
```

This is the full file.
```rust,no_run,noplayground
{{#include file.rs:all}}
```

取り込むアンカー内で、アンカーのパターンを含む行は無視されます。

ファイルを取り込み、最初は指定した行だけを表示する

rustdoc_includeヘルパーは、完全な例を含む外部のRustファイルからコードを取り込みます。ただし、includeと同じように行番号やアンカーを指定し、最初はその部分の行だけを表示します。

行番号の範囲やアンカーの間にない行も取り込まれますが、先頭に#を付けます。読者はコードを展開して完全な例を見ることができ、Rustdocはmdbook testの実行時に完全な例を使います。

たとえば、次のRustプログラムを含むfile.rsというファイルを考えます。

fn main() {
    let x = add_one(2);
    assert_eq!(x, 3);
}

fn add_one(num: i32) -> i32 {
    num + 1
}

次の構文で、最初は2行目だけを表示するコードを取り込めます。

To call the `add_one` function, we pass it an `i32` and bind the returned value to `x`:

```rust
{{#rustdoc_include file.rs:2}}
```

手作業でコードを挿入し、#を使って2行目以外を非表示にした場合と、同じ結果になります。

To call the `add_one` function, we pass it an `i32` and bind the returned value to `x`:

```rust
# fn main() {
    let x = add_one(2);
#     assert_eq!(x, 3);
# }
#
# fn add_one(num: i32) -> i32 {
#     num + 1
# }
```

つまり、次のように表示されます(残りのファイルを見るには「展開」アイコンをクリックします)。

fn main() {
    let x = add_one(2);
    assert_eq!(x, 3);
}

fn add_one(num: i32) -> i32 {
    num + 1
}

実行可能なRustファイルを挿入する

次の構文で、実行可能なRustファイルを本へ挿入できます。

{{#playground file.rs}}

Rustファイルのパスは、現在のソースファイルからの相対パスで指定します。

再生ボタンをクリックすると、コードがRust Playgroundへ送られ、コンパイル・実行されます。結果は返送され、コードの直下へ表示されます。

生成したコードの表示例です。

fn main() {
    println!("Hello World!");

    // You can even hide lines! :D
    println!("I am hidden! Expand the code snippet to see me");
}

ファイル名の後に渡した値は、コードブロックの属性として追加されます。たとえば、{{#playground example.rs editable}}は、次のようなコードブロックを生成します。

```rust,editable
# Contents of example.rs here.
```

editable属性は、Rustのコードブロック属性で説明したとおり、エディターを有効にします。

ページの<title>を指定する

章の先頭近くに{{#title ...}}を置くと、目次(サイドバー)の項目とは異なる<title>を指定できます。

{{#title My Title}}

mdBookが提供するHTMLクラス

Rustロゴ

class="left"と"right"

これらのクラスは、インラインHTMLで画像を左右に寄せるために、既定で用意されています。

<img class="right" src="images/rust-logo-blk.svg" alt="The Rust logo">

class="hidden"

hiddenクラスを付けたHTMLタグは表示されません。

<div class="hidden">This will not be seen.</div>

Font Awesomeのアイコン

mdBookには、Font Awesome Freeバージョン6の、MITライセンスのSVGファイルのコピーが含まれます。<i>構文を模倣し、結果をインラインSVGへ変換します。regular、solid、brandsのアイコンだけを含み、lightなどの有料機能は含みません。

たとえば、次のHTML構文に対して、

The result looks like this: <i class="fa-solid fa-print"></i>

次のように表示されます:

利用できるアイコンは、無料のアイコン集合を参照してください。