Created: February 9, 2019

Last modified: July 23, 2025

configuration for this website

This is the entire configuration for this website including the css styling and org-publish configuration. The features this website supports can be seen here.

Website CSS

Doom One Dark Theme

https://github.com/doomemacs/themes

@media (prefers-color-scheme: dark) {
    :root {
        --bg        : #282c34;
        --fg        : #bbc2cf;
        --bg-alt    : #21242b;
        --fg-alt    : #5B6268;
        --base0     : #1B2229;
        --base1     : #1c1f24;
        --base2     : #202328;
        --base3     : #23272e;
        --base4     : #3f444a;
        --base5     : #5B6268;
        --base6     : #73797e;
        --base7     : #9ca0a4;
        --base8     : #DFDFDF;
        --grey      : #3f444a;
        --red       : #ff6c6b;
        --i-red     : #ce537a;
        --orange    : #da8548;
        --green     : #98be65;
        --i-green   : #2d9574;
        --teal      : #4db5bd;
        --yellow    : #ECBE7B;
        --blue      : #51afef;
        --dark-blue : #2257A0;
        --magenta   : #c678dd;
        --violet    : #a9a1e1;
        --cyan      : #46D9FF;
        --dark-cyan : #5699AF;
    }
}

Doom One Light Theme

@media (prefers-color-scheme: light) {
    :root {
        --bg        : #fafafa;
        --fg        : #383a42;
        --bg-alt    : #f0f0f0;
        --fg-alt    : #c6c7c7;
        --base0     : #f0f0f0;
        --base1     : #e7e7e7;
        --base2     : #dfdfdf;
        --base3     : #c6c7c7;
        --base4     : #9ca0a4;
        --base5     : #383a42;
        --base6     : #202328;
        --base7     : #1c1f24;
        --base8     : #1b2229;
        --grey      : #9ca0a4;
        --red       : #e45649;
        --i-red     : #e45649;
        --orange    : #da8548;
        --green     : #50a14f;
        --i-green   : #50a14f;
        --teal      : #4db5bd;
        --yellow    : #986801;
        --blue      : #4078f2;
        --dark-blue : #a0bcf8;
        --magenta   : #a626a4;
        --violet    : #b751b6;
        --cyan      : #0184bc;
        --dark-cyan : #005478;
    }
}

elements

Much of this is from org-html-style-default

h1 {
  font-size: 32px;
  font-weight: bold;
}

body {
  font-family: "Fira Sans", sans-serif;
  color: var(--fg);
  background-color: var(--bg);
  max-width: 42em;
  margin: auto;
}

#preamble {
  text-align: center;
}
#postamble {
  text-align: center;
  margin: 2em;
}
#postamble p, #preamble p {
  font-size: 90%;
  margin: .2em;
}

p { line-height: 1.5; }
p.verse { margin-left: 3%; }
a {
  color: var(--blue);
  background-color: inherit;
  font: inherit;
  text-decoration: inherit;
}
a:hover {
  text-decoration: underline;
}
ul {
    line-height: 1.5;
}
.title  {
  text-align: center;
  margin-bottom: .2em;
}
.subtitle {
  text-align: center;
  font-size: medium;
  font-weight: bold;
  margin-top:0;
}
.todo   { font-family: monospace; color: red; }
.done   { font-family: monospace; color: green; }
.priority { font-family: monospace; color: orange; }
.tag    { background-color: #eee; font-family: monospace;
          padding: 2px; font-size: 80%; font-weight: normal; }
