22 Commits

Author SHA1 Message Date
2787bed48d fix Matěj damage 2025-10-03 11:09:23 +02:00
a691d84e1b implement attachments 2025-10-03 11:07:22 +02:00
Matej-Zucha-TUL
a0c75deba0 Change example document signature to reflect reality better 2025-10-03 09:26:49 +02:00
Matej-Zucha-TUL
1a7418d2cd Add optional consultant parameter 2025-10-03 09:25:37 +02:00
2e300ded3c add pronouns picking for english 2025-10-02 23:28:07 +02:00
0e9fbcdc93 update doc comment for the tultemplate2 function 2025-10-02 23:27:43 +02:00
bfe08ac9b4 fix some image/table list problems 2025-10-02 23:26:48 +02:00
8a76ee9e1e update documentation 2025-10-02 20:57:37 +02:00
d954a0e687 classic template fixes 2025-10-02 20:57:22 +02:00
eba0ec7826 add image and table listings 2025-10-02 20:39:26 +02:00
768ba54856 classic template fixes 2025-10-02 15:26:55 +02:00
85a6ed8d44 add study branch to info page 2025-10-02 14:11:14 +02:00
afe325da0a fix error on no author 2025-10-02 13:45:22 +02:00
cc079dd87d fix no bp document type on info page 2025-10-02 13:40:56 +02:00
08c7123041 fix incorrect panic message on supported genders 2025-10-02 13:39:20 +02:00
c786ec2a4a allow content abstract type 2025-10-02 13:34:15 +02:00
5773e9785b expand czech disclaimer genders 2025-10-02 13:31:14 +02:00
f31bcaddec fix some build mistakes 2025-10-02 12:11:34 +02:00
26d861b72a improve bibliography a bit 2025-10-01 22:34:31 +02:00
6bebe41d6e add citation tests 2025-10-01 22:25:35 +02:00
4e634e6ff9 document other arguments 2025-10-01 21:31:57 +02:00
b03978a2c0 add disclaimer base and bachelor to english 2025-10-01 21:31:34 +02:00
14 changed files with 525 additions and 59 deletions

View File

@@ -10,7 +10,8 @@ watch_example:
example: example.pdf
TO_PACK := $(shell find template -type f) template/LICENSE
PACK_TARGETS := $(TO_PACK:%=pack/tultemplate2/%) pack/tultemplate2/example.typ
PACK_TARGETS := $(TO_PACK:%=pack/tultemplate2/%) pack/tultemplate2/example.typ \
pack/tultemplate2/citations.bib
.PHONY: pack
pack: pack/tultemplate2.zip
@@ -25,7 +26,7 @@ pack/tultemplate2.zip: $(PACK_TARGETS)
rm -f $@
cd pack && zip -r tultemplate2.zip tultemplate2
pack/tultemplate2/example.typ: example.typ
pack/tultemplate2/%: %
ln -f $< $@
pack/tultemplate2/template/LICENSE: LICENSE

View File

@@ -191,6 +191,34 @@ Tady je praktická ukázka jednoduchého vložení obrázku s popiskem:
Logo *TUL*
])
Obrázky se zobrazí na začátku dokumentu v seznamu (pokud to daný typ dokumentu vyžaduje).
== Tabulky
Tabulky lze vytvářet takto:
```typst
#figure(table(
columns: 3,
table.header([], [*Sloupec 1*], [*Sloupec 2*]),
[*Řádek 1*], [a], [b],
[*Řádek 2*], [c], [d],
), caption: "Moje krásná tabulka")
```
#highlight[Hlavičku tabulky (první řádek) je dobré zabalit do funkce header (viz. výše)], to je
kvůli tomu, že Typst do vygenerovaného PDF souboru poté přidá metadata (například pro osoby se
zrakovým postižením).
#figure(table(
columns: 3,
table.header([], [*Sloupec 1*], [*Sloupec 2*]),
[*Řádek 1*], [a], [b],
[*Řádek 2*], [c], [d],
), caption: "Moje krásná tabulka")
Tabulky se zobrazí na začátku dokumentu v seznamu (pokud to daný typ dokumentu vyžaduje).
== Citace
Šablona podporuje správu citací pomocí standardního BibTeX @bibtex souboru, stejně jako
@@ -291,6 +319,42 @@ Zvýrazněné hodnoty jsou základní -- pokud vynecháte parametr, pak bude pou
- `lang` (základní jazyk dokumentu)
- *`"cs"`* - čeština
- `"en"`
#line()
- `document` (typ dokumentu)
- *`"other"`* - nespecifikovaný (neformální) typ dokumentu
- `bp` - Bakalářská práce
#line()
- `title` (nadpis dokumentu)
- Ve formátu `(<zkratka_jazyka>: "<nadpis>")`, například `(cs: "Můj nadpis")`
#line()
- `author` (autor/autoři dokumentu)
- Příklad: `"Pavel Novák"` nebo `"Petra Velká, Jindřich Peterka"`
#line()
- `author_gender` (rod autora v českém jazyce - není potřeba pro angličtinu)
- `"masculine"` - Mužský rod
- `"feminine"` - Ženský rod
- `"we"` - Množné číslo
#line()
- `supervisor` (vedoucí práce)
- Příklad: `"prof. Jindřich Jindřich"`
#line()
- `programme` (studijní program autora)
- Ve formátu `(<zkratka_jazyka>: "<název_programu>")`
#line()
- `abstract` (abstrakt)
- Ve formátu `(<zkratka_jazyka>: [<abstrakt>])`, například `(cs: [Můj *krásný* abstrakt.])`
#line()
- `keywords` (klíčová slova zobrazovaná pod abstraktem)
- Ve formátu `(<zkratka_jazyka>: ("slovo1", "slovo2", ...))`
#line()
- `assignment` (PDF soubor se zadáním)
- Ve formě cesty k souboru, například: `"zadani.pdf"`. Pokud je tento argument vynechán, bude
vložena hláška "vložte zadání" na příslušné místo v dokumentu -- tu stranu můžete pak nahradit
originálem zadání.
#line()
- `citations` (BibTex soubor s citacemi)
- Ve formě cesty k souboru, například: `"citace.bib"`. Pokud není specifikován, bude použit
výchozí (`"citations.bib"`).
#pagebreak(weak: true)
== Zkratky

