Closed34

連番を振る remark プラグイン

hankei6kmhankei6km

カウンターと定義・参照

以下のような場合を考える。

詳しくは「図 1」を参照してください。


![ここに図 1 があるとする](/images/slug/fig1.png)
*図 1*


![ここに図 2 があるとする](/images/slug/fig2.png)
*図 2*


「図 2」を「図 1」と比較すると。
hankei6kmhankei6km

以下のような記述はどうか?

  • :num[value-name]{define} - 変数の定義と参照、初期値は define が使われた回数
  • :num[value-name] - 変数の参照、定義の前に使ってもよい
詳しくは「:num[array-some]」を参照してください。


![ここに図 1 があるとする](/images/slug/fig1.png)
*図 :num[array-some]{define}*


![ここに図 2 があるとする](/images/slug/fig2.png)
*図 :num[array-every]{define}*


「図 :num[array-every]」を「図 :num[array-some]」と比較すると。

hankei6kmhankei6km

毎回変数名を考えるのも大変。

単純なカウンターとして以下の記述は?

  • :num[value-name]{reset} - 変数の定義(参照はしない = tree から削除)、初期値は 0
  • :num[value-name]{up} - 変数の値をカウントアップして参照
:num[fig](reset}

![ここに図 1 があるとする](/images/slug/fig1.png)
*図 :num[fig]{up}*


![ここに図 2 があるとする](/images/slug/fig2.png)
*図 :num[fig]{up}*

hankei6kmhankei6km

変数の値が動的に変更されると以下の「定義の前に使ってもよい」をどう扱うかが問題になる。

  • :num[value-name] - 変数の参照、定義の前に使ってもよい

最終的に確定した値を使うでもよいのだが、ちょっとわかりにくいか?

:num[fig](reset}

![ここに図 1 があるとする](/images/slug/fig1.png)
*図 :num[fig]{up}*


![ここに図 2 があるとする](/images/slug/fig2.png)
*図 :num[fig]{up}*

「図 :num[fig]」を参照してください。   <- これは「図 3」になる。


![ここに図 3 があるとする](/images/slug/fig3.png)
*図 :num[fig]{up}*
hankei6kmhankei6km

どちらの記述に軸足を置くか(よく使うのはどちらか)による。

単純なカウンター方式をよく使うのならば定義前の参照は許可せずに :num[value-name]{lazy} を使うとスッキリしそうだが、これも最終的な値になるのでわかりくいか。

hankei6kmhankei6km

ここまで書いておいてなんだが構文的にラベル(コンテンツ)を変数名にしてもよいのか?

:num{name="fig"} が正しそうだが記述が煩雑かな。

その代わりに :num[図. ${fig}]{name="fig"} 的なこともできそうだが。
それはそれで処理を作るのが大変そう。

hankei6kmhankei6km

簡単に試作してみた。

  • ラベル(コンテンツ)は使わない
  • value-namename 属性で設定
  • カウント中の値を参照する場合は :num{value="fig" look} のようにする

という感じに落ち着きそう。

hankei6kmhankei6km

実際に入力してみた感じでは極端にやりにくいということはなかったが、「ここはdefine だっけ?」と考え込んでしまうこともあった。

あと、存在しない変数を指定した場合はエラーメッセージを出した方がよいのか?

hankei6kmhankei6km

エラーメッセージを Markdown へ挿入するようにした。

存在しない変数を指定して "ReferenceError" が表示されているスクリーンショット
エラーメッセージの表示

スクリプトに組み込んで動かした場合、remark-cli もしくは textlint のエラーにもしたくなる(ターミナル上にもメッセージを表示させたい)。

この辺は後で対応かな。

hankei6kmhankei6km

しばらく試してみた結果。

  • 参照と定義の場合
    • 章などで連番(define のカウンター)をリセットしたくなる
    • 図と表などで連番の系統をわけたくなる
  • カウンターの場合
    • 章などでカウンターをリセットしたくなる
hankei6kmhankei6km

対応としては以下のような感じか。

define をリセットさせる定義の案。以下のように記述すると headingdepth:2 のノードでリセットする。

:::num{reset}
## :num
:::

連番の系統は変数名を . で区切る(1階層のみ)。

:num{name="fig.some" define}
:num{name="tbl.area" define}

カウンターをリセットさせる定義の案。define とほぼ同じ。変数chapter を定義し headingdepth:2 のノードでリセットする。

:::num{reset}
## :num{name="chapter"}
:::
hankei6kmhankei6km

「定義と参照」と「カウンター」が混在しているのは不自然になってきた気がする。

プラグインをわけるかも。

hankei6kmhankei6km

define のカウンターはクラスを作ってリセットなどの制御をできるようにした。

hankei6kmhankei6km

カウンターは自動カウントを付けるかも。

:::num{increment}
## :num{name="chapter"}
:::
hankei6kmhankei6km

変数を参照するときに記述が長い。

name 属性ではなく id 属性にするとショートカットが使える。

https://github.com/micromark/micromark-extension-directive#syntax