.timestamp { color: var(--fg-alt); }
.timestamp-kwd { color: var(--dark-cyan); }
.org-right  { margin-left: auto; margin-right: 0px;  text-align: right; }
.org-left   { margin-left: 0px;  margin-right: auto; text-align: left; }
.org-center { margin-left: auto; margin-right: auto; text-align: center; }
.underline { text-decoration: underline; }
table { border-collapse:collapse; }
caption.t-above { caption-side: top; }
caption.t-bottom { caption-side: bottom; }
td, th { vertical-align:top;  }
th.org-right  { text-align: center;  }
th.org-left   { text-align: center;   }
th.org-center { text-align: center; }
td.org-right  { text-align: right;  }
td.org-left   { text-align: left;   }
td.org-center { text-align: center; }
dt { font-weight: bold; }
.footpara { display: inline; }
.footdef  { margin-bottom: 1em; }
.figure { padding: 1em; }
.figure p { text-align: center; }
.footnotes { text-transform: lowercase; }
.equation-container {
  display: table;
  text-align: center;
  width: 100%;
}
.equation {
  vertical-align: middle;
}
.equation-label {
  display: table-cell;
  text-align: right;
  vertical-align: middle;
}
.inlinetask {
  padding: 10px;
  border: 2px solid gray;
  margin: 10px;
  background: #ffffcc;
}
#org-div-home-and-up
{ text-align: right; font-size: 70%; white-space: nowrap; }
textarea { overflow-x: auto; }
.linenr { font-size: smaller }
.code-highlighted { background-color: #ffff00; }
.org-info-js_info-navigation { border-style: none; }
#org-info-js_console-label
{ font-size: 10px; font-weight: bold; white-space: nowrap; }
.org-info-js_search-highlight
{ background-color: #ffff00; color: #000000; font-weight: bold; }
.org-svg { width: 90%; }
.org-src-container { }
.org-ul {}

.menu {
  display: inline-block;
  padding: 0.2em;
  position: relative;
  background-color: var(--base0);
  border-radius: 0.2em;
}
button {
  border: none;
  background-color: inherit;
  font-size: inherit;
  font: inherit;
  cursor: pointer;
  color: var(--blue);
}
button:hover {
  text-decoration: underline;
}

.menu-btn {
  display: inline-block;
  width: 6em;
  transition: all 0.2s ease;
  color: var(--fg);
  padding: 0.3em;
  margin: 0.2em;
  border-radius: 0.2em;
  border: 2px solid var(--magenta);
  fill: var(--fg);
}
.menu-btn:hover {
  background-color: var(--magenta);
  color: var(--base0);
  fill: var(--base0);
}

org classes

.org-builtin {color: var(--magenta);}
.org-comment {color: var(--fg-alt);}
.org-comment-delimiter {color: var(--fg-alt);}
.org-constant {color: var(--violet);}
.org-css-property {color: var(--green);}
.org-css-selector {color: var(--blue);}
.org-doc {color: #83898d;}
.org-font-latex-bold {font-weight: bold;}
.org-font-latex-math {color: var(--green);}
.org-font-latex-script-char {color: var(--dark-blue);}
.org-font-latex-sedate {color: #d3d3d3;}
.org-function-name {color: var(--magenta);}
.org-keyword {color: var(--blue);}
.org-operator {}
.org-whitespace-line {
  color: var(--red);
  background-color: var(--base0);
  font-weight: bold;
}
.org-negation-char {
  color: var(--blue);
  font-weight: bold;
}
.org-org-block {
  background-color: var(--base3);
}
.org-org-block-begin-line {
  color: var(--fg-alt);
  background-color: var(--base3);
}
.org-org-block-end-line {
  color: var(--fg-alt);
  background-color: var(--base3);
}
.org-org-meta-line {color: #83898d;}
.org-org-target {text-decoration: underline;}
.org-rainbow-delimiters-depth-1 {color: var(--blue);}
.org-rainbow-delimiters-depth-2 {color: var(--magenta);}
.org-rainbow-delimiters-depth-3 {color: var(--green);}
.org-rainbow-delimiters-depth-4 {color: var(--violet);}
.org-rainbow-delimiters-depth-5 {color: var(--teal);}
.org-rainbow-delimiters-depth-6 {color: var(--blue);}
.org-rainbow-delimiters-depth-7 {color: var(--magenta);}
.org-rainbow-delimiters-depth-8 {color: var(--green);}
.org-rainbow-delimiters-depth-9 {color: var(--violet);}
.org-regexp-grouping-backslash {
  color: var(--blue);
  font-weight: bold;
}
.org-regexp-grouping-construct {
  color: var(--blue);
  font-weight: bold;
}
.org-sh-heredoc {color: var(--green);}
.org-sh-quoted-exec {
  color: var(--blue);
  font-weight: bold;
}
.org-string {color: var(--green);}
.org-type {color: var(--yellow);}
.org-variable-name {color: #dcaeea;}
.org-warning {color: var(--yellow);}
.org-diff-added {
  color: var(--green);
  background-color: var(--bg-alt);
}
.org-diff-changed {
  color: var(--violet);
}
.org-diff-changed-unspecified {
  color: var(--violet);
  background-color: #333333;
}
.org-diff-context {}
.org-diff-error {
  color: #ff0000;
  background-color: #000000;
  font-weight: bold;
}
.org-diff-file-header {color: var(--blue);}
.org-diff-function {color: var(--cyan);}
.org-diff-header {color: var(--cyan);}
.org-diff-hunk-header {color: var(--violet);}
.org-diff-index {color: var(--blue);}
.org-diff-indicator-added {
  color: #22aa22;
  background-color: var(--bg-alt);
}
.org-diff-indicator-changed {color: #aaaa22;}
.org-diff-indicator-removed {
  color: #aa2222;
  background-color: var(--base3);
}
.org-diff-nonexistent {color: var(--blue);}
.org-diff-refine-added {
  color: var(--green);
  background-color: var(--bg-alt);
}
.org-diff-refine-changed {color: var(--violet);}
.org-diff-refine-removed {
  color: var(--red);
  background-color: var(--base3);
}
.org-diff-removed {
  color: var(--red);
  background-color: var(--base3);
}

Source Code

pre {
  border: 1px solid #e6e6e6;
  border-radius: 3px;
  padding: 8pt;
  font-family: monospace;
  overflow: auto;
  margin: 1.2em;
}
pre.src {
  position: relative;
  overflow: auto;
}
pre.src:before {
  display: none;
  position: absolute;
  top: -8px;
  right: 12px;
  padding: 3px;
  color: #555;
  background-color: #f2f2f299;
}
pre.src:hover:before { display: inline; margin-top: 14px;}
pre.src-C:before { content: 'C'; }
pre.src-css:before { content: 'CSS'; }
pre.src-dot:before { content: 'Graphviz'; }
pre.src-calc:before { content: 'Emacs Calc'; }
pre.src-emacs-lisp:before { content: 'Emacs Lisp'; }
pre.src-elisp:before { content: 'Emacs Lisp'; }
pre.src-fortran:before { content: 'Fortran'; }
pre.src-haskell:before { content: 'Haskell'; }
pre.src-js:before { content: 'Javascript'; }
pre.src-latex:before { content: 'LaTeX'; }
pre.src-lisp:before { content: 'Lisp'; }
pre.src-lua:before { content: 'Lua'; }
pre.src-org:before { content: 'Org mode'; }
pre.src-python:before { content: 'Python'; }
pre.src-jupyter-python:before { content: 'Jupyter Python'; }
pre.src-jupyter-julia:before { content: 'Jupyter Julia'; }
pre.src-ruby:before { content: 'Ruby'; }
pre.src-scheme:before { content: 'Scheme'; }
pre.src-sed:before { content: 'Sed'; }
pre.src-sh:before { content: 'shell'; }
pre.src-makefile:before { content: 'Makefile'; }
pre.src-perl:before { content: 'Perl'; }
pre.src-shell:before { content: 'Shell Script'; }
pre.src-cpp:before  { content: 'C++'; }
pre.src-bash:before  { content: 'bash'; }
pre.src-html:before { content: 'HTML'; }
pre.src-prolog:before { content: 'Prolog'; }
pre.src-tex:before { content: 'TeX'; }
pre.src-plain-tex:before { content: 'Plain TeX'; }
pre.src-conf:before { content: 'Configuration File'; }

Reveal.js CSS

main styles

html, body, div, span, applet, object, iframe,
h1, h2, h3, h4, h5, h6, p, blockquote, pre,
a, abbr, acronym, address, big, cite, code,
del, dfn, em, img, ins, kbd, q, s, samp,
small, strike, strong, sub, sup, tt, var,
b, u, i, center,
dl, dt, dd, ol, ul, li,
fieldset, form, label, legend,
table, caption, tbody, tfoot, thead, tr, th, td,
article, aside, canvas, details, embed,
figure, figcaption, footer, header, hgroup,
main, menu, nav, output, ruby, section, summary,
time, mark, audio, video {
  margin: 0;
  padding: 0;
  border: 0;
  font-size: 100%;
  font: inherit;
  vertical-align: baseline;
}

.org-svg {
  width: 100%;
  /*transform-origin: top left;*/
}
.org-right  { margin-left: auto; margin-right: 0px;  text-align: right; }
.org-left   { margin-left: 0px;  margin-right: auto; text-align: left; }
.org-center { margin-left: auto; margin-right: auto; text-align: center; }

.header-quote {
  display: inline-block;
  vertical-align: middle;
  font-size: 30pt;
  font-style: italic;
  text-align: left;
  padding-left: 74px;
}

.no-display { display: none; }

.abspos { position: absolute; }

.csl-bib-body {
  font-size: 14pt;
}

.reveal {
  position:relative;
  width:100%;
  height:100%;
  overflow:hidden;
  touch-action:pinch-zoom;
  font-family: "Fira Sans", sans-serif;
  font-size: 32pt;
  font-weight: normal;
}
.reveal .slides {
  position:absolute;
  width:100%;
  height:100%;
  top:0;
  right:0;
  bottom:0;
  left:0;
  margin:auto;
  pointer-events:none;
  overflow:visible;
  z-index:1;
  text-align:center;
  perspective:600px;
  perspective-origin:50% 40%
}
html.reveal-full-page {
  width:100%;
  height:100%;
  height:100vh;
  height:calc(var(--vh,1vh) * 100);
  height:100dvh;
  overflow:hidden
}
.reveal-viewport {
  height:100%;
  overflow:hidden;
  position:relative;
  line-height:1;
  margin:0;
}
.content {
  background: #fff;
  background-color: #fafafa;
  color:#000;
}
.reveal-viewport:fullscreen {
  top:0!important;
  left:0!important;
  width:100%!important;
  height:100%!important;
  transform:none!important
}

section.has-dark-background, section.has-dark-background h1, section.has-dark-background h2, section.has-dark-background h3, section.has-dark-background h4, section.has-dark-background h5, section.has-dark-background h6 {
  color: #fff;
}

.reveal ::selection {
  color:  #fff;
  background: #98bdef;
  text-shadow: none;
}
.reveal .slides section,
.reveal .slides section > section {
  line-height: 1.3;
  font-weight: inherit;
}

.reveal h1,
.reveal h2,
.reveal h3,
.reveal h4,
.reveal h5,
.reveal h6 {
  margin: 0 0 20px 0;
  color: #000;
  font-weight: 450;
  line-height: 1.2;
  letter-spacing: normal;
  text-transform: none;
  text-shadow: none;
  word-wrap: break-word;

  font-size: 50pt;
  /*text-align: left;*/
  background-color: #613583FF;
  color: #FFFFFF;
  padding-top: 20px;
  padding-bottom: 10px;
}

.reveal p {
  margin: 10px 0;
  line-height: 1.2;
}
/* Remove trailing margins after titles */
.reveal h1:last-child,
.reveal h2:last-child,
.reveal h3:last-child,
.reveal h4:last-child,
.reveal h5:last-child,
.reveal h6:last-child {
  margin-bottom: 0;
}
/* Ensure certain elements are never larger than the slide itself */
.reveal img,
.reveal video,
.reveal iframe {
  max-width: 95%;
  max-height: 95%;
  margin: 10px;
}
.reveal strong,
.reveal b {
  font-weight: bold;
}
.reveal em,
.reveal i {
  font-style: italic;
}
.reveal ol,
.reveal dl,
.reveal ul {
  display: inline-block;
  text-align: left;
  margin: 0 0 0 1em;
}
.reveal ol {
  list-style-type: decimal;
}
.reveal ul {
  list-style-type: disc;
}
.reveal ul ul {
  list-style-type: square;
}
.reveal ul ul ul {
  list-style-type: circle;
}
.reveal ul ul,
.reveal ul ol,
.reveal ol ol,
.reveal ol ul {
  display: block;
  margin-left: 40px;
}
.reveal dt {
  font-weight: bold;
}
.reveal dd {
  margin-left: 40px;
}
.reveal blockquote {
  display: block;
  position: relative;
  width: 70%;
  margin: 20px auto;
  padding: 5px;
  font-style: italic;
  background: rgba(255, 255, 255, 0.05);
  box-shadow: 0px 0px 2px rgba(0, 0, 0, 0.2);
}
.reveal blockquote p:first-child,
.reveal blockquote p:last-child {
  display: inline-block;
}
.reveal q {
  font-style: italic;
}
.reveal pre {
  display: block;
  position: relative;
  width: 90%;
  margin: 20px auto;
  text-align: left;
  font-size: 0.55em;
  font-family: monospace;
  line-height: 1.2em;
  word-wrap: break-word;
  box-shadow: 0px 5px 15px rgba(0, 0, 0, 0.15);
}
.reveal code {
  font-family: monospace;
  text-transform: none;
  tab-size: 2;
}
.reveal pre code {
  display: block;
  padding: 5px;
  overflow: auto;
  max-height: 400px;
  word-wrap: normal;
}
.reveal .code-wrapper {
  white-space: normal;
}
.reveal .code-wrapper code {
  white-space: pre;
}
/*
.reveal table {
  margin: auto;
  border-collapse: collapse;
  border-spacing: 0;
}
.reveal table th {
  font-weight: bold;
}
.reveal table th,
.reveal table td {
  text-align: left;
  padding: 0.2em 0.5em 0.2em 0.5em;
  border-bottom: 1px solid;
}
.reveal table th[align=center],
.reveal table td[align=center] {
  text-align: center;
}
.reveal table th[align=right],
.reveal table td[align=right] {
  text-align: right;
}
.reveal table tbody tr:last-child th,
.reveal table tbody tr:last-child td {
  border-bottom: none;
}
*/
.reveal table td {
  /*padding: 0px 15px;*/
  vertical-align: center;
}
.reveal a {
  color: #5F5F5F;
  text-decoration: none;
}
.reveal a:visited {
  color: #5F5F5F;
  text-decoration: none;
}
.reveal a:hover {
  color: #2a76dd;
  text-shadow: none;
  border: none;
}
.reveal iframe {
  z-index:1
}
.reveal .progress {
  position:absolute;
  display:none;
  height:5px;
  width:100%;
  bottom:0;
  left:0;
  z-index:10;
  background: rgba(0, 0, 0, 0.2);
  background-color:rgba(0,0,0,.2);
  color: #613583FF;
}
.reveal .progress:after {
  content:"";
  display:block;
  position:absolute;
  height:10px;
  width:100%;
  top:-10px
}
.reveal .progress span {
  display:block;
  height:100%;
  width:100%;
  background-color:currentColor;
  transition:transform .8s cubic-bezier(.26,.86,.44,.985);
  transform-origin:0 0;
  transform:scaleX(0)
}
.reveal .slide-number {
  position:absolute;
  display:block;
  right:20px;
  bottom:24px;
  font-size:22pt;
  line-height:1;
  color:#000;
  /*
  z-index:1;
  font-weight: bold;
  padding:8px;
  color:#fff;
  background-color:rgba(0,0,0,.4);
  */
}
.reveal .slide-number a {
  color:currentColor
}
.reveal .slide-number-delimiter {
  margin:0 3px
}
.reveal.embedded {
  touch-action:pan-y
}
.reveal.embedded.is-vertical-slide {
  touch-action:none
}

fragments

.reveal .fragment {
/*  transition:all .2s ease */
}
.reveal .fragment:not(.custom) {
  opacity:0;
  visibility:hidden;
  will-change:opacity
}
.reveal .fragment.visible {
  opacity:1;
  visibility:inherit
}
.reveal .fragment.disabled {
  transition:none
}
.reveal .fragment.fade-out {
  opacity:1;
  visibility:inherit
}
.reveal .fragment.fade-out.visible {
  opacity:0;
  visibility:hidden
}
.reveal .fragment.semi-fade-out {
  opacity:1;
  visibility:inherit
}
.reveal .fragment.semi-fade-out.visible {
  opacity:.5;
  visibility:inherit
}
.reveal .fragment.strike {
  opacity:1;
  visibility:inherit
}
.reveal .fragment.strike.visible {
  text-decoration:line-through
}
.reveal .fragment.current-visible,
.reveal .fragment.fade-in-then-out {
  opacity:0;
  visibility:hidden
}
.reveal .fragment.current-visible.current-fragment,
.reveal .fragment.fade-in-then-out.current-fragment {
  opacity:1;
  visibility:inherit
}
.reveal .fragment.fade-in-then-semi-out {
  opacity:0;
  visibility:hidden
}
.reveal .fragment.fade-in-then-semi-out.visible {
  opacity:.5;
  visibility:inherit
}
.reveal .fragment.fade-in-then-semi-out.current-fragment {
  opacity:1;
  visibility:inherit
}
.reveal .fragment.highlight-blue,
.reveal .fragment.highlight-current-blue,
.reveal .fragment.highlight-current-green,
.reveal .fragment.highlight-current-red,
.reveal .fragment.highlight-green,
.reveal .fragment.highlight-red {
  opacity:1;
  visibility:inherit
}
.reveal .fragment.highlight-red.visible {
  color:#ff2c2d
}
.reveal .fragment.highlight-green.visible {
  color:#17ff2e
}
.reveal .fragment.highlight-blue.visible {
  color:#1b91ff
}
.reveal .fragment.highlight-current-red.current-fragment {
  color:#ff2c2d
}
.reveal .fragment.highlight-current-green.current-fragment {
  color:#17ff2e
}
.reveal .fragment.highlight-current-blue.current-fragment {
  color:#1b91ff
}

animation

.reveal .slides>section {
  perspective:600px
}
.reveal .slides>section,
.reveal .slides>section>section {
  display:none;
  position:absolute;
  width:100%;
  pointer-events:auto;
  z-index:10;
  transform-style:flat;
  transition:transform-origin .8s cubic-bezier(.26,.86,.44,.985),transform .8s cubic-bezier(.26,.86,.44,.985),visibility .8s cubic-bezier(.26,.86,.44,.985),opacity .8s cubic-bezier(.26,.86,.44,.985)
}
.reveal[data-transition-speed=fast] .slides section {
  transition-duration:.4s
}
.reveal[data-transition-speed=slow] .slides section {
  transition-duration:1.2s
}
.reveal .slides section[data-transition-speed=fast] {
  transition-duration:.4s
}
.reveal .slides section[data-transition-speed=slow] {
  transition-duration:1.2s
}
.reveal .slides>section.stack {
  padding-top:0;
  padding-bottom:0;
  pointer-events:none;
  height:100%
}
.reveal .slides>section.present,
.reveal .slides>section>section.present {
  display:block;
  z-index:11;
  opacity:1
}
.reveal .slides>section:empty,
.reveal .slides>section>section:empty,
.reveal .slides>section>section[data-background-interactive],
.reveal .slides>section[data-background-interactive] {
  pointer-events:none
}
.reveal.center,
.reveal.center .slides,
.reveal.center .slides section {
  min-height:0!important
}
.reveal .slides>section:not(.present),
.reveal .slides>section>section:not(.present) {
  pointer-events:none
}
.reveal.overview .slides>section,
.reveal.overview .slides>section>section {
  pointer-events:auto
}
.reveal .slides>section.future,
.reveal .slides>section.future>section,
.reveal .slides>section.past,
.reveal .slides>section.past>section,
.reveal .slides>section>section.future,
.reveal .slides>section>section.past {
  opacity:0
}
.reveal .slides section[data-transition=fade],
.reveal.fade .slides section:not([data-transition]),
.reveal.fade .slides>section>section:not([data-transition]) {
  transform:none;
  transition:opacity .5s
}
.reveal.fade.overview .slides section,
.reveal.fade.overview .slides>section>section {
  transition:none
}
.reveal .slides section[data-transition=none],
.reveal.none .slides section:not([data-transition]) {
  transform:none;
  transition:none
}
.reveal .no-transition,
.reveal .no-transition *,
.reveal .slides.disable-slide-transitions section {
  transition:none!important
}
.reveal .slides.disable-slide-transitions section {
  transform:none!important
}

backgrounds

.reveal .backgrounds {
  position:absolute;
  width:100%;
  height:100%;
  top:0;
  left:0;
  perspective:600px
}
.reveal .slide-background {
  display:none;
  position:absolute;
  width:100%;
  height:100%;
  opacity:0;
  visibility:hidden;
  overflow:hidden;
  background-color:rgba(0,0,0,0);
  transition:all .8s cubic-bezier(.26,.86,.44,.985)
}
.reveal .slide-background-content {
  position:absolute;
  width:100%;
  height:100%;
  background-position:50% 50%;
  background-repeat:no-repeat;
  background-size:cover
}
.reveal .slide-background.stack {
  display:block
}
.reveal .slide-background.present {
  opacity:1;
  visibility:visible;
  z-index:2
}
.print-pdf .reveal .slide-background {
  opacity:1!important;
  visibility:visible!important
}
.reveal .slide-background video {
  position:absolute;
  width:100%;
  height:100%;
  max-width:none;
  max-height:none;
  top:0;
  left:0;
  object-fit:cover
}

slide overview

.reveal.overview {
  perspective-origin:50% 50%;
  perspective:700px
}
.reveal.overview .slides section {
  height:100%;
  top:0!important;
  opacity:1!important;
  overflow:hidden;
  visibility:visible!important;
  cursor:pointer;
  box-sizing:border-box
}
.reveal.overview .slides section.present,
.reveal.overview .slides section:hover {
  outline:10px solid rgba(150,150,150,.4);
  outline-offset:10px
}
.reveal.overview .slides section .fragment {
  opacity:1;
  visibility:visible;
  transition:none
}
.reveal.overview .slides section:after,
.reveal.overview .slides section:before {
  display:none!important
}
.reveal.overview .slides>section.stack {
  padding:0;
  top:0!important;
  background:0 0;
  outline:0;
  overflow:visible
}
.reveal.overview .backgrounds {
  perspective:inherit
}
.reveal.overview .backgrounds .slide-background {
  opacity:1;
  visibility:visible;
  outline:10px solid rgba(150,150,150,.1);
  outline-offset:10px
}
.reveal.overview .backgrounds .slide-background.stack {
  overflow:visible
}
.reveal.overview .slides section,
.reveal.overview-deactivating .slides section {
  transition:none
}
.reveal.overview .backgrounds .slide-background,
.reveal.overview-deactivating .backgrounds .slide-background {
  transition:none
}

jump-to-slide

.reveal .jump-to-slide {
  position:absolute;
  top:15px;
  left:15px;
  z-index:30;
  font-size:32px;
  -webkit-tap-highlight-color:transparent
}
.reveal .jump-to-slide-input {
  background:0 0;
  padding:8px;
  font-size:inherit;
  color:currentColor;
  border:0
}
.reveal .jump-to-slide-input::placeholder {
  color:currentColor;
  opacity:.5
}
.reveal.has-dark-background .jump-to-slide-input {
  color:#fff
}
.reveal.has-light-background .jump-to-slide-input {
  color:#222
}
.reveal .jump-to-slide-input:focus {
  outline:0
}
.reveal-viewport.reveal-scroll .scrollbar {
  position:sticky;
  top:50%;
  z-index:20;
  opacity:0;
  transition:all .3s ease
}

help overlay

.reveal .overlay-help .overlay-content {
  overflow:auto
}
.reveal .overlay-help-content {
  width:100%;
  max-width:600px;
  margin:auto;
  text-align:center;
  letter-spacing:normal
}
.reveal .overlay-help-content .title {
  font-size:20px;
  margin-top:0
}
.reveal .overlay-help-content table {
  border:1px solid #fff;
  border-collapse:collapse;
  font-size:16px
}
.reveal .overlay-help-content table td,
.reveal .overlay-help-content table th {
  width:200px;
  padding:14px;
  border:1px solid #fff;
  vertical-align:middle
}
.reveal .overlay-help-content table th {
  padding-top:20px;
  padding-bottom:20px
}

speaker notes

.reveal aside.notes {
  display:none
}
.reveal .speaker-notes {
  display:none;
  position:absolute;
  width:33.3333333333%;
  height:100%;
  top:0;
  left:100%;
  padding:14px 18px 14px 18px;
  z-index:1;
  font-size:18px;
  line-height:1.4;
  border:1px solid rgba(0,0,0,.05);
  color:#222;
  background-color:#f5f5f5;
  overflow:auto;
  box-sizing:border-box;
  text-align:left;
  -webkit-overflow-scrolling:touch
}
.reveal .speaker-notes .notes-placeholder {
  color:#ccc;
  font-style:italic
}
.reveal .speaker-notes:focus {
  outline:0
}
.reveal .speaker-notes:before {
  content:"Speaker notes";
  display:block;
  margin-bottom:10px;
  opacity:.5
}
.reveal.show-notes {
  max-width:75%;
  overflow:visible
}
.reveal.show-notes .speaker-notes {
  display:block
}
@media screen and (min-width:1600px) {
  .reveal .speaker-notes {
    font-size:20px
  }
}
@media screen and (max-width:1024px) {
  .reveal.show-notes {
    border-left:0;
    max-width:none;
    max-height:70%;
    max-height:70vh;
    overflow:visible
  }
  .reveal.show-notes .speaker-notes {
    top:100%;
    left:0;
    width:100%;
    height:30vh;
    border:0
  }
}
@media screen and (max-width:600px) {
  .reveal.show-notes {
    max-height:60%;
    max-height:60vh
  }
  .reveal.show-notes .speaker-notes {
    top:100%;
    height:40vh
  }
  .reveal .speaker-notes {
    font-size:14px
  }
}

printing

html.reveal-print * {
  -webkit-print-color-adjust:exact
}
html.reveal-print {
  width:100%;
  height:100%;
  overflow:visible
}
html.reveal-print body {
  margin:0 auto!important;
  border:0;
  padding:0;
  float:none!important;
  overflow:visible
}
html.reveal-print .nestedarrow,
html.reveal-print .reveal .controls,
html.reveal-print .reveal .playback,
html.reveal-print .reveal .progress,
html.reveal-print .reveal.overview,
html.reveal-print .state-background {
  display:none!important
}
html.reveal-print .reveal pre code {
  overflow:hidden!important
}
html.reveal-print .reveal {
  width:auto!important;
  height:auto!important;
  overflow:hidden!important
}
html.reveal-print .reveal .slides {
  position:static;
  width:100%!important;
  height:auto!important;
  zoom:1!important;
  pointer-events:initial;
  left:auto;
  top:auto;
  margin:0!important;
  padding:0!important;
  overflow:visible;
  display:block;
  perspective:none;
  perspective-origin:50% 50%
}
html.reveal-print .reveal .slides .pdf-page {
  position:relative;
  overflow:hidden;
  z-index:1;
  page-break-after:always
}
html.reveal-print .reveal .slides .pdf-page:last-of-type {
  page-break-after:avoid
}
html.reveal-print .reveal .slides section {
  visibility:visible!important;
  display:block!important;
  position:absolute!important;
  margin:0!important;
  padding:0!important;
  box-sizing:border-box!important;
  min-height:1px;
  opacity:1!important;
  transform-style:flat!important;
  transform:none!important
}
html.reveal-print .reveal section.stack {
  position:relative!important;
  margin:0!important;
  padding:0!important;
  page-break-after:avoid!important;
  height:auto!important;
  min-height:auto!important
}
html.reveal-print .reveal img {
  box-shadow:none
}
html.reveal-print .reveal .backgrounds {
  display:none
}
html.reveal-print .reveal .slide-background {
  display:block!important;
  position:absolute;
  top:0;
  left:0;
  width:100%;
  height:100%;
  z-index:auto!important
}
html.reveal-print .reveal.show-notes {
  max-width:none;
  max-height:none
}
html.reveal-print .reveal .speaker-notes-pdf {
  display:block;
  width:100%;
  height:auto;
  max-height:none;
  top:auto;
  right:auto;
  bottom:auto;
  left:auto;
  z-index:100
}
html.reveal-print .reveal .speaker-notes-pdf[data-layout=separate-page] {
  position:relative;
  color:inherit;
  background-color:transparent;
  padding:20px;
  page-break-after:always;
  border:0
}
/*
html.reveal-print .reveal .slide-number-pdf {
  display:block;
  position:absolute;
  font-size:14px;
  visibility:visible
}
*/
html.reveal-print .aria-status {
  display:none
}
@media print {
  .backgrounds {
    background-color: #fafafa;
  }
  html:not(.print-pdf) {
    overflow:visible;
    width:auto;
    height:auto
  }
  html:not(.print-pdf) body {
    margin:0;
    padding:0;
    overflow:visible
  }
  html:not(.print-pdf) .reveal {
    background:#fff;
    font-size:20pt
  }
  html:not(.print-pdf) .reveal .backgrounds,
  html:not(.print-pdf) .reveal .controls,
  html:not(.print-pdf) .reveal .progress,
  html:not(.print-pdf) .reveal .slide-number,
  html:not(.print-pdf) .reveal .state-background {
    display:none!important
  }
  html:not(.print-pdf) .reveal li,
  html:not(.print-pdf) .reveal p,
  html:not(.print-pdf) .reveal td {
    font-size:20pt!important;
    color:#000
  }
  html:not(.print-pdf) .reveal h1,
  html:not(.print-pdf) .reveal h2,
  html:not(.print-pdf) .reveal h3,
  html:not(.print-pdf) .reveal h4,
  html:not(.print-pdf) .reveal h5,
  html:not(.print-pdf) .reveal h6 {
    color:#000!important;
    height:auto;
    line-height:normal;
    text-align:left;
    letter-spacing:normal
  }
  html:not(.print-pdf) .reveal h1 {
    font-size:28pt!important
  }
  html:not(.print-pdf) .reveal h2 {
    font-size:24pt!important
  }
  html:not(.print-pdf) .reveal h3 {
    font-size:22pt!important
  }
  html:not(.print-pdf) .reveal h4 {
    font-size:22pt!important;
    font-variant:small-caps
  }
  html:not(.print-pdf) .reveal h5 {
    font-size:21pt!important
  }
  html:not(.print-pdf) .reveal h6 {
    font-size:20pt!important;
    font-style:italic
  }
  html:not(.print-pdf) .reveal a:link,
  html:not(.print-pdf) .reveal a:visited {
    color:#000!important;
    font-weight:700;
    text-decoration:underline
  }
  html:not(.print-pdf) .reveal div,
  html:not(.print-pdf) .reveal ol,
  html:not(.print-pdf) .reveal p,
  html:not(.print-pdf) .reveal ul {
    visibility:visible;
    position:static;
    width:auto;
    height:auto;
    display:block;
    overflow:visible;
    margin:0;
    text-align:left!important
  }
  html:not(.print-pdf) .reveal pre,
  html:not(.print-pdf) .reveal table {
    margin-left:0;
    margin-right:0
  }
  html:not(.print-pdf) .reveal pre code {
    padding:20px
  }
  html:not(.print-pdf) .reveal blockquote {
    margin:20px 0
  }
  html:not(.print-pdf) .reveal .slides {
    position:static!important;
    width:auto!important;
    height:auto!important;
    left:0!important;
    top:0!important;
    margin-left:0!important;
    margin-top:0!important;
    padding:0!important;
    zoom:1!important;
    transform:none!important;
    overflow:visible!important;
    display:block!important;
    text-align:left!important;
    perspective:none;
    perspective-origin:50% 50%
  }
  html:not(.print-pdf) .reveal .slides section {
    visibility:visible!important;
    position:static!important;
    width:auto!important;
    height:auto!important;
    display:block!important;
    overflow:visible!important;
    left:0!important;
    top:0!important;
    margin-left:0!important;
    margin-top:0!important;
    padding:60px 20px!important;
    z-index:auto!important;
    opacity:1!important;
    page-break-after:always!important;
    transform-style:flat!important;
    transform:none!important;
    transition:none!important
  }
  html:not(.print-pdf) .reveal .slides section.stack {
    padding:0!important
  }
  html:not(.print-pdf) .reveal .slides section:last-of-type {
    page-break-after:avoid!important
  }
  html:not(.print-pdf) .reveal .slides section .fragment {
    opacity:1!important;
    visibility:visible!important;
    transform:none!important
  }
  html:not(.print-pdf) .reveal section img {
    display:block;
    margin:15px 0;
    background:#fff;
    border:1px solid #666;
    box-shadow:none
  }
  html:not(.print-pdf) .reveal section small {
    font-size:.8em
  }
  html:not(.print-pdf) .reveal .hljs {
    max-height:100%;
    white-space:pre-wrap;
    word-wrap:break-word;
    word-break:break-word;
    font-size:15pt
  }
  html:not(.print-pdf) .reveal .hljs .hljs-ln-numbers {
    white-space:nowrap
  }
  html:not(.print-pdf) .reveal .hljs td {
    font-size:inherit!important;
    color:inherit!important
  }
}

Poster CSS

html, body, div, span, applet, object, iframe,
h1, h2, h3, h4, h5, h6, p, blockquote, pre,
a, abbr, acronym, address, big, cite, code,
del, dfn, em, img, ins, kbd, q, s, samp,
small, strike, strong, sub, sup, tt, var,
b, u, i, center,
dl, dt, dd, ol, ul, li,
fieldset, form, label, legend,
table, caption, tbody, tfoot, thead, tr, th, td,
article, aside, canvas, details, embed,
figure, figcaption, footer, header, hgroup,
main, menu, nav, output, ruby, section, summary,
time, mark, audio, video {
  margin: 0;
  padding: 0;
  border: 0;
  font-size: 100%;
  font: inherit;
  vertical-align: baseline;
}

:root {
    --bg: #613583FF;
}

body {
  font-family: "Fira Sans", sans-serif;
  color: black;
  background-color: white;
  width: 1000mm;
  height: 707mm;
  font-size: 28pt;
  font-weight: normal;
  /*border: 3px solid red;*/
  text-align: left;
}

b {
  font-weight: bold;
}
em, i {
  font-style: italic;
}

h2 {
  display: none;
}

p {
  line-height: 1.4;
}

ul {
  margin: 0 0 0 1em;
}

a {
  color: #5F5F5F;
  text-decoration: none;
}

.abspos {
  position: absolute;
}

.org-svg {
  width: 100%;
}

.title {
  max-width: fit-content;
  margin-inline: auto;
  margin-top: -30mm;
  text-align: center;
  font-size: 45pt;
  font-weight: bold;
  background-color: var(--bg);
  color: #FFFFFF;
  border-radius: 10mm;
  padding: 25mm 10mm 5mm;
}

.sechead {
  background-color: var(--bg);
  color: #FFFFFF;
  padding: 1mm 5mm;
  border-radius: 3mm;
  max-width: fit-content;
  font-size: 32pt;
}

.section {
  border: 3mm solid var(--bg);
  border-radius: 5mm;
  padding: 5mm;
}

.box {
  border: 1mm solid black;
  padding: 1mm 5mm;
}

/*
@media print {
  @page {
    size: 1000mm 707mm;
  }
}
*/

svg favicon

<svg width="86pt" height="86pt" version="1.1" viewBox="0 0 86 86" xmlns="http://www.w3.org/2000/svg">
<style>
@media (prefers-color-scheme: dark) {
.grid {
stroke: white;
fill: none;
stroke-width: 2.1918;
stroke-miterlimit: 10;
clip-path: url(#clip);
}
.node {fill: white;}
.outl {
stroke: white;
fill: none;
stroke-width: .797;
stroke-miterlimit: 10;
}
.arro {
stroke: white;
fill: white;
stroke-width: .797;
stroke-miterlimit: 10;
}
}
@media (prefers-color-scheme: light) {
.grid {
stroke: black;
fill: none;
stroke-width: 2.1918;
stroke-miterlimit: 10;
clip-path: url(#clip);
}
.node {fill: black;}
.outl {
stroke: black;
fill: none;
stroke-width: .797;
stroke-miterlimit: 10;
}
.arro {
stroke: black;
fill: black;
stroke-width: .797;
stroke-miterlimit: 10;
}
}
</style>
<defs>
<clipPath id="clip">
<path d="m61.578 29.039-36.824-21.258-36.824 21.258v42.52l36.824 21.262 36.824-21.262z"/>
</clipPath>
</defs>
<g id="page" transform="translate(18.246 -7.3008)">
<path class="grid" d="m81.445 50.301h-56.691" clip-path="url(#clip)"/>
<path class="grid" d="m53.098 1.2031-28.344 49.098" clip-path="url(#clip)"/>
<path class="grid" d="m-3.5937 1.2031 28.348 49.098" clip-path="url(#clip)"/>
<path class="grid" d="m-31.941 50.301h56.695" clip-path="url(#clip)"/>
<path class="grid" d="m-3.5937 99.398 28.348-49.098" clip-path="url(#clip)"/>
<path class="grid" d="m53.098 99.398-28.344-49.098" clip-path="url(#clip)"/>
<path class="grid" d="m67.273 25.75h-85.039l42.52 73.648z" clip-path="url(#clip)"/>
<path class="grid" d="m24.754 1.2031-42.52 73.645h85.039z" clip-path="url(#clip)"/>
<path class="node" d="m57.066 50.301c0-2.1914-1.7734-3.9688-3.9687-3.9688-2.1914 0-3.9649 1.7773-3.9649 3.9688s1.7735 3.9688 3.9649 3.9688c2.1953 0 3.9687-1.7773 3.9687-3.9688z"/>
<path class="node" d="m42.894 25.75c0-2.1914-1.7773-3.9688-3.9687-3.9688s-3.9688 1.7774-3.9688 3.9688 1.7774 3.9687 3.9688 3.9687 3.9687-1.7773 3.9687-3.9687z"/>
<path class="node" d="m14.547 25.75c0-2.1914-1.7774-3.9688-3.9688-3.9688s-3.9687 1.7774-3.9687 3.9688 1.7773 3.9687 3.9687 3.9687 3.9688-1.7773 3.9688-3.9687z"/>
<path class="node" d="m0.375 50.301c0-2.1914-1.7773-3.9688-3.9687-3.9688-2.1915 0-3.9688 1.7773-3.9688 3.9688s1.7773 3.9688 3.9688 3.9688c2.1914 0 3.9687-1.7773 3.9687-3.9688z"/>
<path class="node" d="m14.547 74.848c0-2.1915-1.7774-3.9688-3.9688-3.9688s-3.9687 1.7773-3.9687 3.9688c0 2.1914 1.7773 3.9687 3.9687 3.9687s3.9688-1.7773 3.9688-3.9687z"/>
<path class="node" d="m42.894 74.848c0-2.1915-1.7773-3.9688-3.9687-3.9688s-3.9688 1.7773-3.9688 3.9688c0 2.1914 1.7774 3.9687 3.9688 3.9687s3.9687-1.7773 3.9687-3.9687z"/>
<path class="node" d="m28.723 50.301c0-2.1914-1.7774-3.9688-3.9688-3.9688-2.1914 0-3.9687 1.7773-3.9687 3.9688s1.7773 3.9688 3.9687 3.9688c2.1914 0 3.9688-1.7773 3.9688-3.9688z"/>
<path class="outl" d="m61.578 29.039-36.824-21.258-36.824 21.258v42.52l36.824 21.262 36.824-21.262z"/>
<path class="arro" d="m43.812 18.781 2.8086 3.4375-0.40625-2.0469 1.9766-0.67188z"/>
<path class="arro" d="m38.117 15.496 2.8125 3.4375-0.41016-2.0508 1.9805-0.67187z"/>
<path class="arro" d="m10.086 16.25 4.3828-0.71875-1.9805-0.67188 0.41015-2.0469z"/>
<path class="arro" d="m4.3906 19.535 4.3828-0.71485-1.9766-0.67187 0.40625-2.0508z"/>
<path class="arro" d="m-1.3047 22.824 4.3828-0.71875-1.9766-0.67188 0.40625-2.0469z"/>
<path class="arro" d="m-12.07 47.855 1.5703 4.1523-1.5703-1.3789-1.5703 1.3789z"/>
<path class="arro" d="m0.24218 78.668 4.3789 0.71485-1.9766 0.67187 0.40625 2.0508z"/>
<path class="arro" d="m5.9336 81.957 4.3828 0.71485-1.9766 0.67187 0.40625 2.0469z"/>
<path class="arro" d="m35.691 86.504 2.8125-3.4375-0.40625 2.0508 1.9766 0.67187z"/>
<path class="arro" d="m41.387 83.215 2.8125-3.4336-0.41015 2.0469 1.9805 0.67188z"/>
<path class="arro" d="m47.082 79.93 2.8086-3.4375-0.40625 2.0469 1.9805 0.67188z"/>
<path class="arro" d="m61.578 48.441-1.5703 4.1524 1.5703-1.3789 1.5703 1.3789z"/>
</g>
</svg>

Mathjax JS

https://groups.google.com/g/mathjax-users/c/M6Uh4ANEdPU https://github.com/mathjax/MathJax/issues/3304 https://github.com/mathjax/MathJax/issues/3392

window.MathJax = {
    options: {
        menuOptions: {
            settings: {
                enrich: false,
            }
        },
    },
    loader: {
        load: ['[tex]/physics', '[tex]/mathtools']
    },
    tex: {
        packages: {'[+]': ['physics', 'mathtools']},
        tags: "ams",
        ams: {
            multlineWidth: "85%"
        },
        mathtools: {
            'use-unicode': true
        }
    },
    output: {
        font: 'mathjax-fira',
        fontPath: '/mathjax/fira-font'
    }
};
(function () {
    var script = document.createElement('script');
    script.src = '/mathjax/tex-chtml-nofont.js';
    script.async = true;
    document.head.appendChild(script);
})();

Reveal JS

import Reveal from './revealjs/index.js'
import RevealNotes from './revealjs/notes/plugin.js'

function replaceWithSection(el) {
    let sec = document.createElement("section");
    sec.innerHTML = el.innerHTML;
    for (const name of el.getAttributeNames()) {
        const value = el.getAttribute(name);
        sec.setAttribute(name, value);
    }
    el.parentNode.replaceChild(sec, el);
}

let content = document.getElementById("content");
let wrapper = document.createElement("div");
content.parentNode.insertBefore(wrapper, content);
wrapper.appendChild(content);
content.classList.add("slides");
wrapper.classList.add("reveal");
document.querySelectorAll("div.outline-3").forEach(replaceWithSection);
document.querySelectorAll("div.outline-2").forEach(replaceWithSection);

// Inspired by js from
// https://github.com/hakimel/reveal.js/issues/1626
// https://github.com/ranr01/reveal-inline-svg
// https://dev.to/dannyengelman/load-file-web-component-add-external-content-to-the-dom-1nd

customElements.define("load-file", class extends HTMLElement {
  async connectedCallback() {
    const shadowRoot = this.attachShadow({mode:"open"});
    shadowRoot.innerHTML = await (await fetch(this.getAttribute("src"))).text();

    this.querySelectorAll("param").forEach(function(p) {
        var svg_elem = shadowRoot.querySelector("#".concat(p.getAttribute("id")));
        for (const attr of p.attributes) {
            svg_elem.setAttribute(attr.name, attr.value);
        }
    });
    this.replaceWith(...shadowRoot.childNodes);
  }
})

Reveal.initialize({
    width: 1920,
    height: 1080,
    hash: true,
    controls: false,
    slideNumber: 'c',
    transition: "none",
    viewDistance: 4,
    hideCursorTime: 1000,
    //disableLayout: true,
    center: false,
    margin: 0,
    pdfMaxPagesPerSlide: 1,
    //pdfSeparateFragments: false,
    plugins: [ RevealNotes ]
});
/*
Reveal.on('ready', event => {
    Reveal.configure({ slideNumber: !(event.indexh === 0) });
});
Reveal.addEventListener('slidechanged', (event) => {
    Reveal.configure({ slideNumber: !(event.indexh === 0) });
});
*/

HTML

https://css-tricks.com/svg-favicons-and-all-the-fun-things-we-can-do-with-them/

<link href="/favicon.svg" rel="icon" type="image/svg+xml">
<link href="/font/fira.css" rel="stylesheet" type="text/css">
<script src="/mathjax-init.js" type="text/javascript" async></script>
<link href="/styles.css" rel="stylesheet" type="text/css">
<link href="/reveal.css" rel="stylesheet" type="text/css">
<script src="/revealjs/reveal.js" type="module" defer></script>
<script src="/revealjs/notes/plugin.js" type="module" defer></script>
<script src="/reveal-init.js" type="module" defer></script>
<div class="menu">
<a class="menu-btn" href="/">Akira Kyle</a>
<span style="color: var(--func);">|</span>
<a class="menu-btn" href="/blog">Blogoroam</a>
</div>
(let* ((named-element (org-element-map (org-element-parse-buffer) org-element-all-elements
                        (lambda (element)
                          (when (string= (org-element-property :name element) name)
                            element))
                        nil t))
       (result (org-element-property :value named-element)))
  (format "\"%s\"" (replace-regexp-in-string "\\\"" "\\\\\"" result))) ;; escape quote
(setq my-org-html-head
<<blk-to-elisp-str("html-head")>>
)
(setq my-org-html-head-website
<<blk-to-elisp-str("html-head-website")>>
)
(setq my-org-html-head-reveal
<<blk-to-elisp-str("html-head-reveal")>>
)
(setq my-org-html-preamble
<<blk-to-elisp-str("html-preamble")>>
)

Emacs Lisp org-publish

See How I publish my wiki with org-publish for another take on exporting org-roam using org-publish.

List of notes/pages

(defun my-org-get-env-key (post-filename key)
  "Extract the value of `#+title:`, `#+author:`, `#+date:`, or `#+filetags:`
from post-filename."
  (with-temp-buffer (insert-file-contents post-filename)
                    (cadar (org-collect-keywords (list key)))))

(defun my-notes-filenames ()
  "Returns a list of all files sorted approprately."
  (sort
   (mapcan (lambda (dir)
             (directory-files
              (file-name-as-directory (concat my-org-dir dir)) t ".*\\.org$" nil))
           '("notes" "config"))
   (lambda (a b)
     (>
     (org-time-string-to-seconds (my-org-get-env-key a "date"))
     (org-time-string-to-seconds (my-org-get-env-key b "date"))))))

(defun my-filenames-to-org-list (post-filenames)
  (seq-reduce
   (lambda (acc el) (concat acc "\n- " el))
   (seq-map (lambda (fname)
              (concat
               (org-export-get-date
                `(:date ,(org-element-parse-secondary-string
                          (my-org-get-env-key fname "date")
                          (org-element-restriction 'keyword))) "%Y-%m-%d")
               ": "
               (org-link-make-string
                (concat "file:" (file-relative-name fname))
                (my-org-get-env-key fname "title"))))
            post-filenames)
   ""))

org roam export backlinks and reflinks and citations

  • insert-bibliography eliminates the need for #+print_bibliography: at the end of every file
    • my-filter-citations makes org citations link to the corresponding org-roam nodes
      • I didn’t end up trying to use the csl formatter to get the nice, configurable inline style, but rather just make the org-roam title close to what the csl formatter would do (yeah this is hacky).
;; TODO: Still need to fix spacing also consider leaving in original citation, just add link to ref-notes only if it exists...
(defun my-filter-citations (data backend info)
  (let* ((cite-to-id
          (lambda (el)
            (let* ((key (concat "@" (org-element-property :key el)))
                   (node (org-roam-node-from-ref key))
                   (_ (and (not node) (error "No org roam node for key %s" key)))
                   (id (org-roam-node-id node))
                   (title (org-roam-node-title node)))
              (org-link-make-string (concat "id:" id) title))))
         (cites-to-ids
          (lambda (elts)
            (with-temp-buffer
              (save-excursion
                (insert (concat " (" (mapconcat cite-to-id elts "; ") ") "))
                (car (org-element-map (org-element-parse-buffer) 'paragraph
                       'org-element-contents))))))
         (map-citation
          (lambda (el)
            (unless (org-element-property :style el)
              (mapc (lambda (l) (org-element-insert-before l el))
                    (funcall cites-to-ids (org-element-contents el)))
              (org-element-extract-element el)))))
    (org-element-map data 'citation map-citation info nil nil t)
    data))

(defun insert-bibliography (backend)
  "Insert reflinks into the end of the org file before parsing it."
  (when (eq backend 'html)
    (goto-char (point-min))
    (when (re-search-forward "\\[cite:.*\\]" nil t)
      (goto-char (point-max))
      (insert "\n\n* references\n")
      (insert "#+print_bibliography: :title \"references\""))))

;; https://org-roam.discourse.group/t/export-backlinks-on-org-export/1756/2?page=2
(defun collect-backlinks-string (backend)
  "Insert backlinks into the end of the org file before parsing it."
  (when (and (or (eq backend 'html) (eq backend 'html-with-cite-filter))
             (org-roam-node-at-point))
    (let* ((backlinks (org-roam-backlinks-get (org-roam-node-at-point))))
      (when backlinks
        (goto-char (point-max))
        (insert "\n\n* backlinks\n")
        (dolist (backlink backlinks)
          (let* ((source-node (org-roam-backlink-source-node backlink))
                 (point (org-roam-backlink-point backlink)))
            (insert
             (format "- [[id:%s][%s]]\n"
                     (file-name-nondirectory (org-roam-node-id source-node))
                     (org-roam-node-title source-node)))))))))

(defun collect-reflinks-string (backend)
  "Insert reflinks into the end of the org file before parsing it."
  (when (and (or (eq backend 'html) (eq backend 'html-with-cite-filter))
             (org-roam-node-at-point))
    (let* ((reflinks (org-roam-reflinks-get (org-roam-node-at-point))))
      (when reflinks
        (goto-char (point-max))
        (insert "\n\n* reflinks:\n")
        (dolist (reflink reflinks)
          (let* ((source-node (org-roam-reflink-source-node reflink))
                 (point (org-roam-reflink-point reflink)))
            (unless (string= (org-roam-node-id source-node)
                             (org-roam-node-id (org-roam-node-at-point)))
              (insert
               (format "- [[id:%s][%s]]\n"
                       (file-name-nondirectory (org-roam-node-id source-node))
                       (org-roam-node-title source-node))))))))))

remove automatically generated ids

https://emacs.stackexchange.com/questions/36366/disable-auto-id-generation-in-org-mode-html-export https://github.com/alphapapa/unpackaged.el/issues/21 https://kozikow.blog/2016/06/05/make-internal-links-exported-by-org-unique/ https://www.vidal-rosset.net/the_code_that_runs_this_blog.html https://www.mail-archive.com/emacs-orgmode@gnu.org/msg141199.html

(defun unpackaged/org-export-new-title-reference (datum cache)
  "Return new reference for DATUM that is unique in CACHE."
  (cl-macrolet ((inc-suffixf (place)
                             `(progn
                                (string-match (rx bos
                                                  (minimal-match (group (1+ anything)))
                                                  (optional "--" (group (1+ digit)))
                                                  eos)
                                              ,place)
                                ;; HACK: `s1' instead of a gensym.
                                (-let* (((s1 suffix) (list (match-string 1 ,place)
                                                           (match-string 2 ,place)))
                                        (suffix (if suffix
                                                    (string-to-number suffix)
                                                  0)))
                                  (setf ,place (format "%s--%s" s1 (cl-incf suffix)))))))
    (let* ((title (org-element-property :raw-value datum))
           (ref (url-hexify-string (substring-no-properties title)))
           (parent (org-element-property :parent datum)))
      (while (--any (equal ref (car it))
                    cache)
        ;; Title not unique: make it so.
        (if parent
            ;; Append ancestor title.
            (setf title (concat (org-element-property :raw-value parent)
                                "--" title)
                  ref (url-hexify-string (substring-no-properties title))
                  parent (org-element-property :parent parent))
          ;; No more ancestors: add and increment a number.
          (inc-suffixf ref)))
      ref)))

(defun unpackaged/org-export-get-reference (datum info)
  "Like `org-export-get-reference', except uses heading titles instead of random numbers."
  (let ((cache (plist-get info :internal-references)))
    (or (car (rassq datum cache))
        (let* ((crossrefs (plist-get info :crossrefs))
               (cells (org-export-search-cells datum))
               ;; Preserve any pre-existing association between
               ;; a search cell and a reference, i.e., when some
               ;; previously published document referenced a location
               ;; within current file (see
               ;; `org-publish-resolve-external-link').
               ;;
               ;; However, there is no guarantee that search cells are
               ;; unique, e.g., there might be duplicate custom ID or
               ;; two headings with the same title in the file.
               ;;
               ;; As a consequence, before re-using any reference to
               ;; an element or object, we check that it doesn't refer
               ;; to a previous element or object.
               (new (or (cl-some
                         (lambda (cell)
                           (let ((stored (cdr (assoc cell crossrefs))))
                             (when stored
                               (let ((old stored))
                                 (and (not (assoc old cache)) stored)))))
                         cells)
                        (when (org-element-property :raw-value datum)
                          ;; Heading with a title
                          (unpackaged/org-export-new-title-reference datum cache))
                          ;; NOTE: This probably breaks some Org Export
                          ;; feature, but if it does what I need, fine.
                          (org-export-format-reference
                           (org-export-new-reference cache))))
               (reference-string new))
          ;; Cache contains both data already associated to
          ;; a reference and in-use internal references, so as to make
          ;; unique references.
          (dolist (cell cells) (push (cons cell new) cache))
          ;; Retain a direct association between reference string and
          ;; DATUM since (1) not every object or element can be given
          ;; a search cell (2) it permits quick lookup.
          (push (cons reference-string datum) cache)
          (plist-put info :internal-references cache)
          reference-string))))

(advice-add #'org-export-get-reference :override #'unpackaged/org-export-get-reference)

publish config

;; I use the ~#+modified:~ property rather than org's default of using the
;; file's modification time, since my org files are in git
(defun my-org-html-build-preamble (info)
  (let* ((spec (org-html-format-spec info))
         (date (cdr (assq ?d spec)))
         (timestamp-format (plist-get info :html-metadata-timestamp-format))
         (modified-str (cadar (org-collect-keywords '("modified"))))
         (modified-parsed (org-element-parse-secondary-string
                           modified-str (org-element-restriction 'keyword)))
         (modified (org-export-get-date `(:date ,modified-parsed)
                                        timestamp-format)))
    (concat
     my-org-html-preamble
     (and (plist-get info :with-date)
          (org-string-nw-p date)
          (format "<p class=\"date\">Created: %s</p>\n" date))
     (and (plist-get info :with-date)
          (org-string-nw-p modified)
          (format "<p class=\"date\">Last modified: %s</p>\n" modified)))))

;;(setq org-export-async-init-file (expand-file-name "~/notebook/setup.el")
;;      org-export-in-background t)
(setq org-html-metadata-timestamp-format "%B %e, %Y")
(setq org-html-htmlize-output-type 'css)
(setq org-html-html5-fancy t)
(setq org-html-doctype "html5")
(setq org-export-with-toc nil)
(setq org-export-with-section-numbers nil)
(setq org-export-time-stamp-file nil)
(setq org-html-head-include-default-style nil)
(setq org-html-head-include-scripts nil)
(setq org-html-head my-org-html-head)
(setq org-html-head-extra my-org-html-head-website)
(setq org-html-preamble 'my-org-html-build-preamble)
(setq org-html-postamble nil)
(setq org-html-mathjax-template "")
(setq org-html-self-link-headlines t)
(setq org-html-prefer-user-labels t)

;; for org-html-link to omit .html from a href links
(setq org-html-extension "")

(org-export-define-derived-backend 'html-with-cite-filter 'html)

(defun my-org-html-publish-to-html (plist filename pub-dir)
  (org-publish-org-to 'html filename ".html" plist pub-dir))

(defun my-org-html-publish-to-html-with-cite-filter (plist filename pub-dir)
  (let ((org-export-filter-parse-tree-functions '(my-filter-citations)))
    (org-publish-org-to 'html-with-cite-filter filename ".html" plist pub-dir)))

(add-hook 'org-export-before-processing-functions 'insert-bibliography)
(add-hook 'org-export-before-processing-functions 'collect-backlinks-string)
(add-hook 'org-export-before-processing-functions 'collect-reflinks-string)

(defun my-publish-dir-with-cite-filter (dir)
  `(,(concat "notebook-" dir)
    :base-directory ,(concat my-org-dir "notebook/" dir)
    :publishing-directory ,(concat my-website-publish-dir my-collab-url dir)
    :publishing-function my-org-html-publish-to-html-with-cite-filter))

(defun my-publish-dir (dir)
  `(,dir
    :base-directory ,(concat my-org-dir dir)
    :publishing-directory ,(concat my-website-publish-dir dir)
    :publishing-function my-org-html-publish-to-html))
    ;;:html-postamble "Insert comments here..."))

(setq org-publish-project-alist
      `(
        ,(cons "top" (cdr (my-publish-dir "")))
        ,(my-publish-dir "config")
        ,(my-publish-dir "notes")
        ,(my-publish-dir-with-cite-filter "ref-notes")
        ,(my-publish-dir-with-cite-filter "notes")
        ("notebook-talks"
         :base-directory ,(concat my-org-dir "notebook/talks")
         :publishing-directory ,(concat my-website-publish-dir my-collab-url "talks")
         :publishing-function my-org-html-publish-to-html
         ;:html-container "section"
         ;:html-content-class "reveal slides"
         :html-head-extra ,my-org-html-head-reveal
         :html-preamble nil
         :with-title nil)
        ;("pub"
        ; :exclude "info/.*\\|rough/.*\\|notebook/.*\\|ref-notes/.*"
        ; :recursive t)
        ;("inkscape"
        ; :base-directory ,(concat my-org-dir "inkscape")
        ; :publishing-directory ,(concat my-website-publish-dir my-collab-url "inkscape")
        ; :base-extension "svg"
        ; :publishing-function org-publish-attachment)
        ("website" :components ("top" "config" "notes"))
        ))
<<org-html-strings>>
<<org-dir-vars>>
<<org-html-export-remove-auto-id>>
<<list-org-files>>
<<org-roam-export-helpers>>
<<org-publish-project>>
(org-publish "website" t)

Need to run org-id-update-id-locations and org-roam-update-org-id-locations when exporting and get “org-export-data: Unable to resolve link”

Preview with simple-httpd

(require 'simple-httpd)

(defun httpd-gen-path (path &optional root)
  "Translate GET to secure path in ROOT (`httpd-root')."
  (let ((clean (expand-file-name (httpd-clean-path path) (or root httpd-root))))
    (if (file-directory-p clean)
        (let* ((dir (file-name-as-directory clean))
               (indexes (cl-mapcar (apply-partially 'concat dir) httpd-indexes))
               (existing (cl-remove-if-not 'file-exists-p indexes)))
          (or (car existing) dir))
      (if (file-exists-p clean)
          clean
        (concat clean ".html")))))

(setq httpd-root my-website-publish-dir)
(setq httpd-listings t)
(setq httpd-host "0.0.0.0")
(httpd-start)

references