167
template/attachments.typ Normal file
View File

@@ -0,0 +1,167 @@
#import "utils.typ": assert_type_signature, is_none
#import "lang.typ": get_lang_item
#let attachment_data = state("attachment_data");
#let attach_link(name, link) = {
assert_type_signature(link, "string", "attach link argument");
assert_type_signature(name, "string", "attach link name argument");
("link", link, name)
}
#let attach_content(name, inner_content) = {
assert_type_signature(inner_content, "content", "attach content argument");
assert_type_signature(name, "string", "attach content name argument");
("content", inner_content, name)
}
#let attach_pdf(name, filepath) = {
assert_type_signature(filepath, "string", "attach pdf argument");
assert_type_signature(name, "string", "attach pdf name argument");
("pdf", filepath, name)
}
#let attach_file_reference(name, filename) = {
assert_type_signature(filename, "string", "attach file reference filename argument");
assert_type_signature(name, "string", "attach file reference name argument");
("ref", filename, name)
}
#let make_content_anchor(idx) = {
"attachment_" + str(idx + 1)
}
#let generate_attachment_content(attachment, idx) = {
let attachment_type = attachment.at(0);
if attachment_type == "content" {
let anchor = make_content_anchor(idx);
[#metadata(attachment.at(1)) #label(anchor)];
}
}
#let generate_attachment_info(attachment, idx) = {
let attachment_type = attachment.at(0);
if type(attachment_type) != str {
panic("invalid attachment - wrap the attach using: attach_content, attach_pdf, ...");
}
if attachment_type == "content" {
let anchor = make_content_anchor(idx);
"(\"content\",\"" + anchor + "\",\"" + attachment.at(2) + "\")"
} else if attachment_type == "pdf" {
"(\"pdf\",\"" + attachment.at(1) + "\",\"" + attachment.at(2) + "\")"
} else if (
attachment_type == "pdf" or
attachment_type == "link" or
attachment_type == "ref"
) {
"(" + attachment.map((v) => { "\"" + v + "\"" }).join(",") + ",)"
} else {
panic("unknown attachment type '" + attachment_type + "'");
}
}
#let attachments(attachments) = {
assert_type_signature(
attachments, "array[array[string | content]] | array[string | content]", "attachments"
);
context {
if not is_none(attachment_data.get()) {
panic("re-definition of attachments - attachments must only be defined once");
}
if attachments.len() == 0 {
attachment_data.update("false");
} else {
attachment_data.update({
"(" + if type(attachments) == array and type(attachments.at(0)) == array {
for (idx, attachment) in attachments.enumerate() {
(generate_attachment_info(attachment, idx),)
}.join(", ")
} else {
generate_attachment_info(attachments, 0)
} + ",)"
})
if type(attachments) == array and type(attachments.at(0)) == array {
for (idx, attachment) in attachments.enumerate() {
generate_attachment_content(attachment, idx);
}
} else {
generate_attachment_content(attachments, 0);
}
}
}
}
#let list_entry(language, entry, is_embedded) = {
let entry_type = entry.at(0);
entry.at(2);
if entry_type == "link" {
": ";
link(entry.at(1));
} else if entry_type == "ref" {
": soubor ";
raw(entry.at(1));
}
if is_embedded {
text(
" (" + get_lang_item(language, "attached_bellow") + ")",
style: "italic",
fill: black.lighten(50%),
);
}
}
#let attachment_list(language) = {
context {
let data = attachment_data.get();
if is_none(data) {
return;
}
let data = eval(data);
heading(get_lang_item(language, "attachments"), numbering: none);
// listing
let has_embedded = false;
let enum_items = ();
for attachment in data {
let attachment_type = attachment.at(0);
let is_embedded = false;
if attachment_type == "content" or attachment_type == "pdf" {
has_embedded = true;
is_embedded = true;
}
enum_items.push(list_entry(language, attachment, is_embedded));
}
enum(..enum_items.map((v) => { enum.item(v) }), spacing: 1em);
if has_embedded {
pagebreak(weak: true);
}
// embedded
set page(footer: none);
for (idx, attachment) in data.enumerate() {
let attachment_type = attachment.at(0);
if attachment_type == "content" {
heading(
level: 2,
get_lang_item(language, "attachment") + " " + str(idx + 1),
numbering: none,
outlined: false,
);
query(label(attachment.at(1))).at(0).value;
} else if attachment_type == "pdf" {
import "@preview/muchpdf:0.1.1": muchpdf
page(place(center + horizon, heading(
level: 2,
get_lang_item(language, "attachment") + " " +
str(idx + 1) + " " +
get_lang_item(language, "next_page_attachment"),
numbering: none,
outlined: false,
)), margin: 0em);
set page(margin: 0em);
muchpdf(read("../" + attachment.at(1), encoding: none), width: 100%);
}
}
}
}

