forked from jbirnick/typst-great-theorems
-
Notifications
You must be signed in to change notification settings - Fork 0
/
lib.typ
140 lines (133 loc) · 4.27 KB
/
lib.typ
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
#let mathblock(
blocktitle: none,
counter: none,
numbering: "1.1",
formatter: (blocktitle, number: none, title: none, body) => [
*#blocktitle#if number != none [ #number].*#if title != none [ (#title)]
#body
// NOTE: Custom suffix here
],
..global_block_args,
) = {
// wrap native counter
if counter != none and type(counter) != dictionary {
counter = (
step: (..args) => {
counter.step(..args)
},
get: (..args) => {
counter.get(..args)
},
at: (..args) => {
counter.at(..args)
},
display: (..args) => {
counter.display(..args)
},
)
}
// return the environment for the user
if counter != none {
return (title: none, numbering: numbering, formatter: formatter, number: auto, ..local_block_args, body) => {
figure(kind: "great-theorem-counted", supplement: blocktitle, outlined: false)[#block(
width: 100%,
..global_block_args.named(),
..local_block_args.named(),
)[
#if number == auto [
// step and counter
#(counter.step)()
#{
number = context (counter.display)(numbering)
}
// store counter so reference can get counter value
// NOTE: alternatively could store result of counter.get(), but then it would take one more layout iteration
#metadata(loc => {
std.numbering(numbering, ..((counter.at)(loc)))
})
#label("great-theorems:numberfunc")
] else [
// store manual number for reference
#metadata(loc => number)
#label("great-theorems:numberfunc")
]
// show content
#formatter(blocktitle, number: number, title: title, body)
]]
}
} else {
return (title: none, numbering: numbering, formatter: formatter, ..local_block_args, body) => {
figure(kind: "great-theorem-uncounted", supplement: blocktitle, outlined: false)[#block(
width: 100%,
..global_block_args.named(),
..local_block_args.named(),
)[
// show content
#formatter(blocktitle, number: none, title: title, body)
]]
}
}
}
#let proofblock(
blocktitle: "Proof",
prefix: text(style: "oblique", [Proof.]),
prefix_with_of: of => text(style: "oblique", [Proof of #of.]),
suffix: [#h(1fr) $square$],
bodyfmt: body => body,
..global_block_args,
) = {
// return the environment for the user
return (
of: none,
prefix: prefix,
prefix_with_of: prefix_with_of,
suffix: suffix,
bodyfmt: bodyfmt,
..local_block_args,
body,
) => {
if type(of) == label {
of = ref(of)
}
figure(kind: "great-theorem-uncounted", supplement: blocktitle, outlined: false)[#block(
width: 100%,
..global_block_args.named(),
..local_block_args.named(),
)[
// show content
#if of != none [#prefix_with_of(of)] else [#prefix]
#bodyfmt(body)
#suffix
]]
}
}
#let great-theorems-init(body) = {
show figure.where(kind: "great-theorem-counted"): set align(start)
show figure.where(kind: "great-theorem-counted"): set block(breakable: true)
show figure.where(kind: "great-theorem-counted"): fig => fig.body
show figure.where(kind: "great-theorem-uncounted"): set align(start)
show figure.where(kind: "great-theorem-uncounted"): set block(breakable: true)
show figure.where(kind: "great-theorem-uncounted"): fig => fig.body
show ref: it => {
if it.element != none and it.element.func() == figure and it.element.kind == "great-theorem-counted" {
let supplement = if it.citation.supplement != none {
it.citation.supplement
} else {
it.element.supplement
}
let data = query(selector(label("great-theorems:numberfunc")).after(it.target)).first()
let numberfunc = data.value
link(it.target, [#supplement #numberfunc(data.location())])
} else if it.element != none and it.element.func() == figure and it.element.kind == "great-theorem-uncounted" {
let supplement = if it.citation.supplement != none {
it.citation.supplement
} else {
it.element.supplement
}
link(it.target, [#supplement])
} else {
it
}
}
body
}