diff options
| author | metamuffin <metamuffin@disroot.org> | 2026-02-21 12:09:59 +0100 |
|---|---|---|
| committer | metamuffin <metamuffin@disroot.org> | 2026-02-21 12:09:59 +0100 |
| commit | 276da3a082333b2287eca2e0fb2127fc6d1619e5 (patch) | |
| tree | d0240b797455d571ceb39c1d57dd27d98ea955aa | |
| parent | 356bc5fe6913e85b18a2cb355f30019cdfd6b146 (diff) | |
| download | jellything-276da3a082333b2287eca2e0fb2127fc6d1619e5.tar jellything-276da3a082333b2287eca2e0fb2127fc6d1619e5.tar.bz2 jellything-276da3a082333b2287eca2e0fb2127fc6d1619e5.tar.zst | |
person fallback images
| -rw-r--r-- | common/src/routes.rs | 3 | ||||
| -rw-r--r-- | import/fallback_generator/src/lib.rs | 4 | ||||
| -rw-r--r-- | import/src/lib.rs | 2 | ||||
| -rw-r--r-- | server/src/routes.rs | 3 | ||||
| -rw-r--r-- | server/src/ui/assets.rs | 20 | ||||
| -rw-r--r-- | ui/src/components/node_card.rs | 18 |
6 files changed, 43 insertions, 7 deletions
diff --git a/common/src/routes.rs b/common/src/routes.rs index 82a6f45..3ee1e4c 100644 --- a/common/src/routes.rs +++ b/common/src/routes.rs @@ -21,6 +21,9 @@ pub fn u_node_slug_player_time(node: &str, time: f64) -> String { pub fn u_image(path: &str, size: usize) -> String { format!("/image/{path}?size={size}") } +pub fn u_image_fallback_person(name: &str, size: usize) -> String { + format!("/image_fallback/person/{name}?size={size}") +} pub fn u_node_slug_watched(node: &str, state: &str) -> String { format!("/n/{node}/watched?state={state}") } diff --git a/import/fallback_generator/src/lib.rs b/import/fallback_generator/src/lib.rs index 60b8cc5..d24356d 100644 --- a/import/fallback_generator/src/lib.rs +++ b/import/fallback_generator/src/lib.rs @@ -5,7 +5,7 @@ use image::{DynamicImage, ImageBuffer, ImageEncoder, Rgba, codecs::qoi::QoiEncod use imageproc::drawing::{draw_text_mut, text_size}; use std::hash::{Hash, Hasher}; -pub fn generate_fallback(name: &str) -> Result<Vec<u8>> { +pub fn generate_person_fallback(name: &str) -> Result<Vec<u8>> { let width = 1024; let height = (width * 1000) / 707; @@ -102,5 +102,5 @@ fn random_accent(text: &str, y: f32) -> Rgba<f32> { #[test] fn generate_fallback_test() { - generate_fallback("Hello world!").unwrap(); + generate_person_fallback("Hello world!").unwrap(); } diff --git a/import/src/lib.rs b/import/src/lib.rs index 7e402be..ceda42f 100644 --- a/import/src/lib.rs +++ b/import/src/lib.rs @@ -42,6 +42,8 @@ use std::{ }; use tokio::{runtime::Handle, sync::Semaphore, task::spawn_blocking}; +pub use jellyimport_fallback_generator::generate_person_fallback; + #[derive(Debug, Deserialize, Serialize, Default, Clone)] pub struct Config { media_path: PathBuf, diff --git a/server/src/routes.rs b/server/src/routes.rs index 4a875f4..334fb39 100644 --- a/server/src/routes.rs +++ b/server/src/routes.rs @@ -18,7 +18,7 @@ use crate::{ log::{r_admin_log, r_admin_log_stream}, r_admin_dashboard, }, - assets::r_image, + assets::{r_image, r_image_fallback_person}, error::{r_api_catch, r_catch}, home::r_home, node::r_node, @@ -95,6 +95,7 @@ pub(super) fn build_rocket(state: Arc<State>) -> Rocket<Build> { // r_admin_users, // r_items, r_image, + r_image_fallback_person, r_assets_font, r_assets_js_map, r_assets_js, diff --git a/server/src/ui/assets.rs b/server/src/ui/assets.rs index 91bb5e2..5903b83 100644 --- a/server/src/ui/assets.rs +++ b/server/src/ui/assets.rs @@ -6,7 +6,10 @@ use super::error::MyResult; use crate::{request_info::RequestInfo, responders::cache::CacheControlImage}; use anyhow::Context; -use rocket::{get, http::ContentType}; +use jellycache::HashKey; +use jellycommon::routes::u_image; +use jellyimport::generate_person_fallback; +use rocket::{get, http::ContentType, response::Redirect}; use std::path::PathBuf; use tokio::task::spawn_blocking; @@ -34,6 +37,21 @@ pub async fn r_image( Ok((ContentType::AVIF, CacheControlImage(encoded))) } +#[get("/image_fallback/person/<name>?<size>")] +pub async fn r_image_fallback_person( + ri: RequestInfo<'_>, + name: &str, + size: Option<usize>, +) -> MyResult<Redirect> { + let path = ri + .state + .cache + .store(format!("fallback/person/{}.image", HashKey(name)), || { + generate_person_fallback(name) + })?; + Ok(Redirect::found(u_image(&path, size.unwrap_or(2048)))) +} + // #[get("/n/<id>/image/<slot>?<size>")] // pub async fn r_item_poster( // session: A<Session>, diff --git a/ui/src/components/node_card.rs b/ui/src/components/node_card.rs index 1b8fd67..eb00ccc 100644 --- a/ui/src/components/node_card.rs +++ b/ui/src/components/node_card.rs @@ -10,7 +10,7 @@ use crate::{ }; use jellycommon::{ jellyobject::Object, - routes::{u_image, u_node_slug, u_node_slug_player}, + routes::{u_image, u_image_fallback_person, u_node_slug, u_node_slug_player}, *, }; @@ -22,7 +22,7 @@ markup::define! { div[class=cls] { .poster { a[href=u_node_slug(&slug)] { - img[src=u_image(node.get(NO_PICTURES).unwrap_or_default().get(PICT_COVER).unwrap_or_default(), 512), loading="lazy"]; + img[src=cover_image(&node, 512), loading="lazy"]; } .cardhover.item { @if node.has(NO_TRACK.0) { @@ -49,7 +49,7 @@ markup::define! { div[class="node card widecard poster"] { div[class=&format!("poster {}", aspect_class(node))] { a[href=u_node_slug(&slug)] { - img[src=u_image(node.get(NO_PICTURES).unwrap_or_default().get(PICT_COVER).unwrap_or_default(), 512), loading="lazy"]; + img[src=cover_image(&node, 512), loading="lazy"]; } .cardhover.item { @if node.has(NO_TRACK.0) { @@ -65,3 +65,15 @@ markup::define! { } } } + +fn cover_image(node: &Object, size: usize) -> String { + if let Some(cover) = node.get(NO_PICTURES).unwrap_or_default().get(PICT_COVER) { + return u_image(cover, size); + } + if let Some(title) = node.get(NO_TITLE) + && node.get(NO_KIND) == Some(KIND_PERSON) + { + return u_image_fallback_person(title, 512); + } + return String::new(); +} |