View File

@@ -1,5 +1,17 @@
#import "../lang.typ": get_lang_item
#import "common.typ": mainpage, default_styling, assignment, disclaimer, abstract, toc, abbrlist
#import "common.typ": (
mainpage,
default_styling,
assignment,
disclaimer,
abstract,
toc,
abbrlist,
imagelist,
tablelist,
bibliogr
)
#import "../attachments.typ": attachment_list
#import "../utils.typ": is_none, assert_dict_has, assert_not_none
#let bp(
@@ -7,20 +19,30 @@
faculty_id, faculty_color, language, assignment_document, citation_file,
// document info
title, author, author_gender, supervisor, study_programme, abstract_content, keywords,
title, author, author_gender, supervisor, consultant, study_programme, study_branch, abstract_content,
keywords,
content
) = {
let force_langs = ("cs", "en");
assert_not_none(title, "title");
assert_dict_has(force_langs, title, "title");
assert_not_none(study_programme, "study programme");
assert_dict_has((language,), study_programme, "study programme");
assert_not_none(study_branch, "study branch");
assert_dict_has((language,), study_branch, "study branch");
assert_not_none(abstract_content, "abstract");
assert_dict_has(force_langs, abstract_content, "abstract");
if not is_none(keywords) {
assert_dict_has(force_langs, keywords, "keywords");
}
if language == "cs" {
assert_not_none(author_gender, "author gender");
}
mainpage(faculty_id, language, none, title, author, supervisor, study_programme);
mainpage(faculty_id, language, "bp", title, author, supervisor, consultant, study_programme, study_branch);
assignment(language, assignment_document);
default_styling(false, faculty_color, {
disclaimer(language, faculty_id, "bp", author, author_gender);
@@ -28,7 +50,11 @@
abstract("en", title, abstract_content, keywords);
toc(language);
abbrlist(language);
content
bibliography(citation_file, style: "../tul_citace.csl");
imagelist(language);
tablelist(language);
pagebreak(weak: true);
content;
bibliogr(language, citation_file);
attachment_list(language);
});
}

View File

