Extract pdf texture into a method

This commit is contained in:
Laurenz Stampfl 2025-07-19 23:52:27 +02:00
parent 4b733b5f8b
commit 9bacb89fc8
3 changed files with 58 additions and 53 deletions

1
Cargo.lock generated
View File

@ -3258,6 +3258,7 @@ dependencies = [
"comemo",
"ecow",
"flate2",
"hayro",
"image",
"ttf-parser",
"typst-library",

View File

@ -7,7 +7,7 @@ use tiny_skia::IntSize;
use typst_library::foundations::Smart;
use typst_library::layout::Size;
use typst_library::text::{FontBook, FontStretch, FontStyle, FontVariant, FontWeight};
use typst_library::visualize::{Image, ImageKind, ImageScaling};
use typst_library::visualize::{Image, ImageKind, ImageScaling, PdfImage};
use crate::{AbsExt, State};
@ -101,59 +101,62 @@ fn build_texture(image: &Image, w: u32, h: u32) -> Option<Arc<sk::Pixmap>> {
texture
}
ImageKind::Pdf(pdf) => {
let sf = pdf.standard_fonts().clone();
let select_standard_font = move |font: StandardFont| -> Option<FontData> {
let bytes = match font {
StandardFont::Helvetica => sf.helvetica.normal.clone(),
StandardFont::HelveticaBold => sf.helvetica.bold.clone(),
StandardFont::HelveticaOblique => sf.helvetica.italic.clone(),
StandardFont::HelveticaBoldOblique => {
sf.helvetica.bold_italic.clone()
}
StandardFont::Courier => sf.courier.normal.clone(),
StandardFont::CourierBold => sf.courier.bold.clone(),
StandardFont::CourierOblique => sf.courier.italic.clone(),
StandardFont::CourierBoldOblique => sf.courier.bold_italic.clone(),
StandardFont::TimesRoman => sf.times.normal.clone(),
StandardFont::TimesBold => sf.times.bold.clone(),
StandardFont::TimesItalic => sf.times.italic.clone(),
StandardFont::TimesBoldItalic => sf.times.bold_italic.clone(),
StandardFont::ZapfDingBats => sf.zapf_dingbats.clone(),
StandardFont::Symbol => sf.symbol.clone(),
};
bytes.map(|d| {
let font_data: Arc<dyn AsRef<[u8]> + Send + Sync> =
Arc::new(d.clone());
font_data
})
};
let interpreter_settings = InterpreterSettings {
font_resolver: Arc::new(move |query| match query {
FontQuery::Standard(s) => select_standard_font(*s),
FontQuery::Fallback(f) => {
select_standard_font(f.pick_standard_font())
}
}),
warning_sink: Arc::new(|_| {}),
};
let page = pdf.page();
let render_settings = RenderSettings {
x_scale: w as f32 / pdf.width(),
y_scale: h as f32 / pdf.height(),
width: Some(w as u16),
height: Some(h as u16),
};
let hayro_pix = hayro::render(page, &interpreter_settings, &render_settings);
sk::Pixmap::from_vec(hayro_pix.take_u8(), IntSize::from_wh(w, h)?)?
}
ImageKind::Pdf(pdf) => build_pdf_texture(pdf, w, h)?,
};
Some(Arc::new(texture))
}
fn build_pdf_texture(pdf: &PdfImage, w: u32, h: u32) -> Option<sk::Pixmap> {
let sf = pdf.standard_fonts().clone();
let select_standard_font = move |font: StandardFont| -> Option<FontData> {
let bytes = match font {
StandardFont::Helvetica => sf.helvetica.normal.clone(),
StandardFont::HelveticaBold => sf.helvetica.bold.clone(),
StandardFont::HelveticaOblique => sf.helvetica.italic.clone(),
StandardFont::HelveticaBoldOblique => {
sf.helvetica.bold_italic.clone()
}
StandardFont::Courier => sf.courier.normal.clone(),
StandardFont::CourierBold => sf.courier.bold.clone(),
StandardFont::CourierOblique => sf.courier.italic.clone(),
StandardFont::CourierBoldOblique => sf.courier.bold_italic.clone(),
StandardFont::TimesRoman => sf.times.normal.clone(),
StandardFont::TimesBold => sf.times.bold.clone(),
StandardFont::TimesItalic => sf.times.italic.clone(),
StandardFont::TimesBoldItalic => sf.times.bold_italic.clone(),
StandardFont::ZapfDingBats => sf.zapf_dingbats.clone(),
StandardFont::Symbol => sf.symbol.clone(),
};
bytes.map(|d| {
let font_data: Arc<dyn AsRef<[u8]> + Send + Sync> =
Arc::new(d.clone());
font_data
})
};
let interpreter_settings = InterpreterSettings {
font_resolver: Arc::new(move |query| match query {
FontQuery::Standard(s) => select_standard_font(*s),
FontQuery::Fallback(f) => {
select_standard_font(f.pick_standard_font())
}
}),
warning_sink: Arc::new(|_| {}),
};
let page = pdf.page();
let render_settings = RenderSettings {
x_scale: w as f32 / pdf.width(),
y_scale: h as f32 / pdf.height(),
width: Some(w as u16),
height: Some(h as u16),
};
let hayro_pix = hayro::render(page, &interpreter_settings, &render_settings);
sk::Pixmap::from_vec(hayro_pix.take_u8(), IntSize::from_wh(w, h)?)
}

View File

@ -21,6 +21,7 @@ base64 = { workspace = true }
comemo = { workspace = true }
ecow = { workspace = true }
flate2 = { workspace = true }
hayro = { workspace = true }
image = { workspace = true }
ttf-parser = { workspace = true }
xmlparser = { workspace = true }