Shortcuts are available for id= ({#readme} for {id=readme}) and
class ({.big} for {class=big}).

今回の場合だとこうなる。

  1. :num{name="foo"} これが
  2. :num{#foo} こうなる

記述は短縮できてよいのだが、参照する側(n 個)にも同一 id が振られるのが違和感ある。

定義と参照で記述を非対称にすると違和感減るか?

  • :num{#foo define} - 定義は属性として id を指定
  • :num[#foo] または :num[foo] - 参照はラベルの中から foo を参照
hankei6kmhankei6km

変数の定義(reset のブロック)を毎回記述するのは非効率。

使いたいのは大体同じ。

:::num{reset}
# :num
## :num
:::

:::cnt{reset}
:cnt{name="chapter"}
:cnt{name="fig"}
:cnt{name="chart"}
:cnt{name="tbl"}
:::

:::cnt{increment}
# :cnt{name="chapter"}
## :cnt{name="chapter"}
:::
hankei6kmhankei6km

テンプレート設定的なもの指定できるようにしたい。

  1. ファイルを用意しておいて cat で対象の .md ファイルに連結してしまう
    プラグイン側の対応は必要ないが cat で連結できるタイミングがあるとも限らない
  2. プラグインのオプションでマークダウンの文字列をわたす
    わたされた文字列を別途パースし変数の定義など更新する必要がある
  3. プラグインのオプションで普通に指定する
    リセットの設定などは指定する項目が多い(マークダウンで書いていたものをオブジェクトで表現することになる)

あとで考える。

hankei6kmhankei6km

カウンターの機能はやはりマージした。

変数名の指定はid を使うようにした。

  • カウンターの定義 - :num{#var reset}
  • 割り当ての定義 - :num{#var}
  • 参照するとき - :num[var]

定義時の define をなくしたので少し簡潔になった。

テンプレートは options で渡すようにした(連結用の.md を外部に持つのは面倒)。

hankei6kmhankei6km
実行準備ができた状態です(図 :num[sec]-:num[fig.ready])。

以下のようになります(図 :num[sec]-:num[fig.result])。

のように毎回 "図 :num[sec]-" を記述するのは手間がかかりすぎる。

以下のような書式指定機能が欲しくなる。

:::num{format assign}
:num[図 :nnum[sec]-:num]{series=fig}
:::
hankei6kmhankei6km

書式機能もつけてみた。

:::num{format assign}
:num[図 :num[sec]-:num]{series=fig}
:num[写真 :num[sec]-:num]{series=photo}
:num[グラフ :num[sec]-:num]{series=chart}
:num[グラフ :num[sec]-:num]{series=grapgh}
:num[図式 :num[sec]-:num]{series=diagram}
:num[フロー :num[sec]-:num]{series=flow}
:num[表 :num[sec]-:num]{series=tbl}
:::

テンプレートなどで上記のように記述しておくと :num[fig-result]図 1-1 のようになる。

以下のような感じにできたので、とりあえずはこの辺までかな。

remark-numers で書式ありの連番が振られるように編集しているスクリーンショット
編集

remark-numers で書式ありの連番が振られた状態のプレビューを表示しているスクリーンショット
プレビュー

hankei6kmhankei6km

アコーディオンの記述 :::details タイトルremark-directive\:::details タイトル にエスケープされる。

タイトル 部分が :::name[label]{attributes} の構文とあわないことから通常のテキストとして処理されるために発生している。
(:::messageContainerDirective として処理される)

これは対応が難しい。

暫定的に sed -e 's/^\\:::/:::/' で行頭の \::: を置き換えで対応かな。

hankei6kmhankei6km

定義と参照で異なる書式。表のラベル(キャプション)風な表示で使えそうかなと。
この辺は CSS が使える環境ならそちらに任せるかな?

:num[▼ 表 :num[sec]-:num]{series=tbl bind=define}
:num[表 :num[sec]-:num]{series=tbl bind=refer}
hankei6kmhankei6km

複数の変数をまとめて参照する機能と書式。
(図 4-2、図 4-3) という表示はちょっと長いので対応したい。

書式の定義

:num[図 :num[sec]-:num]{series=fig join=","}

参照時の記述では , 区切りで複数の変数を指定。

結果は以下の通り(:num[fig-foo,fig-bar])

変換結果。

結果は以下の通り(図 4-2,3)
hankei6kmhankei6km

オートリセットなどのトリガーを式で指定。
とくに困っているわけではないのだが、現行の記述だと柔軟性がないので。

案としては以下のような感じ。

  • 式(jsonpathが利用できないか考えている)をトリガーとしてわたす
  • 式は unist-util-visit-parents から渡される parents + node の配列とマッチするかを検証
  • マッチしたらリセット処理発動
hankei6kmhankei6km

カウンターの初期値を外部から挿入。
これも現状ではとくに困っていないのだが、Zenn 本のように章でファイルがわかれている場合用。

以下のようにすると環境変数などから値を設定など。

# 〇〇について

:num{#chapter reset="$CHAPTER"}
hankei6kmhankei6km

という感じでいまのところこのは 4 つかな。

  • 定義と参照で異なる書式
  • 複数の変数をまとめて参照する機能と書式
  • オートリセットなどのトリガーを式で指定
  • カウンターの初期値を外部から挿入

とりあえず、ここでクローズ。

このスクラップは2022/01/11にクローズされました