@@ -1,7 +1,7 @@
// tools & utils
#import "../theme.typ": faculty_logotype, tul_logomark, faculty_color
#import "../lang.typ": lang_id, get_lang_item
#import "../utils.typ": assert_in_dict, assert_in_arr, map_none
#import "../utils.typ": assert_in_dict, assert_in_arr, map_none, assert_dict_has
// thesis types
#import "bp.typ": bp
@@ -12,16 +12,21 @@
language, faculty_id, document_type, citation_file, assignment_document,
// document info
title, author, author_gender, supervisor, study_programme, abstract, keywords,
title, author, author_gender, supervisor, consultant, study_programme, study_branch, abstract, keywords,
// content
content,
) = {
// argument pre-checking
let document_types = (
"bp": bp,
"other": other,
)
assert_in_dict(document_type, document_types, "document type");
map_none(title, (v) => assert_dict_has((language,), v, "title"));
map_none(study_programme, (v) => assert_dict_has((language,), v, "study programme"));
map_none(study_branch, (v) => assert_dict_has((language,), v, "study branch"));
document_types.at(document_type)(
faculty_id,
@@ -33,7 +38,9 @@
author,
author_gender,
supervisor,
consultant,
study_programme,
study_branch,
abstract,
keywords,
content,

View File

@@ -7,6 +7,11 @@
#let serif_font = "Merriweather";
#let tul_logomark_size = 6.5em;
// COUNTERS
#let image_count = counter("image_count");
#let table_count = counter("table_count");
// TYPST ELEMENT STYLING
#let default_styling(flip_bonding, faculty_color, content) = {
@@ -32,6 +37,19 @@
set text(font: serif_font);
set par(justify: true);
// figures
let figure_numbering(realcount, c) = {
context realcount.step();
context numbering("1. 1", counter(heading).get().at(0), c)
};
show figure.where(kind: image): set figure(numbering: figure_numbering.with(image_count));
show figure.where(kind: table): set figure(numbering: figure_numbering.with(table_count));
show figure.where(kind: table): set figure.caption(position: top);
show figure: it => {
block(it, above: 2em, below: 2em);
}
set image(width: 80%);
// heading
set heading(numbering: "1.1.1 ");
show heading: it => {
@@ -43,6 +61,10 @@
);
};
show heading.where(level: 1): it => {
// reset figure counters
context counter(figure.where(kind: image)).update(0);
context counter(figure.where(kind: table)).update(0);
pagebreak(weak: true);
v(2cm);
it
@@ -54,7 +76,6 @@
block(it, fill: rgb("#eee"), inset: 1em)
};
set highlight(fill: faculty_color.lighten(90%));
set image(width: 80%);
content
}
@@ -75,7 +96,7 @@
faculty_id,
language,
document_type,
title, author, supervisor, study_programme,
title, author, supervisor, consultant, study_programme, study_branch,
) = {
let info_name_value_padding = 5em;
let info_name_min_width = 10em;
@@ -97,8 +118,10 @@
// [field_name, field_value, bold]
let info_fields = (
("study_programme", study_programme, false),
(if author.contains(", ") { "authors" } else { "author" }, author, true),
("study_branch", study_branch, false),
("author", author, true),
("supervisor", supervisor, false),
("consultant", consultant, false),
)
context {
let max_field_name_width = calc.max(..info_fields.map((v) => {
@@ -110,13 +133,13 @@
}), info_name_min_width.to-absolute());
grid(
columns: 2,
rows: (auto, 1.2em),
gutter: .5em,
..info_fields.filter((v) => { type(v.at(1)) != type(none) }).map((v) => {
(
block(
align(top, block(
text(get_lang_item(language, v.at(0)) + ":", style: "italic", font: base_font),
width: max_field_name_width + info_name_value_padding,
),
width: max_field_name_width + info_name_value_padding
)),
text(v.at(1), font: base_font, weight: if v.at(2) { "bold" } else { "regular" })
)
}).flatten(),
@@ -133,21 +156,22 @@
faculty_id,
language,
document_type,
title, author, supervisor, study_programme,
title, author, supervisor, consultant, study_programme, study_branch
) = {
import "../utils.typ": has_all_none
import "../utils.typ": has_all_none, map_none
let nonetype = type(none);
page({
if has_all_none((
document_type, title, author, supervisor, study_programme,
document_type, title, author, supervisor, consultant, study_programme,
)) {
place(center + horizon, align(left, faculty_logotype(faculty_id, language)));
} else {
header(faculty_id, language);
align({
info(
faculty_id, language, document_type, title.at(language),
author, supervisor, study_programme,
faculty_id, language, document_type, map_none(title, (v) => v.at(language)),
author, supervisor, consultant, map_none(study_programme, (v) => v.at(language)),
map_none(study_branch, (v) => v.at(language)),
);
v(5em);
}, bottom);
@@ -216,6 +240,61 @@
}
}
// _ OUTLINE FIGURE INNER
#let _outline_figure_inner(selector, title, body_mapper) = {
let entry(selector, element) = {
link(
element.location(),
grid(
columns: 3,
gutter: .5em,
stack(
dir: ltr,
text(numbering(
"1.1",
counter(heading).at(element.location()).at(0),
counter(selector).at(element.location()).at(0),
)),
h(.5em),
text(body_mapper(element)),
),
box(repeat([.], gap: 0.15em)),
str(element.location().page()),
),
)
}
heading(title, numbering: none);
for el in query(figure.where(kind: selector)) {
if is_none(el.caption) {
continue;
}
entry(figure.where(kind: selector), el);
}
}
// _ FIGURE OUTLINE
#let _figure_outline(realcount, target, title) = {
context {
if realcount.final().at(0) == 0 {
return;
}
_outline_figure_inner(target, title, (it) => it.caption.body);
}
}
// IMAGE LIST
#let imagelist(language) = {
_figure_outline(image_count, image, get_lang_item(language, "image_list"));
}
// TABLE LIST
#let tablelist(language) = {
_figure_outline(table_count, table, get_lang_item(language, "table_list"));
}
// ABBREVIATION LIST
#let abbrlist(language) = {
@@ -249,3 +328,15 @@
};
outline(title: get_lang_item(language, "toc"));
}
// BIBLIOGRAPHY
#let bibliogr(language, citations_file) = {
if language == "cs" {
bibliography(citations_file, style: "../tul_citace.csl");
} else if language == "en" {
bibliography(citations_file, style: "iso-690-numeric");
} else {
panic("unknown language for bibliography '" + language + "'");
}
}

