diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/LICENSE b/packages/preview/unofficial-tyut-thesis/0.2.2/LICENSE new file mode 100644 index 0000000000..1be93cc396 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/LICENSE @@ -0,0 +1,21 @@ +MIT License + +Copyright (c) 2025 pdcxs + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +SOFTWARE. diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/README.md b/packages/preview/unofficial-tyut-thesis/0.2.2/README.md new file mode 100644 index 0000000000..13d5efd6c5 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/README.md @@ -0,0 +1,9 @@ +# unofficial-tyut-thesis + +非官方太原理工大学本科毕业论文 typst 模板 + +本项目在 [南京大学学位论文 modern-nju-thesis](https://github.com/nju-lug/modern-nju-thesis) 的基础上进行了修改,在此表示感谢。 + +只适用于本科生,研究生与博士生请勿使用。 + +如果需要在在线版APP中使用此模板,需要将 `fonts` 目录中的所有字体上传至项目目录中。 \ No newline at end of file diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/assets/tyut-logo.jpg b/packages/preview/unofficial-tyut-thesis/0.2.2/assets/tyut-logo.jpg new file mode 100644 index 0000000000..bac6beaa30 Binary files /dev/null and b/packages/preview/unofficial-tyut-thesis/0.2.2/assets/tyut-logo.jpg differ diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/appendix.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/appendix.typ new file mode 100644 index 0000000000..d6e9db3148 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/appendix.typ @@ -0,0 +1,31 @@ +#import "@preview/i-figured:0.2.4" +#import "@preview/numbly:0.1.0": numbly + +// 后记,重置 heading 计数器 +#let appendix( + numbering: numbly( + "附录{1:A}. ", + "{1:A}.{2} ", + "{1:A}.{2}.{3} ", + "{1:A}.{2}.{3}.{4} ", + "{1:A}.{2}.{3}.{4}.{5} ", + "{1:A}.{2}.{3}.{4}.{5}.{6} ", + ), + // figure 计数 + show-figure: i-figured.show-figure.with(numbering: "A-1"), + // equation 计数 + show-equation: i-figured.show-equation.with(numbering: "(A-1)"), + // 重置计数 + reset-counter: true, + it, +) = { + set heading(numbering: numbering) + if reset-counter { + counter(heading).update(0) + } + // 设置 figure 的编号 + show figure: show-figure + // 设置 equation 的编号 + show math.equation.where(block: true): show-equation + it +} \ No newline at end of file diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/doc.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/doc.typ new file mode 100644 index 0000000000..be6f2245dd --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/doc.typ @@ -0,0 +1,24 @@ +#let doc( + info: (:), + fallback: false, + lang: "zh", + margin: ( + top: 3.3cm, + bottom: 2.3cm, + left: 2.8cm, + right: 2.3cm, + ), + it, +) = { + if type(info.title) == str { + info.title = info.title.split("\n") + } + + set text(fallback: fallback, lang: lang) + set page(margin: margin) + set document( + title: (("",) + info.title).sum(), + author: info.author, + ) + it +} diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/glossary.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/glossary.typ new file mode 100644 index 0000000000..bf4c22ca0d --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/glossary.typ @@ -0,0 +1,34 @@ +#let glossary_entries = state("glossary_entries", (:)) + +#let make-glossary-table(gls) = { + for item in gls { + glossary_entries.update(tbl => { + tbl.insert(item.key, (short: item.short, long: item.long, appeared: false, description: item.description)) + tbl + }) + } +} + +#let gloss(key) = context { + let itm = glossary_entries + .get() + .at(key, default: ( + appeared: false, + short: [*???*], + long: [*???*], + description: text(fill: red)[*没有找到 #key 对应的术语*], + )) + if itm.appeared { + [#itm.short] + } else { + glossary_entries.update(tbl => { + tbl.insert(key, itm + (appeared: true)) + tbl + }) + if itm.description != "" { + [#itm.description (#itm.long, #itm.short) ] + } else { + [#itm.long (#itm.short) ] + } + } +} diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/mainmatter.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/mainmatter.typ new file mode 100644 index 0000000000..df38071831 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/mainmatter.typ @@ -0,0 +1,148 @@ +#import "@preview/numbly:0.1.0": numbly +#import "@preview/pointless-size:0.1.2": zh +#import "@preview/i-figured:0.2.4" +#import "@preview/cuti:0.4.0": show-cn-fakebold +#import "@preview/itemize:0.2.0" as el + +#let mainmatter( + twoside: false, + leading: 1.5 * 15.6pt - 0.7em, + spacing: 1.5 * 15.6pt - 0.7em, + font: "SimSun", + justify: true, + text-args: auto, + heading-font: auto, + first-line-indent: (amount: 2em, all: true), + mono-font: ("Courier New", "LXGW WenKai Mono GB"), + numbering: numbly( + "{1}. ", + "{1}.{2} ", + "{1}.{2}.{3} ", + "{1}.{2}.{3}.{4} ", + "{1}.{2}.{3}.{4}.{5} ", + "{1}.{2}.{3}.{4}.{5}.{6} ", + ), + heading-weight: ("regular",), + heading-above: (2 * 15.6pt - 0.7em, 1.5 * 15.6pt - 0.4em), + heading-below: (2 * 15.6pt - 0.7em, 1.5 * 15.6pt - 0.7em), + heading-pagebreak: (true, false), + heading-size: (zh(-3), zh(4), zh(-4)), + heading-align: (center, auto), + show-figure: i-figured.show-figure, + show-equation: i-figured.show-equation, + caption-style: none, + caption-size: zh(5), + separator: " ", + ..args, + it, +) = { + // 辅助函数 + let array-at(arr, pos) = { + arr.at(calc.min(pos, arr.len()) - 1) + } + let unpairs(pairs) = { + let dict = (:) + for pair in pairs { + dict.insert(..pair) + } + dict + } + + let heading-text-args-lists = args + .named() + .pairs() + .filter(pair => pair.at(0).starts-with("heading-")) + .map(pair => ( + pair.at(0).slice("heading-".len()), + pair.at(1), + )) + + // 页码设置 + set page(numbering: (..nums) => text(size: zh(-5), [#nums.at(0)])) + counter(page).update(1) + + // 字体 + if text-args == auto { + text-args = (font: ("Times New Roman", font), size: zh(-4)) + } + if heading-font == auto { + heading-font = (("Times New Roman", "SimHei"),) + } + + // 标题设置 + set heading(numbering: numbering) + show heading: it => { + set text( + font: array-at(heading-font, it.level), + size: array-at(heading-size, it.level), + bottom-edge: "descender", + weight: array-at(heading-weight, it.level), + ..unpairs(heading-text-args-lists.map(pair => (pair.at(0), array-at(pair.at(1), it.level)))), + ) + set block( + above: array-at(heading-above, it.level), + below: array-at(heading-below, it.level), + ) + it + } + // 章节标题居中并自动换页 + show heading: it => { + if array-at(heading-pagebreak, it.level) { + pagebreak(weak: true) + } + if array-at(heading-align, it.level) != auto { + set align(array-at(heading-align, it.level)) + it + } else { + it + } + } + + // 正文样式 + show: show-cn-fakebold + set text(..text-args) + set par( + leading: leading, + justify: justify, + first-line-indent: first-line-indent, + spacing: spacing, + ) + show raw: set text(font: mono-font) + show raw.where(block: true): set par(leading: 0.55em) + + // 编号对齐 + show: el.default-enum-list + + // 脚注样式 + show footnote.entry: set text(font: ("Times New Roman", font), size: zh(5)) + + // figure 编号 + show heading: i-figured.reset-counters + show heading: i-figured.reset-counters.with(extra-kinds: ("algo",)) + show figure: show-figure.with(extra-prefixes: (algo: "alg:")) + + // 公式编号 + show math.equation.where(block: true): show-equation + set math.equation(supplement: "公式") + + // 表格 + show figure.where(kind: table): set figure.caption(position: top) + set figure.caption(separator: separator) + if caption-style == none { + caption-style = (font: ("Times New Roman", "SimHei")) + } + show figure.caption: it => text(size: caption-size, ..caption-style, it) + + // 大表格和代码可跨页 + show figure: set block(breakable: true) + + // 去除空行连接时中文中间的空格 + // https://www.w3.org/TR/clreq/#table_of_punctuation_marks + let han-or-punct = "[-\p{sc=Hani}。.,、:;!‼?⁇⸺——……⋯⋯~–—·・‧//「」『』“”‘’()《》〈〉【】〖〗〔〕[]{}_﹏●•]" + show regex(han-or-punct + " " + han-or-punct): it => { + let (a, _, b) = it.text.clusters() + a + b + } + + it +} diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/preface.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/preface.typ new file mode 100644 index 0000000000..e3b9e82192 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/layouts/preface.typ @@ -0,0 +1,12 @@ +#let preface( + twoside: false, + ..args, + it, +) = { + if twoside { + pagebreak() + " " + } + counter(page).update(0) + set page(numbering: "I") + it +} \ No newline at end of file diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/lib.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/lib.typ new file mode 100644 index 0000000000..2b04ff929b --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/lib.typ @@ -0,0 +1,86 @@ +#import "pages/cover.typ": cover +#import "pages/decl.typ": decl +#import "pages/abstract.typ": abstract +#import "pages/abstract-en.typ": abstract-en +#import "layouts/doc.typ": doc +#import "layouts/preface.typ": preface +#import "pages/outline-page.typ": outline-page +#import "layouts/mainmatter.typ": mainmatter +#import "layouts/glossary.typ": gloss, make-glossary-table +#import "pages/acknowledgement.typ": acknowledgement +#import "layouts/appendix.typ": appendix +#import "utils/bilingual.typ": bibliography +#import "@preview/gb7714-bilingual:0.2.3": multicite + +#let documentclass( + info: (:), + twoside: false, + anonymous: false, + font: "SimSun", + reference-font: ("Times New Roman", "SimSun"), +) = { + return ( + doc: (..args) => { + doc( + ..args, + info: info + args.named().at("info", default: (:)), + ) + }, + cover: (..args) => { + cover( + anonymous: anonymous, + ..args, + info: info, + ) + }, + decl: (..args) => decl( + anonymous: anonymous, + twoside: twoside, + ..args, + info: info, + ), + abstract: (..args) => abstract( + twoside: twoside, + info: info, + font: font, + ..args, + ), + abstract-en: (..args) => abstract-en( + twoside: twoside, + info: info, + ..args, + ), + preface: (..args) => preface( + twoside: twoside, + ..args, + ), + outline-page: (..args) => outline-page( + twoside: twoside, + font: font, + ..args, + ), + mainmatter: (..args) => mainmatter( + twoside: twoside, + font: font, + ..args, + ), + gloss: gloss, + make-glossary-table: make-glossary-table, + bibliography: bibliography, + multicite: multicite, + acknowledgement: (..args) => { + acknowledgement( + anonymous: anonymous, + twoside: twoside, + font: font, + ..args, + ) + }, + appendix: (..args) => { + appendix( + ..args, + ) + }, + twoside: twoside, + ) +} diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/pages/abstract-en.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/abstract-en.typ new file mode 100644 index 0000000000..da25d6f339 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/abstract-en.typ @@ -0,0 +1,47 @@ +#import "@preview/cuti:0.4.0": show-cn-fakebold +#import "@preview/pointless-size:0.1.2": zh + +#let abstract-en( + twoside: false, + outline-title: "Abstract", + outlined: true, + info: (:), + keywords: (), + body, +) = { + if type(info.title-en) == str { + info.title-en = info.title-en.split("\n") + } + + pagebreak(weak: true, to: if twoside { "odd" }) + + [ + #show: show-cn-fakebold + #text(size: 0pt, fill: white)[ + #heading( + numbering: none, + level: 1, + outlined: outlined, + bookmarked: outlined, + outline-title, + ) + ] + #align(center)[ + #text(font: "Times New Roman", size: 14pt, weight: "bold")[ + #info.title-en.join("") + ] + #v(2em) + #text(size: 12pt, font: "Times New Roman", weight: "bold")[Abstract] + ] + #set text(size: 12pt, font: "Times New Roman") + #set par( + justify: true, + first-line-indent: 2em, + spacing: 1.5 * 15.6pt - 0.7em, + leading: 1.5 * 15.6pt - 0.7em, + ) + #body + + #text(font: "Times New Roman", size: 12pt)[*Key words:* #keywords.join("; ")] + ] +} diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/pages/abstract.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/abstract.typ new file mode 100644 index 0000000000..7921f9a1ec --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/abstract.typ @@ -0,0 +1,48 @@ +#import "@preview/cuti:0.4.0": show-cn-fakebold +#import "@preview/pointless-size:0.1.2": zh + +#let abstract( + twoside: false, + outline-title: "摘要", + outlined: true, + info: (:), + keywords: (), + font: "SimSun", + body, +) = { + if type(info.title) == str { + info.title = info.title.split("\n") + } + + pagebreak(weak: true, to: if twoside { "odd" }) + + [ + #show: show-cn-fakebold + #text(size: 0pt, fill: white)[ + #heading( + numbering: none, + level: 1, + outlined: outlined, + bookmarked: outlined, + outline-title, + ) + ] + #align(center)[ + #text(font: "SimHei", size: 18pt, weight: "bold")[ + #info.title.join("") + ] + #v(2em) + #text(size: 14pt, font: "SimHei")[摘#h(1em)要] + ] + #set text(size: zh(-4), font: ("Times New Roman", font)) + #set par( + justify: true, + first-line-indent: 2em, + spacing: 1.5 * 15.6pt - 0.7em, + leading: 1.5 * 15.6pt - 0.7em, + ) + #body + + #text(font: "SimHei", size: zh(4))[关键词:]#text(font: ("Times New Roman", font))[#keywords.join(";")] + ] +} diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/pages/acknowledgement.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/acknowledgement.typ new file mode 100644 index 0000000000..8737d6ee8c --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/acknowledgement.typ @@ -0,0 +1,28 @@ +#import "@preview/pointless-size:0.1.2": zh +// 致谢页 +#let acknowledgement( + // documentclass 传入参数 + anonymous: false, + twoside: false, + // 其他参数 + title: "致  谢", + outlined: true, + font: "SimSun", + body, +) = { + if not anonymous { + pagebreak(weak: true, to: if twoside { "even" }) + [ + #show heading: it => text(fill: white, size: 0pt, it) + #heading(level: 1, numbering: none, outlined: outlined, bookmarked: outlined, title) + + #align(center)[ + #set text(size: zh(-4), font: "SimHei") + #title + ] + + #set text(size: zh(5), font: ("Times New Roman", font)) + #body + ] + } +} diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/pages/cover.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/cover.typ new file mode 100644 index 0000000000..4f70f212e3 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/cover.typ @@ -0,0 +1,171 @@ +#import "@preview/pointless-size:0.1.2": zh +#import "@preview/cuti:0.4.0": show-cn-fakebold +#import "../utils/justify-text.typ": justify-text + +#let cover( + anonymous: false, // 是否匿名,用于盲审送审 + info: (:), // 论文相关信息 + twoside: false, + info-key-width: 72pt, + column-gutter: 10pt, + row-gutter: 11.5pt, + info-inset: (x: 0pt, bottom: 0.5pt), + stroke-width: 0.5pt, + anonymous-info-keys: ( + "student-id", + "author", + "author-en", + "supervisor", + "supervisor-en", + "supervisor-ii", + "supervisor-ii-en", + "chairman", + "class", + "department", + "reviewer", + ), +) = { + // 默认参数 + let info = ( + ( + title: ("基于 Typst 的太原理工大学论文模板", "非官方版本"), + session: "20XX", + student-id: "1001011010", + author: "张三", + class: "XX班", + department: "XX学院", + major: "XX专业", + supervisor: ("李四", "讲师"), + submit-date: datetime.today(), + ) + + info + ) + + + // 处理参数 + if type(info.title) == str { + info.title = info.title.split("\n") + } + assert(type(info.submit-date) == datetime, message: "submit-date must be datetime.") + + let info-key(body, is-meta: true) = { + set text( + font: if is-meta { ("Times New Roman", "KaiTi") } else { ("Times New Roman", "SimHei") }, + size: zh(3), + ) + rect( + width: 100%, + inset: info-inset, + stroke: none, + justify-text(with-tail: is-meta, body), + ) + } + + let info-value(key, body, is-meta: false, no-stroke: false) = { + set align(center) + rect( + width: 100%, + inset: info-inset, + stroke: if no-stroke { none } else { (bottom: stroke-width + black) }, + text( + font: if is-meta { ("Times New Roman", "KaiTi") } else { ("Times New Roman", "SimHei") }, + bottom-edge: "descender", + size: zh(3), + if anonymous and (key in anonymous-info-keys) { + if is-meta { "█████" } else { "██████████" } + } else { + body + }, + ), + ) + } + + let info-long-value(key, body) = { + let processed = if anonymous and (key in anonymous-info-keys) { + "██████████" + } else { + body + } + + if type(processed) == str and processed.contains("\n") { + let lines = processed.split("\n") + grid.cell( + colspan: 3, + stack( + spacing: 1em, + ..lines.map(line => info-value(key, line)), + ), + ) + } else { + // 原逻辑 + grid.cell( + colspan: 3, + info-value(key, processed), + ) + } + } + + let anonymous-text(key, body) = { + if anonymous and (key in anonymous-info-keys) { + "██████████" + } else { + body + } + } + + // 正式渲染 + show: show-cn-fakebold + pagebreak(weak: true, to: if twoside { "odd" }) + + set align(center) + + if anonymous { + v(267pt - 3.3cm) + } else { + v(130pt - 3.3cm) + image("../assets/tyut-logo.jpg", width: 12.11cm) + v(2pt) + } + + text( + size: 30pt, + font: ("Times New Roman", "KaiTi"), + weight: "bold", + )[#underline[#info.session]届本科生毕业设计(论文)] + + v(80pt) + text(size: zh(-1), font: ("Times New Roman", "SimHei"), weight: "bold", info.title.join("\n")) + v(30pt) + + block( + width: 318pt, + grid( + columns: (info-key-width, 1fr, info-key-width, 1fr), + column-gutter: column-gutter, + row-gutter: row-gutter, + info-key("学号"), + info-long-value("student-id", info.student-id), + info-key("姓名"), + info-long-value("author", info.author), + + info-key("学院"), + info-long-value("department", info.department), + info-key("专业"), + info-long-value("major", info.major), + + info-key("班级"), + info-long-value("class", info.class), + info-key("指导教师"), + info-long-value("supervisor", info.supervisor.join([#h(1cm)])), + ), + ) + + place( + center + bottom, + text( + font: ("Times New Roman", "KaiTi"), + size: zh(3), + "完成日期:" + info.submit-date.display("[year]年[month padding:none]月"), + ), + ) +} diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/pages/decl.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/decl.typ new file mode 100644 index 0000000000..fbcb490add --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/decl.typ @@ -0,0 +1,93 @@ +#import "@preview/pointless-size:0.1.2": zh +#let decl( + anonymous: false, + twoside: false, + author-signature: none, + supervisor-signature: none, + info: (:), +) = { + // 匿名送审不需要此页内容 + if anonymous { + return + } + + pagebreak(weak: true, to: if twoside { "odd" }) + + set par( + first-line-indent: (amount: 2em, all: true), + leading: 1.5em, + ) + + [ + #v(24pt) + #align(center)[ + #text(font: "SimHei", size: zh(3))[声明及论文使用的授权]] + #v(10pt) + + #set text(size: zh(4), font: "SimSun") + 本人郑重声明:所呈交的毕业设计(论文)是本人在指导教师的指导下取得的研究成果,毕业设计(论文)写作严格遵循学术规范。除了文中特别加以标注和致谢的地方外,毕业设计(论文)中不包含其他人已经发表或撰写的研究成果。因本毕业设计(论文)引起的法律结果完全由本人承担。太原理工大学享有本毕业设计(论文)的研究成果。 + + #v(5em) + + #stack( + dir: ltr, + stack( + dir: ltr, + [论文作者签名:], + if author-signature != none { author-signature }, + ), + 1fr, + if "author-sign-date" in info { + info.author-sign-date.display("[year]年[month padding:none]月[day padding:none]日") + } else { + [年#h(1cm)月#h(1cm)日] + }, + h(2cm), + ) + #v(7em) + + 本毕业设计(论文)作者和指导教师同意太原理工大学保留使用毕业设计(论文)的规定,即:学校有权保留送交毕业设计(论文)的复印件,允许毕业设计(论文)被查阅和借阅;学校可以上网公布全部内容,可以采用影印、缩印或其他复制手段保存毕业设计(论文)。 + + #v(5em) + + #stack( + dir: ltr, + spacing: 2cm, + stack( + dir: ttb, + spacing: 2em, + stack( + dir: ltr, + [论文作者签名:], + [#if author-signature != none { author-signature }], + ), + stack( + dir: ltr, + [签字日期:], + if "author-sign-date" in info { + h(0.2cm) + info.author-sign-date.display("[year]年[month padding:none]月[day padding:none]日") + } else { [#h(1cm)年#h(1cm)月#h(1cm)日] }, + ), + ), + + stack( + dir: ttb, + spacing: 2em, + stack( + dir: ltr, + [指导教师签名:], + [#if supervisor-signature != none { supervisor-signature }], + ), + stack( + dir: ltr, + [签字日期:], + if "supervisor-sign-date" in info { + h(0.2cm) + info.supervisor-sign-date.display("[year]年[month padding:none]月[day padding:none]日") + } else { [#h(1cm)年#h(1cm)月#h(1cm)日] }, + ), + ), + ) + ] +} diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/pages/outline-page.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/outline-page.typ new file mode 100644 index 0000000000..129fe29379 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/pages/outline-page.typ @@ -0,0 +1,85 @@ +#import "@preview/pointless-size:0.1.2": zh + +#let outline-page( + twoside: false, + depth: 3, + title: "目  录", + outlined: false, + font: "SimSun", + title-vspace: 25pt, + title-text-args: auto, + reference-font: auto, + reference-size: zh(-3), + bookmarked: true, + above: (2pt, 14pt), + below: (14pt, 14pt), + indent: (0pt, 18pt, 28pt), + fill: (repeat([.], gap: 0.15em),), + gap: .3em, + ..args, +) = { + if title-text-args == auto { + title-text-args = (font: "SimHei", size: zh(-3), weight: "bold") + } + if reference-font == auto { + reference-font = ("Times New Roman", "SimHei") + } + + pagebreak(weak: true, to: if twoside { "odd" }) + + set text(font: reference-font, size: reference-size) + + { + set align(center) + text(..title-text-args, title) + text(size: 0em, fill: white)[#heading( + numbering: none, + level: 1, + outlined: false, + bookmarked: bookmarked, + title, + )] + } + + v(title-vspace) + + set outline(indent: level => indent.slice(0, calc.min(level + 1, indent.len())).sum()) + + show outline.entry: entry => block( + above: above.at( + entry.level - 1, + default: above.last(), + ), + below: below.at( + entry.level - 1, + default: below.last(), + ), + link( + entry.element.location(), + entry.indented( + none, + { + text( + font: ("Times New Roman", font), + size: zh(-4), + { + if entry.prefix() not in (none, []) { + entry.prefix() + h(gap) + } + entry.body() + }, + ) + box(width: 1fr, inset: (x: .25em), fill.at(entry.level - 1, default: fill.last())) + { + show text: set text(size: zh(-4), font: ("Times New Roman", font)) + entry.page() + } + }, + gap: 0pt, + ), + ), + ) + + outline(title: none, depth: depth) +} diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/template/imgs/author-signature.jpg b/packages/preview/unofficial-tyut-thesis/0.2.2/template/imgs/author-signature.jpg new file mode 100644 index 0000000000..5b5a531494 Binary files /dev/null and b/packages/preview/unofficial-tyut-thesis/0.2.2/template/imgs/author-signature.jpg differ diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/template/references.bib b/packages/preview/unofficial-tyut-thesis/0.2.2/template/references.bib new file mode 100644 index 0000000000..e527042376 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/template/references.bib @@ -0,0 +1,34 @@ +@INPROCEEDINGS{deepLearn, + author={Goularas, Dionysis and Kamis, Sani}, + booktitle={2019 International Conference on Deep Learning and Machine Learning in Emerging Applications (Deep-ML)}, + title={Evaluation of Deep Learning Techniques in Sentiment Analysis from Twitter Data}, + year={2019}, + volume={}, + number={}, + pages={12-17}, + address={}, + keywords={Sentiment analysis;Deep learning;Feature extraction;Task analysis;Twitter;Recurrent neural networks;sentiment analysis, deep learning, convolutional neural networks, LSTM, word embedding models, Twitter data}, + doi={}} + +@book{蒋有绪1998, + title={中国森林群落分类及其群落学特征}, + author={蒋有绪 and 郭泉水 and 马娟 and others}, + year={1998}, + publisher={科学出版社}, + address={北京}, + pages={11-12}, + isbn={}, + doi={}, + url={}, +} + +@inproceedings{中国力学学会1990, + title={第3届全国实验流体力学学术会议论文集}, + author={中国力学学会}, + year={1990}, + address={天津}, + publisher={奇怪的出版社}, + pages={20-24}, + booktitle={}, + doi={}, +} \ No newline at end of file diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/template/thesis.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/template/thesis.typ new file mode 100644 index 0000000000..b365e20e32 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/template/thesis.typ @@ -0,0 +1,397 @@ +#import "@preview/unofficial-tyut-thesis:0.2.2": documentclass +#import "@preview/gb7714-bilingual:0.2.3": init-gb7714 +#import "@preview/codly:1.3.0": codly-init // 如果不需要插入源代码,可以删除此行代码 +#import "@preview/algo:0.3.6": * // 如不需要伪代码,可以删除此行代码 + +#let ( + doc, + cover, + decl, + abstract, + abstract-en, + preface, + outline-page, + mainmatter, + gloss, + make-glossary-table, + bibliography, + multicite, + acknowledgement, + twoside, + appendix, +) = documentclass( + // anonymous: true, // 需要匿名可以打开此选项 + // twoside: true, // 打印纸质版时可以打开此选项 + info: ( + title: ("基于 Typst 的太原理工大学论文模板", "——非官方版本"), + title-en: " A Typst Template for TYUT Thesis - Unofficial Edition", + author: "爱因斯坦", + student-id: "11001101010086", + // department: "计算机科学与技术学院\n(大数据学院)", // 多行内容可以添加\n + department: "XX学院", + session: "20XX", + major: "XX专业", + class: "XX班", + supervisor: ("张三", "教授"), + submit-date: datetime.today(), + // submit-date: datetime(year: 2025, month: 1, day: 28) + // author-sign-date: datetime.today(), // 承诺书作者签名日期 + // supervisor-sign-date: datetime(year: 1997, month: 1, day:1), // 承诺书导师签名日期 + ), + // font: "KaiTi", // Main Font + // reference-font: ("Times New Roman", "SimSun"), +) + +#show: doc +#show: codly-init.with() // 如果不需要插入源代码,可以删除此行代码 +#cover() + +#show: init-gb7714.with(read("references.bib"), style: "numeric", version: "2025") + +// #decl( +// author-signature: place( +// dy: -1em, +// dx: 1em, +// image("imgs/author-signature.jpg", height: 2em)), +// supervisor-signature: place( +// dy: -1em, +// dx: 1em, +// image("imgs/author-signature.jpg", height: 2em)), +// ) +#decl() + +#show: preface + +// 术语列表 +#make-glossary-table(( + ( + key: "urllc", + short: "URLLC", + long: "Ultra-Reliable and Low Latency Communications", + description: "超可靠低延迟通信", + ), + ( + key: "api", + short: "API", + long: "Application Program Interface", + description: "应用程序接口", + ), + ( + key: "tyut", + short: "TYUT", + long: "Taiyuan University of Technology", + description: "太原理工大学", + ), + ( + key: "yolo", + short: "YOLO", + long: "You Only Look Once", + description: "", + ), +)); + +#abstract(keywords: ("Typst", "TYUT", "Template", "Thesis", "毕业论文"))[ + 本项目是基于 Typst 制作的一款适用于#gloss("tyut")本科毕设论文的模板,注意此模板不是#gloss("tyut")官方模板,因此有不被承认的风险,请谨慎使用。 + + 使用本项目需要具备基本的 Typst 使用知识,学习大概需要1小时,需要阅读#link("https://typst.app/docs/tutorial")[#text(fill: blue)[#underline[官方入门教程]]]。 +] + +#abstract-en(keywords: ("Typst", "TYUT", "Template", "Thesis"))[ + This project is based on Typst to produce a template for undergraduate BSc thesis of Taiyuan University of Technology, note that it is an unofficial template, so there exists the risk of not being recognized, please use with caution. + + Using this project requires basic knowledge of using Typst, which takes about 1 hour to learn and requires reading #link("https://typst.app/docs/tutorial")[#text(fill: blue)[#underline[Official Getting Started Tutorial]]]. +] + +#outline-page() + +#pagebreak() + +#show: mainmatter + + += 绪论 +== 基本书写 + +直接输入文字即可。需要注意,如果两行之间没有空行, +像现在这样,会自动合并为一行。如果需要换行, +则需要多打一个空行。 + +像现在这样。 + +== 无序列表 +可以通过以下方式添加无续列表: + +- 表项1 +- 表项2 + - 表项3 + - 表项4 + +== 有序列表 + +通过以下方式添加有续列表: + ++ 表项1 ++ 表项2 + + 表项3 + + 表项4 ++ 表项5 + +使用如下方式更改有续列表的编号样式: + +#[ + #set enum(numbering: "A.a)") + + 表项1 + + 表项2 + + 表项3 + + 表项4 + + 表项5 +] + +或者更复杂的自定义方案: + +#[ + #enum( + numbering: "A.", + enum.item(1)[表项1], + enum.item(2)[表项2 + #enum( + numbering: (..nums) => "B." + numbering("a)", ..nums), + enum.item(1)[表项3], + enum.item(2)[表项4], + ) + ], + enum.item(3)[表项5], + ) +] + +== 术语 + +如果论文中出现缩写,推荐使用 gloss 工具进行管理,先将相关内容放入文档开头处的 make-glossary-table 中,之后再使用,例如,第一次出现#gloss("urllc")时,会写出对应的中文内容、英文全称和缩写,之后再出现 +#gloss("urllc")时,则只出现缩写。再举一个例子:#gloss("api")应当是全称,#gloss("api")和#gloss("api")应当只显示缩写。如果术语没有中文翻译,则可以使其 description 为空字符串,例如#gloss("yolo"),第一次出现时只显示全称,之后再出现则只显示缩写,如#gloss("yolo")。 + +如果引用了列表中没有出现的术语,则会出现红色警告,例如:#gloss("vanet") + +== 图片和表格 + +引用@tbl:timing,引用@tbl:timing-tlt,以及@fig:some-figure。引用图表时,表格和图片分别需要加上 `tbl:`和`fig:` 前缀才能正常显示编号。图片、表格以及引用的标签,尽量不要添加编号信息,以真正的内容作为标签。比如,`` 是一个好标签,`` 是一个糟糕的标签。 + +#align( + center, + ( + stack(dir: ltr)[ + #figure( + table( + align: center + horizon, + columns: 4, + [t], [1], [2], [3], + [y], [0.3s], [0.4s], [0.8s], + ), + caption: [常规表], + ) + ][ + #h(50pt) + ][ + #figure( + table( + columns: 4, + stroke: none, + table.hline(), + [t], [1], [2], [3], + table.hline(stroke: .5pt), + [y], [0.3s], [0.4s], [0.8s], + table.hline(), + ), + caption: [三线表], + ) + ] + ), +) + +如果图片太大导致空白区域太大,可以添加`placement`选项,比如@fig:some-figure 所展示的用法。 + +#figure( + image("imgs/author-signature.jpg", width: 50%), + numbering: none, + placement: auto, + caption: [图片测试], +) + +#figure( + [ + #set text(font: ("Times New Roman", "SimHei"), size: 10pt) + #set stack(dir: ttb, spacing: 0.5em) + #set image(height: 2cm) + #grid( + columns: 2, + gutter: 1em, + stack(image("imgs/author-signature.jpg"), [(a) 子图1]), stack(image("imgs/author-signature.jpg"), [(b) 子图2]), + stack(image("imgs/author-signature.jpg"), [(c) 子图3]), stack(image("imgs/author-signature.jpg"), [(d) 子图4]), + )], + caption: [多图示例], + placement: auto, +) + +@fig:multiple-figures 是一个多图合并的例子。 + +== 引用 + +直接引用相关 `bib` 文件中的条目即可,如这里引用了@deepLearn。中文引用@蒋有绪1998 也可以正常显示。引用会按照出现的顺序自动编号,因此,尽量不要在引用的标签中加入序号信息。例如,`ref6` 是一个糟糕的引用标签,`` 则是一个不错的引用标签。默认引用为上标形式,如果想要采用非上标形式,则需要这样:另见#cite(, form: "prose")的详细分析。引用也可以添加作者,比如:#cite(<蒋有绪1998>, form: "author")在#cite(<蒋有绪1998>, form: "prose")中,提出了重要的理论框架。 + +当需要在同一个地方引用多个文献时,需要使用 `multicite` 函数,如#multicite("蒋有绪1998", "deepLearn", "中国力学学会1990"),此时,引用会自动进行合并,如果不是连续的序号,则会自动断开,如#multicite("deepLearn", "中国力学学会1990")。此外,如果需要非上标形式,则可以:#multicite("蒋有绪1998", "deepLearn", "中国力学学会1990", form: "prose")。需要注意的是,`multicite` 不支持直接引用作者,即 `form` 字段不支持 `author` 选项。 + + += 数学公式与代码 + +== 数学公式示例 + +我们可以利用求根公式来得到一般形式的一元二次方程:$a x^2 + b x + c = 0$ 的解,其具体内容为(如果不希望公式后边段落有缩进,可以使用以下方式临时关闭): + +$ + x_(1,2) = (-b plus.minus sqrt(b^2 - 4 a c)) / (2 a), +$ + +#[ + #set par(first-line-indent: 0em) + 其中, $a, b$ 和 $c$ 为原始方程的系数。根据@eqt:root-finder, 可以看到,每个一元二次方程,都有两个解,不过有时候两个根可能相等,有时候可能会出现复数根。 +] + +根据相关公式,我们可以得到 $e^x$ 的泰勒展示: + +$ + e^x= sum_(i=0)^oo x^i / i!. +$ + +如果某个公式不需要编号,可以加入 `<->` 标签。如: + +$ + integral.cont sqrt(x^2+y^2) dif x dif y. +$ <-> + +但是后续公式会自动继续编号: + +$ + e^(i pi) + 1 = 0. +$ + +更多数学公式内容,参考#text(fill: blue)[#underline[#link("https://typst.app/docs/reference/math/")[*官方文档*]]]。也可使用#text(fill: blue)[#underline[#link("https://typerino.com/")[*在线公式编辑器*]]]进行公式编辑。 + +== 代码 + +=== 原始效果 + +行内代码块需要包裹在反引号内,如 `http`,块级代码则需要以三个反引号包裹,后面加上语言名称(可选),如@lst:cpp-code 所示。 +如果需要引用代码,需要加上`lst`,如这里引用了@lst:cpp-code。 + +#figure( + ```cpp + #include + #include + using std::cout; + using std::endl; + using std::vector; + + int main() { + vector v{10, 3}; + for (auto i : v) { + cout << i << endl; + } + return 0; + } + ```, + placement: auto, + caption: [代码块展示], +) + + +==== 四级标题不会出现在目录中 + +这是四级标题下的内容。 + + +=== 伪代码 + +伪代码可以用 `algo` 库,如@alg:fib 所示。 + + +#figure( + algo( + title: "Fib", + parameters: ("n",), + )[ + if $n < 0$:#i\ // use #i to indent the following lines + return null#d\ // use #d to dedent the following lines + if $n = 0$ or $n = 1$:#i #comment[you can also]\ + return $n$#d #comment[添加 comments!]\ + return #smallcaps("Fib")$(n-1) +$ #smallcaps("Fib")$(n-2)$ + ], + caption: [斐波那契数列], + kind: "algo", + supplement: "算法", +) + +从@alg:fib 中可以看到,斐波那契数列可以用递归的方式进行计算。 + + +// 参考文献 +#bibliography() + + +#acknowledgement[ + 作者在设计(论文)期间都是在×××教授全面、具体指导下完成进行的。×老师渊博的学识、敏锐的思维、民主而严谨的作风使学生受益非浅,并终生难忘。 + + 感谢×××副教授等在毕业设计工作中给予的帮助。 + + 感谢我的学友和朋友对我的关心和帮助。 + +] + +// 如果不需要附录,请删除后续内容 + +#show: appendix + +// 手动分页 +#if twoside { + pagebreak() + " " +} + += 关于网络演算的基本说明 + +== 到达曲线的说明 + +$ + lr(chevron.l f, alpha chevron.r) = sup_(0 <= t <= s) [f(x-t) + f(t) <= alpha] +$ + +#figure( + image("imgs/author-signature.jpg"), + caption: [附录图片], +) + +再试试表格。 + +#figure( + table( + align: center, + columns: 3, + [a], [b], [c], + [d], [e], [f], + ), + caption: [附录表格], +) + +附录中的公式引用:@eqt:appendix-equation,附录中的图片引用:@fig:appendix-figure,附录中的表格引用:@tbl:appendix-table。 + += 一些证明细节 + +== 另外的数学公式 + +$ + integral_(-oo)^oo x dif x = 0 +$ + +#figure( + image("imgs/author-signature.jpg"), + caption: [附录图片], +) + +附录中的公式引用:@eqt:appendix-equation2,附录中的图片引用:@fig:appendix-figure2. diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/thumbnail.png b/packages/preview/unofficial-tyut-thesis/0.2.2/thumbnail.png new file mode 100644 index 0000000000..6d01f81b7f Binary files /dev/null and b/packages/preview/unofficial-tyut-thesis/0.2.2/thumbnail.png differ diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/typst.toml b/packages/preview/unofficial-tyut-thesis/0.2.2/typst.toml new file mode 100644 index 0000000000..8097266089 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/typst.toml @@ -0,0 +1,17 @@ +[package] +name = "unofficial-tyut-thesis" +version = "0.2.2" +entrypoint = "lib.typ" +authors = ["pdcxs"] +license = "MIT" +description = "非官方太原理工大学本科毕业论文 typst 模板。" +repository = "https://github.com/pdcxs/unofficial-tyut-thesis" +keywords = ["Taiyuan University of Technology", "TYUT", "thesis"] +categories = ["thesis"] +exclude = [] +compiler = "0.14.0" + +[template] +path = "template" +entrypoint = "thesis.typ" +thumbnail = "thumbnail.png" diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/utils/bilingual.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/utils/bilingual.typ new file mode 100644 index 0000000000..6ef15d3e71 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/utils/bilingual.typ @@ -0,0 +1,32 @@ +#import "@preview/gb7714-bilingual:0.2.3": gb7714-bibliography +#import "@preview/pointless-size:0.1.2": zh + +#let bibliography(..args) = gb7714-bibliography( + title: [#heading(level: 1, numbering: none)[#text(size: zh(-4))[参考文献]]], + full-control: entries => { + context { + if entries.len() == 0 { + return + } + + let max-width = measure([[#{ entries.len() }]]).width + + let spacing = 0.5em + let uniform-hanging = max-width + spacing + + for e in entries { + let num-content = [[#e.order]] // 带方括号 + let num-width = measure(num-content).width + par( + hanging-indent: uniform-hanging, + first-line-indent: 0pt, + )[ + #set text(size: zh(5)) + #box(width: max-width)[#align(right)[#num-content]]#h(spacing)#e.labeled-rendered + ] + v(0.2em) + } + } + }, + ..args, +) diff --git a/packages/preview/unofficial-tyut-thesis/0.2.2/utils/justify-text.typ b/packages/preview/unofficial-tyut-thesis/0.2.2/utils/justify-text.typ new file mode 100644 index 0000000000..30dfae1135 --- /dev/null +++ b/packages/preview/unofficial-tyut-thesis/0.2.2/utils/justify-text.typ @@ -0,0 +1,7 @@ +#let justify-text(with-tail: false, tail: ":", body) = { + if with-tail and tail != "" { + stack(dir: ltr, stack(dir: ltr, spacing: 1fr, ..body.split("").filter(it => it != "")), tail) + } else { + stack(dir: ltr, spacing: 1fr, ..body.split("").filter(it => it != "")) + } +} \ No newline at end of file