From 58adf1d025bd7ff149d7fd06147b0f3e069f8c7d Mon Sep 17 00:00:00 2001 From: Martin Haug Date: Sun, 12 Feb 2023 23:32:14 +0100 Subject: [PATCH] Add XMP --- Cargo.lock | 6 ++++++ Cargo.toml | 1 + src/export/pdf/mod.rs | 20 ++++++++++++++++++++ 3 files changed, 27 insertions(+) diff --git a/Cargo.lock b/Cargo.lock index a4c224cb2..d28bb206c 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1191,6 +1191,7 @@ dependencies = [ "unicode-xid", "unscanny", "usvg", + "xmp-writer", ] [[package]] @@ -1565,6 +1566,11 @@ version = "0.13.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4d25c75bf9ea12c4040a97f829154768bbbce366287e2dc044af160cd79a13fd" +[[package]] +name = "xmp-writer" +version = "0.1.0" +source = "git+https://github.com/typst/xmp-writer#a4a36967cd73c9c19548e940bbcc55583a901417" + [[package]] name = "yaml-front-matter" version = "0.1.0" diff --git a/Cargo.toml b/Cargo.toml index b2db54244..8bd8e67e7 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -40,6 +40,7 @@ unicode-segmentation = "1" unicode-xid = "0.2" unscanny = "0.1" usvg = { version = "0.22", default-features = false } +xmp-writer = { git = "https://github.com/typst/xmp-writer" } [profile.dev] debug = 0 diff --git a/src/export/pdf/mod.rs b/src/export/pdf/mod.rs index 60cd4ea2f..38433211c 100644 --- a/src/export/pdf/mod.rs +++ b/src/export/pdf/mod.rs @@ -11,6 +11,7 @@ use std::hash::Hash; use pdf_writer::types::Direction; use pdf_writer::{Finish, Name, PdfWriter, Ref, TextStr}; +use xmp_writer::{LangId, RenditionClass, XmpWriter}; use self::outline::HeadingNode; use self::page::Page; @@ -115,20 +116,39 @@ fn write_catalog(ctx: &mut PdfContext) { }; // Write the document information. + let meta_ref = ctx.alloc.bump(); + let mut xmp = XmpWriter::new(); + let mut info = ctx.writer.document_info(ctx.alloc.bump()); if let Some(title) = &ctx.document.title { info.title(TextStr(title)); + xmp.title([(None, title.as_str())]); } if let Some(author) = &ctx.document.author { info.author(TextStr(author)); + xmp.creator([(author.as_str())]); } info.creator(TextStr("Typst")); + xmp.creator_tool("Typst"); + xmp.num_pages(ctx.document.pages.len() as u32); + xmp.format("application/pdf"); + xmp.language(ctx.languages.keys().map(|lang| LangId(lang.as_str()))); + xmp.rendition_class(RenditionClass::Proof); + xmp.pdf_version("1.7"); + info.finish(); + let xmp_buf = xmp.finish(None); + let mut meta_stream = ctx.writer.stream(meta_ref, &xmp_buf); + meta_stream.pair(Name(b"Type"), Name(b"Metadata")); + meta_stream.pair(Name(b"Subtype"), Name(b"XML")); + meta_stream.finish(); + // Write the document catalog. let mut catalog = ctx.writer.catalog(ctx.alloc.bump()); catalog.pages(ctx.page_tree_ref); catalog.viewer_preferences().direction(dir); + catalog.pair(Name(b"Metadata"), meta_ref); if let Some(outline_root_id) = outline_root_id { catalog.outlines(outline_root_id);