View File

@@ -1,25 +1,39 @@
#import "../lang.typ": get_lang_item
#import "common.typ": mainpage, default_styling, assignment, disclaimer, abstract, toc, abbrlist
#import "../utils.typ": is_none
#import "common.typ": (
mainpage,
default_styling,
assignment,
disclaimer,
abstract,
toc,
abbrlist,
imagelist,
tablelist,
)
#import "../attachments.typ": attachment_list
#import "../utils.typ": is_none, assert_not_none, assert_dict_has, assert_in_arr
#let other(
// general settings
faculty_id, faculty_color, language, assignment_document, citation_file,
// document info
title, author, _, supervisor, study_programme, abstract_content, keywords,
title, author, _, supervisor, consultant, study_programme, study_branch, abstract_content, keywords,
content
) = {
mainpage(faculty_id, language, none, title, author, supervisor, study_programme);
assert_not_none(title, "title");
assert_dict_has((language,), title, "title");
mainpage(faculty_id, language, none, title, author, supervisor, consultant, study_programme, study_branch);
default_styling(true, faculty_color, {
toc(language);
abbrlist(language);
imagelist(language);
tablelist(language);
pagebreak(to: "even", weak: true);
content
// bibliography
content;
bibliography(citation_file, style: "../tul_citace.csl");
attachment_list(language);
});
}

View File

