2024-07-07 13:09:14 +02:00
|
|
|
use std::collections::HashMap;
|
|
|
|
|
2024-07-03 23:34:31 +02:00
|
|
|
use camino::Utf8PathBuf;
|
|
|
|
use chrono::{DateTime, Utc};
|
2024-07-20 17:08:11 +02:00
|
|
|
use hauchiwa::{Content, Link, LinkDate, Linkable, Outline, Sack};
|
2024-07-03 23:34:31 +02:00
|
|
|
use hayagriva::Library;
|
2024-07-05 13:59:07 +02:00
|
|
|
use hypertext::{html_elements, maud_move, GlobalAttributes, Raw, Renderable};
|
2024-07-03 23:34:31 +02:00
|
|
|
use serde::Deserialize;
|
|
|
|
|
2024-07-05 13:59:07 +02:00
|
|
|
const CSS: &str = r#"
|
|
|
|
.slides img {
|
|
|
|
margin-left: auto;
|
|
|
|
margin-right: auto;
|
|
|
|
max-height: 60vh;
|
|
|
|
}
|
|
|
|
"#;
|
2024-07-03 23:34:31 +02:00
|
|
|
|
|
|
|
/// Represents a slideshow
|
|
|
|
#[derive(Deserialize, Debug, Clone)]
|
|
|
|
pub(crate) struct Slideshow {
|
2024-07-05 13:59:07 +02:00
|
|
|
pub title: String,
|
|
|
|
#[serde(with = "super::isodate")]
|
|
|
|
pub date: DateTime<Utc>,
|
|
|
|
pub desc: Option<String>,
|
2024-07-03 23:34:31 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
impl Content for Slideshow {
|
2024-07-07 13:09:14 +02:00
|
|
|
fn parse(
|
|
|
|
data: String,
|
|
|
|
_: Option<&Library>,
|
|
|
|
dir: Utf8PathBuf,
|
|
|
|
hash: HashMap<Utf8PathBuf, Utf8PathBuf>,
|
|
|
|
) -> (Outline, String, Option<Vec<String>>) {
|
2024-07-05 13:59:07 +02:00
|
|
|
let html = data
|
|
|
|
.split("\n-----\n")
|
|
|
|
.map(|chunk| {
|
|
|
|
chunk
|
|
|
|
.split("\n---\n")
|
2024-07-07 13:09:14 +02:00
|
|
|
.map(|s| crate::text::md::parse(s.to_owned(), None, dir.clone(), hash.clone()))
|
2024-07-05 13:59:07 +02:00
|
|
|
.map(|e| e.1)
|
|
|
|
.collect::<Vec<_>>()
|
|
|
|
})
|
|
|
|
.map(|stack| match stack.len() > 1 {
|
|
|
|
true => format!(
|
|
|
|
"<section>{}</section>",
|
|
|
|
stack
|
|
|
|
.into_iter()
|
|
|
|
.map(|slide| format!("<section>{slide}</section>"))
|
|
|
|
.collect::<String>()
|
|
|
|
),
|
|
|
|
false => format!("<section>{}</section>", stack[0]),
|
|
|
|
})
|
|
|
|
.collect::<String>();
|
|
|
|
(Outline(vec![]), html, None)
|
|
|
|
}
|
2024-07-03 23:34:31 +02:00
|
|
|
|
2024-07-05 13:59:07 +02:00
|
|
|
fn render<'s, 'p, 'html>(
|
|
|
|
self,
|
|
|
|
sack: &'s Sack,
|
|
|
|
parsed: impl Renderable + 'p,
|
|
|
|
_: Outline,
|
|
|
|
_: Option<Vec<String>>,
|
|
|
|
) -> impl Renderable + 'html
|
|
|
|
where
|
|
|
|
's: 'html,
|
|
|
|
'p: 'html,
|
|
|
|
{
|
|
|
|
show(self, sack, parsed)
|
|
|
|
}
|
2024-07-03 23:34:31 +02:00
|
|
|
|
2024-07-05 13:59:07 +02:00
|
|
|
fn as_link(&self, path: Utf8PathBuf) -> Option<Linkable> {
|
|
|
|
Some(Linkable::Date(LinkDate {
|
|
|
|
link: Link {
|
|
|
|
path,
|
|
|
|
name: self.title.to_owned(),
|
|
|
|
desc: self.desc.to_owned(),
|
|
|
|
},
|
|
|
|
date: self.date.to_owned(),
|
|
|
|
}))
|
|
|
|
}
|
2024-07-03 23:34:31 +02:00
|
|
|
}
|
|
|
|
|
2024-07-05 13:59:07 +02:00
|
|
|
pub fn show<'s, 'p, 'html>(
|
|
|
|
fm: Slideshow,
|
|
|
|
sack: &'s Sack,
|
|
|
|
slides: impl Renderable + 'p,
|
|
|
|
) -> impl Renderable + 'html
|
|
|
|
where
|
|
|
|
's: 'html,
|
|
|
|
'p: 'html,
|
2024-07-03 23:34:31 +02:00
|
|
|
{
|
2024-07-05 13:59:07 +02:00
|
|
|
crate::html::bare(
|
|
|
|
sack,
|
|
|
|
maud_move!(
|
|
|
|
div .reveal {
|
|
|
|
div .slides {
|
|
|
|
(slides)
|
|
|
|
}
|
|
|
|
}
|
2024-07-03 23:34:31 +02:00
|
|
|
|
2024-07-05 13:59:07 +02:00
|
|
|
script type="module" {
|
|
|
|
(Raw("import 'reveal';"))
|
|
|
|
}
|
2024-07-03 23:34:31 +02:00
|
|
|
|
2024-07-05 13:59:07 +02:00
|
|
|
style { (Raw(CSS)) }
|
|
|
|
),
|
|
|
|
fm.title.clone(),
|
|
|
|
)
|
2024-07-03 23:34:31 +02:00
|
|
|
}
|