Typst 模板的表单
为你自己的 Typst 函数配一个表单,这样撰写报告的人在可视化模式下看到的是带标签的字段,而不是函数调用语法。
Typst 模板通常自带一些函数:封面页、信息框、签署块。撰写报告的人会调用它们,例如 #info-box(title: "Supply risk", tone: "risk")[...]。如果你维护模板,可以把每个函数的参数描述一次。之后,可视化模式会把对该函数的每次调用显示为一张表单:带标签的字段、用于固定选项的列表、用于“是”或“否”的开关。编辑某个字段只会重写 .typ 文件中的那一个参数,所以报告仍是普通的 Typst 源码,编译方式也和原来一样。
读者会看到什么
标题为“读者会看到什么”的部分单独占几行的调用会变成一张卡片。卡片的标题显示表单的名称,以及(如果你选择了的话)一段简短的摘要,例如信息框的标题。每个参数占一行,有它的标签和一个控件。
句子里的调用,例如 #badge("review"),会变成文字行中的一个行内标签。点击这个标签,会在一个小弹出框中打开同样的字段。
文本字段和标记字段在你按 Enter(多行字段中按 ⌘ Enter 或 Ctrl Enter)或离开该字段时保存。按 Esc 会恢复旧值。列表和开关会立即保存。每一次更改都是一个撤销步骤。
把光标移入某个调用时,会显示它的源码,与可视化模式中的其他元素一样。卡片上的在源码中编辑效果相同。
在哪里声明表单
标题为“在哪里声明表单”的部分有两个位置,格式相同:
- 在包中。 在包的
typst.toml中添加[tool.oleafly]部分。Typst 把[tool.*]部分留给其他工具,所以这个包仍能在各处安装和编译。这对@local包和来自 Typst Universe 的@preview包都适用。 - 在项目中。 对于以普通
.typ文件形式保存在项目内的模板,在项目根目录创建oleafly-forms.toml。每个表单还要用module指出定义该函数的文件。
包中的表单:
[tool.oleafly]schema = 1
[[tool.oleafly.forms]]function = "info-box"label = "Info box"summary = "title"
[[tool.oleafly.forms.fields]] arg = "title" kind = "text" label = "Heading" placeholder = "Short heading" required = true
[[tool.oleafly.forms.fields]] arg = "tone" kind = "choice" label = "Tone" default = "note" options = [{ value = "note", label = "Note" }, { value = "risk", label = "Risk" }, "neutral"]
[[tool.oleafly.forms.fields]] arg = 0 kind = "content" label = "Text"项目中的表单,写在 oleafly-forms.toml 中:
[tool.oleafly]schema = 1
[[tool.oleafly.forms]]module = "template/memo.typ"function = "memo-header"label = "Memo header"fields = [ { arg = "to", kind = "text", label = "To" }, { arg = "subject", kind = "text", label = "Subject" },]schema = 1 是必需的。没有它,或者写了别的数字的文件,会被忽略。
每个 [[tool.oleafly.forms]] 条目有:
| 键 | 是否必需 | 含义 |
|---|---|---|
function | 是 | 函数的名称,一个 Typst 标识符。可以包含连字符。 |
module | 仅在 oleafly-forms.toml 中 | 定义该函数的项目文件,相对于项目根目录,文件夹之间用 / 分隔。 |
label | 否 | 表单在卡片和行内标签上的名称。默认是函数的名称。 |
summary | 否 | 其值显示在名称旁边的参数,写法与字段的 arg 相同。 |
fields | 是 | 一个或多个字段。 |
每个字段有:
| 键 | 是否必需 | 含义 |
|---|---|---|
arg | 是 | 命名参数的名称("title"),或位置参数的数字(0 是第一个)。括号后面的 [...] 块算作位于括号内参数之后的位置参数。 |
kind | 是 | text、content、choice、number 或 toggle。 |
label | 是 | 字段的标签。 |
help | 否 | 字段下方的简短说明。 |
placeholder | 否 | 空字段中的灰色文字。 |
required | 否 | true 会把空字段标记为缺失,并隐藏它的清除按钮。Oleafly 绝不会自己添加这个参数。 |
default | 否 | 参数被省略时你的函数所用的值。它只会显示,绝不会写入。 |
各种类型及其额外的键:
text写入 Typst 字符串。加上multiline = true可得到更大的输入框。content编辑 Typst 标记,并把它写成[...]块。字符串参数仍保持为字符串。choice需要options:一个字符串列表,或者在标签与值不同时使用{ value, label }表。值以字符串形式写入。number接受integer、min、max和step。数字没有单位。toggle写入true或false。
哪些调用会得到表单
标题为“哪些调用会得到表单”的部分Oleafly 会跟随报告自己在文件顶层的 #import 和 #let 行:
#import "@local/acme-report:0.1.0" as acme会让#acme.info-box(...)成为表单。#import "@local/acme-report:0.1.0": info-box, status-badge as badge会让#info-box(...)和#badge(...)成为表单。#import "@local/acme-report:0.1.0": *会让该包为其声明了表单的每个函数都成为表单。#import "template/memo.typ": memo-header会匹配module为template/memo.typ的项目表单。路径从报告自己所在的文件夹读取,以/开头时则从项目根目录读取。
包的版本必须完全一致。文件中靠后位置的同名 #let 会从那一点起替换该表单。通过另一个重新导入该包的文件而到达的调用,保持显示其源码文本。
函数的名称如果与可视化模式已经绘制的 Typst 元素相同,例如 table 或 figure,用裸名称调用时会保持内置的外观。#acme.table(...) 或重命名的导入仍然会得到表单。
以只读方式显示的字段
标题为“以只读方式显示的字段”的部分有些参数无法安全地通过表单编辑。它们所在的行会显示源码和原因,在源码中编辑会跳到源码:
- 在源码中计算得出:值是一个表达式,例如
title: data.title。 - 以其他类型的值书写:例如在表单期望文本的地方写成了数字。
- 不在可选项之内:你的
options没有列出的值。 - 由展开参数设置:带有
..args的调用会传入表单看不到的值,所以每个字段都是只读的。
当某个字段无法添加到它应在的位置时,例如缺失参数之后的位置参数,表单会这样说明,并提供在源码中添加。
定义中的错误
标题为“定义中的错误”的部分在 Oleafly 中打开 oleafly-forms.toml,或打开复制进项目的包的 typst.toml,每个问题都会在它所在的行上显示为一个标记:未知的类型、缺少标签、重复的表单、位于项目之外的 module。有问题的表单会被略去,其他表单继续工作。大于 256 KB 的文件不会被读取。
共享模板
标题为“共享模板”的部分Oleafly 从编译器所用的同样那些文件夹中读取包的表单。没有 @local 包的协作者看到的是普通源码,也不会有错误。要让项目中的每个人都能用到这些表单,请打开Typst 包对话框,开启使用项目文件夹中的包,并选择将包复制到项目。这样,包及其表单就会随项目的 typst-packages 文件夹一起传递(参见 Typst 项目)。