@@ -3,18 +3,18 @@
"author": "Autor",
"authors": "Autoři",
"supervisor": "Vedoucí práce",
"consultant": "Konzultant práce",
"study_programme": "Studijní program",
"study_branch": "Studijní obor",
"bp": "Bakalářská práce",
"dp": "Diplomová práce",
"dis": "Disertační práce",
"city": "Liberec",
"toc": "Obsah",
"disclaimer": "Prohlášení",
"disclaimer_content": "Prohlašuji, že {svůj} {práce:tu} jsem vypracoval{a} samostatně jako původní dílo s použitím uvedené literatury a na základě konzultací s vedoucím bakalářské práce a konzultantem.\n\nJsem si vědom{a} toho, že na {moji} {práce:tu} se plně vztahuje zákon č. 121/2000 Sb., o právu autorském, zejména § 60 školní dílo.\n\nBeru na vědomí, že Technická univerzita v Liberci nezasahuje do mých autorských práv užitím {} {práce:té} pro vnitřní potřebu Technické univerzity v Liberci.\n\nUžiji-li {práce:tu} nebo poskytnu-li licenci k {jejímu} využití, jsem si vědom{a} povinnosti informovat o této skutečnosti Technickou univerzitu v Liberci; v tomto případě má Technická univerzita v Liberci právo ode mne požadovat úhradu nákladů, které vynaložila na vytvoření díla, až do jejich skutečné výše.\n\nSoučasně čestně prohlašuji, že text elektronické podoby práce vložený do IS/STAG se shoduje s textem tištěné podoby práce.\n\nBeru na vědomí, že {můj} {práce:ta} bude {zveřejněn} Technickou univerzitou v Liberci v souladu s § 47b zákona č. 111/1998 Sb., o vysokých školách a o změně a doplnění dalších zákonů (zákon o vysokých školách), ve znění pozdějších předpisů.\n\nJsem si vědom{a} následků, které podle zákona o vysokých školách mohou vyplývat z porušení tohoto prohlášení.",
"disclaimer_content": "Prohlašuj{g:i|i|eme}, že {svůj} {práce:tu} js{g:em|em|me} vypracoval{g:|a|i} samostatně jako původní dílo s použitím uvedené literatury a na základě konzultací s vedoucím {{g:mé|mé|naší}} bakalářské práce a konzultantem.\n\nJs{g:em|em|me} si vědom{g:|a|i} toho, že na {{g:moji|moji|naši}} {práce:tu} se plně vztahuje zákon č. 121/2000 Sb., o právu autorském, zejména § 60 školní dílo.\n\nBer{g:u|u|eme} na vědomí, že Technická univerzita v Liberci nezasahuje do {g:mých|mých|našich} autorských práv užitím {{g:mé|mé|naší}} {práce:té} pro vnitřní potřebu Technické univerzity v Liberci.\n\nUžij{g:i|i|eme}-li {práce:tu} nebo poskytn{g:u|u|eme}-li licenci k {jejímu} využití, js{g:em|em|me} si vědom{g:|a|i} povinnosti informovat o této skutečnosti Technickou univerzitu v Liberci; v tomto případě má Technická univerzita v Liberci právo od{g:e|e|} {g:mne|mne|nás} požadovat úhradu nákladů, které vynaložila na vytvoření díla, až do jejich skutečné výše.\n\nSoučasně čestně prohlašuj{g:i|i|eme}, že text elektronické podoby práce vložený do IS/STAG se shoduje s textem tištěné podoby práce.\n\nBer{g:u|u|eme} na vědomí, že {{g:můj|můj|naše}} {práce:ta} bude {zveřejněn} Technickou univerzitou v Liberci v souladu s § 47b zákona č. 111/1998 Sb., o vysokých školách a o změně a doplnění dalších zákonů (zákon o vysokých školách), ve znění pozdějších předpisů.\n\nJs{g:em|em|me} si vědom{g:|a|i} následků, které podle zákona o vysokých školách mohou vyplývat z porušení tohoto prohlášení.",
"disclaimer_replace": {
"bp": {
@@ -22,6 +22,9 @@
"práce:tu": "bakalářskou práci",
"práce:té": "bakalářské práce",
"moji": "moji",
"naše": "naše",
"naši": "naši",
"naší": "naší",
"mé": "mé",
"můj": "moje",
"svůj": "svoji",
@@ -35,6 +38,12 @@
"abstract": "Abstrakt",
"keywords": "Klíčová slova",
"abbrs": "Seznam zkratek",
"image_list": "Seznam obrázků",
"table_list": "Seznam tabulek",
"attachments": "Přílohy",
"attachment": "Příloha",
"next_page_attachment": "začíná na další straně",
"attached_bellow": "dále přiloženo",
"place_assignment": "Sem vložte zadání"
},
@@ -43,24 +52,36 @@
"author": "Author",
"authors": "Authors",
"supervisor": "Supervisor",
"consultant": "Consultant",
"study_programme": "Study programme",
"study_branch": "Study branch",
"bp": "Bachelor thesis",
"dp": "Diploma thesis",
"dis": "Dissertation thesis",
"city": "Liberec",
"toc": "Contents",
"disclaimer": "Declaration",
"disclaimer_bp": "I hereby certify, I, myself, have written my bachelor thesis as an original and primary work using the literature listed below and consulting it with my thesis supervisor and my thesis counsellor.\n\nI acknowledge that my bachelor thesis is fully governed by Act No. 121/2000 Coll., the Copyright Act, in particular Article 60 School Work.\n\nI acknowledge that the Technical University of Liberec does not infringe my copyrights by using my bachelor thesis for internal purposes of the Technical University of Liberec.\n\nI am aware of my obligation to inform the Technical University of Liberec on having used or granted license to use the results of my bachelor thesis; in such a case the Technical University of Liberec may require reimbursement of the costs incurred for creating the result up to their actual amount.\n\nAt the same time, I honestly declare that the text of the printed version of my bachelor thesis is identical with the text of the electronic version uploaded into the IS STAG.\n\nI acknowledge that the Technical University of Liberec will make my bachelor thesis public in accordance with paragraph 47b of Act No. 111/1998 Coll., on Higher Education Institutions and on Amendment to Other Acts (the Higher Education Act), as amended.\n\nI am aware of the consequences which may under the Higher Education Act result from a breach of this declaration.",
"disclaimer_content": "{g:I|We} hereby certify, {g:I|we}, {g:myself|ourselves}, have written {g:my|our} {thesis} as an original and primary work using the literature listed below and consulting it with {g:my|our} thesis supervisor and {g:my|our} thesis counsellor.\n\n{g:I|We} acknowledge that {g:my|our} {thesis} is fully governed by Act No. 121/2000 Coll., the Copyright Act, in particular Article 60 School Work.\n\n{g:I|We} acknowledge that the Technical University of Liberec does not infringe {g:my|our} copyrights by using {g:my|our} {thesis} for internal purposes of the Technical University of Liberec.\n\n{g:I|We} {g:am|are} aware of {g:my|our} obligation to inform the Technical University of Liberec on having used or granted license to use the results of {g:my|our} {thesis}; in such a case the Technical University of Liberec may require reimbursement of the costs incurred for creating the result up to their actual amount.\n\nAt the same time, {g:I|we} honestly declare that the text of the printed version of {g:my|our} {thesis} is identical with the text of the electronic version uploaded into the IS STAG.\n\n{g:I|We} acknowledge that the Technical University of Liberec will make {g:my|our} {thesis} public in accordance with paragraph 47b of Act No. 111/1998 Coll., on Higher Education Institutions and on Amendment to Other Acts (the Higher Education Act), as amended.\n\n{g:I|We} {g:am|are} aware of the consequences which may under the Higher Education Act result from a breach of this declaration.",
"disclaimer_replace": {
"bp": {
"thesis": "bachelor thesis"
}
},
"date": "[year]-[month]-[day]",
"abstract": "Abstract",
"keywords": "Keywords",
"abbrs": "List of abbreviations",
"image_list": "List of images",
"table_list": "List of tables",
"attachments": "Attachments",
"attachment": "Attachment",
"next_page_attachment": "begins on the next page",
"attached_bellow": "attached bellow",
"place_assignment": "Insert your assignment here"
}

