#import "@preview/polylux:0.3.1": themes, logic, utils // #import "../logic.typ" // #import "../utils/utils.typ" // HEIG-VD Y-Sec slides theme // Derived from "University theme" https://github.com/andreasKroepelin/typst-slides #let uni-colors = state("uni-colors", (:)) #let uni-short-title = state("uni-short-title", none) #let uni-short-author = state("uni-short-author", none) #let uni-short-date = state("uni-short-date", none) #let uni-progress-bar = state("uni-progress-bar", true) #let ysec-theme( aspect-ratio: "16-9", short-title: none, short-author: none, short-date: none, color-a: rgb("#E1251B"), color-b: rgb("#444444"), color-c: rgb("#EEEEEE"), progress-bar: true, body ) = { set page( paper: "presentation-" + aspect-ratio, margin: 0em, header: none, footer: none, ) set text(font: "Carlito", size: 25pt) show footnote.entry: set text(size: .6em) uni-progress-bar.update(progress-bar) uni-colors.update((a: color-a, b: color-b, c: color-c)) uni-short-title.update(short-title) uni-short-author.update(short-author) uni-short-date.update(short-date) body } #let title-slide( title: [], subtitle: none, authors: (), institution-name: none, date: none, logo: none, ) = { let authors = if type(authors) == "array" { authors } else { (authors,) } let content = locate( loc => { let colors = uni-colors.at(loc) if logo != none { align(right, logo) } align(center + horizon, { block( inset: 0em, breakable: false, { text(size: 2em, fill: colors.a, strong(title)) if subtitle != none { parbreak() text(size: 1.2em, fill: colors.a, subtitle) } } ) set text(size: .8em) grid( columns: (1fr,) * calc.min(authors.len(), 3), column-gutter: 1em, row-gutter: 1em, ..authors.map(author => text(fill: black, author)) ) v(1em) if institution-name != none { parbreak() text(size: .9em, institution-name) } if date != none { parbreak() text(size: .8em, date) } }) }) logic.polylux-slide(content) } #let slide( title: none, header: none, footer: none, new-section: none, body ) = { let body = pad(x: 2em, y: .5em, body) let progress-barline = locate( loc => { if uni-progress-bar.at(loc) { let cell = block.with( width: 100%, height: 100%, above: 0pt, below: 0pt, breakable: false ) let colors = uni-colors.at(loc) utils.polylux-progress( ratio => { grid( rows: 2pt, columns: (ratio * 100%, 1fr), cell(fill: colors.a), cell(fill: colors.b) ) }) } else { [] } }) let header-text = { if header != none { header } else if title != none { if new-section != none { utils.register-section(new-section) } locate( loc => { let colors = uni-colors.at(loc) block(fill: colors.c, inset: (x: .5em), grid( columns: (60%, 40%), align(top + left, heading(level: 2, text(fill: colors.a, title))), align(top + right, text(fill: colors.a.lighten(65%), utils.current-section)) )) }) } else { [] } } let header = { set align(top) grid(rows: (auto, auto), row-gutter: 3mm, progress-barline, header-text) } let footer = { set text(size: 10pt) set align(center + bottom) let cell(fill: none, it) = rect( width: 100%, height: 100%, inset: 1mm, outset: 0mm, fill: fill, stroke: none, align(horizon, text(fill: white, it)) ) if footer != none { footer } else { locate( loc => { let colors = uni-colors.at(loc) show: block.with(width: 100%, height: auto, fill: colors.b) grid( columns: (25%, 1fr, 15%, 10%), rows: (1.5em, auto), cell(fill: colors.a, uni-short-author.display()), cell(uni-short-title.display()), cell(uni-short-date.display()), cell(logic.logical-slide.display() + [~/~] + utils.last-slide-number) ) }) } } set page( margin: ( top: 2em, bottom: 1em, x: 0em ), header: header, footer: footer, footer-descent: 0em, header-ascent: .6em, ) logic.polylux-slide(body) } #let focus-slide(background-color: none, background-img: none, body) = { let background-color = if background-img == none and background-color == none { rgb("#0C6291") } else { background-color } set page(fill: background-color, margin: 1em) if background-color != none set page( background: { set image(fit: "stretch", width: 100%, height: 100%) background-img }, margin: 1em, ) if background-img != none set text(fill: white, size: 2em) logic.polylux-slide(align(horizon, body)) } #let matrix-slide(columns: none, rows: none, ..bodies) = { let bodies = bodies.pos() let columns = if type(columns) == "integer" { (1fr,) * columns } else if columns == none { (1fr,) * bodies.len() } else { columns } let num-cols = columns.len() let rows = if type(rows) == "integer" { (1fr,) * rows } else if rows == none { let quotient = calc.quo(bodies.len(), num-cols) let correction = if calc.rem(bodies.len(), num-cols) == 0 { 0 } else { 1 } (1fr,) * (quotient + correction) } else { rows } let num-rows = rows.len() if num-rows * num-cols < bodies.len() { panic("number of rows (" + str(num-rows) + ") * number of columns (" + str(num-cols) + ") must at least be number of content arguments (" + str(bodies.len()) + ")") } let cart-idx(i) = (calc.quo(i, num-cols), calc.rem(i, num-cols)) let color-body(idx-body) = { let (idx, body) = idx-body let (row, col) = cart-idx(idx) let color = if calc.even(row + col) { white } else { silver } set align(center + horizon) rect(inset: .5em, width: 100%, height: 100%, fill: color, body) } let content = grid( columns: columns, rows: rows, gutter: 0pt, ..bodies.enumerate().map(color-body) ) logic.polylux-slide(content) } #let heig-logo = block( inset: 10pt, image("logo.svg", alt: "HEIG-VD", fit: "contain", width: 40%) ) #let note(color: gray, contents) = align(center, block(radius: 0.7em, fill: color.lighten(30%), inset: 0.5em, contents)) #let danger-sign = polygon.regular( fill: red.darken(40%), size: 2.5em, vertices: 3, ) + place(center, dy: -1em, text(fill: red.lighten(30%), "!") ) #let danger(contents) = note(color: red, grid(columns: (auto, auto), gutter: 0.5em, danger-sign, contents)) #let qmark = circle(text(size: 1.5em, fill: blue.lighten(30%), "?"), fill: blue.darken(50%)) #let question(contents) = note(color: blue, grid(columns: (auto, auto), gutter: 0.5em, qmark, contents)) #let section-slide(contents) = { set text(size: 48pt); themes.university.slide(align(center, contents)) } #let codeframe(title: none, body) = { let stroke = black + 1pt let radius = 5pt box(stroke: stroke, radius: radius)[ #if title != none { block( stroke: stroke, inset: 0.5em, below: 0em, radius: (top-left: radius, bottom-right: radius), title, ) } #block( width: 100%, inset: (rest: 0.5em), body, ) ] }