View File

@@ -1,4 +1,4 @@
#import "utils.typ": assert_in_dict
#import "utils.typ": assert_in_dict, assert_in_arr, map_none, ok_or
#let lang_ids = (
cs: 0,
@@ -21,16 +21,37 @@
return lang_items.at(lang_abbr).at(item_name);
}
#let replace_czech_gender(raw, gender) = {
let genders = (
feminine: 1,
masculine: 0,
we: 2,
);
assert_in_dict(gender, genders, "author gender");
raw.replace(regex("\{g:([^|]*)\|([^|]*)\|([^}]*)\}"), (match) => {
match.captures.at(genders.at(gender))
});
}
#let replace_english_pronounce(raw, pronounce) = {
let pronounce = ok_or(pronounce, "me");
let pronouns = (
me: 0,
we: 1,
);
assert_in_dict(pronounce, pronouns, "author gender");
raw.replace(regex("\{g:([^|]*)\|([^}]*)\}"), (match) => {
match.captures.at(pronouns.at(pronounce))
});
}
#let disclaimer(language, document_type, author_gender) = {
let disclaimer = get_lang_item(language, "disclaimer_content");
let replacements = get_lang_item(language, "disclaimer_replace").at(document_type);
if language == "cs" {
let gender_transforms = (
male: "",
female: "a",
);
assert_in_dict(author_gender, gender_transforms, "author gender");
disclaimer = disclaimer.replace("{a}", gender_transforms.at(author_gender));
disclaimer = replace_czech_gender(disclaimer, author_gender);
} else if language == "en" {
disclaimer = replace_english_pronounce(disclaimer, author_gender);
}
for (key, value) in replacements.pairs() {
disclaimer = disclaimer.replace("{" + key + "}", value);

View File

@@ -7,6 +7,9 @@
// Git: https://git.zumepro.cz/tul/tultemplate2
#import "prototyping.typ": todo, profile
#import "attachments.typ": (
attachments, attach_content, attach_pdf, attach_link, attach_file_reference
)
// TUL Template 2
//
@@ -22,16 +25,14 @@
// - style (str): Visual style to use. This can be "classic".
// - faculty (str): Factulty abbreviation. One of "fs", "ft", "fp", "ef", "fua", "fm", "fzs", "cxi".
// - lang (str): Language code. This can be "cs" or "en".
// - document (str): Type of document. This can be "bp", "dp", "ds".
// - title_cs (str): The title (Czech) of the document.
// - document (str): Type of document. This can be "bp" or "other".
// - title (dictionary): The title of the document.
// - author (str): The name of the document's author.
// - author_gender (str): The gender of the document's author. Needed only for the `cs` language.
// - supervisor (str): The name of the document's supervisor.
// - programme (str): Study programme.
// - abstract_cs (content): The abstract (Czech).
// - keywords_cs (array): The abstract keywords (Czech).
// - title_en (str): The title (English) of the document.
// - abstract_en (content): The abstract (English).
// - keywords_en (array): The abstract keywords (English).
// - programme (dictionary): Study programme.
// - abstract (dictionary): The abstract.
// - keywords (dictionary): The abstract keywords.
// - assignment (str): Filepath of the assignment document/page.
// - citations (str): The location of the citation file.
// - content (content): The content of the document
@@ -43,7 +44,7 @@
// document info
title: none, keywords: none, abstract: none, author: none, author_gender: none,
supervisor: none, programme: none,
supervisor: none, consultant: none, programme: none, branch: none,
// links
assignment: none, citations: "citations.bib",
@@ -60,13 +61,17 @@
assert_type_signature(document, "string | none", "document kind argument");
assert_type_signature(title, "dictionary[string : string] | none", "title argument");
assert_type_signature(keywords, "dictionary[string : array[string]] | none", "keywords argument");
assert_type_signature(abstract, "dictionary[string : string] | none", "abstract argument");
assert_type_signature(
abstract, "dictionary[string : string | content] | none", "abstract argument"
);
assert_type_signature(author, "string | none", "author argument");
assert_type_signature(author_gender, "string | none", "author gender argument");
assert_type_signature(supervisor, "string | none", "supervisor argument");
assert_type_signature(consultant, "string | none", "consultant argument");
assert_type_signature(
programme, "dictionary[string : string] | none", "study programme argument"
);
assert_type_signature(branch, "dictionary[string : string] | none", "study branch argument");
assert_type_signature(assignment, "string | none", "assignment document argument");
assert_type_signature(citations, "string", "citations file argument");
@@ -85,8 +90,8 @@
// template call
templates.at(style)(
lang, faculty, document, citations, assignment,
title, author, author_gender, supervisor, programme, abstract, keywords,
content
title, author, author_gender, supervisor, consultant,
programme, branch, abstract, keywords, content
);
import "prototyping.typ": assert_release_ready

View File

@@ -1,7 +1,7 @@
<?xml version="1.0" encoding="utf-8"?>
<style xmlns="http://purl.org/net/xbiblio/csl" class="in-text" version="1.0" demote-non-dropping-particle="never" default-locale="en-US">
<info>
<title>ISO-690 (numeric, Czech)</title>
<title>TUL ISO-690</title>
<id>-----</id>
<link href="" rel="self"/>
<link href="" rel="documentation"/>
@@ -264,7 +264,7 @@
<group>
<text term="retrieved" suffix=" " text-case="capitalize-first"/>
<text term="from" suffix=": "/>
<text variable="URL"/>
<text variable="URL" suffix=" "/>
</group>
</if>
</choose>

View File

@@ -0,0 +1,40 @@
@article{Wang2025,
author = {Wang, Erming and Yu, Kaiwen and Cao, Jiqing and Wang, Minghui and Katsel, Pavel and Song, Won-min and Wang, Zhen and Li, Yuxin and Wang, Xusheng and Wang, Qian and Xu, Peng and Yu, Gefei and Zhu, Li and Geng, Jia and Habibi, Parnian and Qian, Lu and Tuck, Tony and Li, Aiqun and TCW, Julia and Roussos, Panos and Brennand, Kristen J. and Haroutunian, Vahram and Johnson, Erik C.B. and Seyfried, Nicholas T. and Levey, Allan I. and Bennett, David A. and Peng, Junmin and Cai, Dongming and Zhang, Bin},
title = {Multiscale proteomic modeling reveals protein networks driving Alzheimers disease pathogenesis},
journal = {Cell},
year = {2025},
volume = {},
number = {},
pages = {},
publisher = {Elsevier},
doi = {10.1016/j.cell.2025.08.038},
url = {https://doi.org/10.1016/j.cell.2025.08.038},
issn = {0092-8674}
}
@misc{csl,
title = {Citation Style Language},
year = {2025},
medium = {online},
accessed = {2025-06-10},
URL = {https://citationstyles.org/},
}
@misc{linux,
journal = {Blog | Linux Foundation},
title = {Classic SysAdmin: Vim 101: A Beginners Guide to Vim},
year = {2025},
medium = {online},
accessed = {2025-06-10},
URL = {https://www.linuxfoundation.org/blog/blog/classic-sysadmin-vim-101-a-beginners-guide-to-vim},
}
@book{Satrapa2011,
author = {Pavel Satrapa},
title = {IPv6},
publisher = {Edice CZ.NIC},
year = {2011},
edition = {3. vydání},
ISBN = {978-80-904248-4-9},
URL = {https://www.bookport.cz/kniha/ipv6-treti-vydani-5999/},
}

View File

@@ -1,4 +1,7 @@
// todo: add citations
@Wang2025
@csl
@linux
@Satrapa2011
#pagebreak(weak: true)
#set text(lang: "cs")
#bibliography("citations.bib", title: "Bibliography - CZ", style: "../template/tul_citace.csl")

6
tests/citations_en.typ Normal file
View File

@@ -0,0 +1,6 @@
@Wang2025
@csl
@linux
@Satrapa2011
#bibliography("citations.bib", title: "Bibliography - EN", style: "iso-690-numeric")