From 07ecf526a689c3904e7f86015ef938eafe6d5b2f Mon Sep 17 00:00:00 2001 From: Divyanshu Gupta Date: Fri, 16 Oct 2026 03:21:50 +0530 Subject: [PATCH] fix(formats): support case-insensitive and spaced !important in HTML CSS --- crates/formats/src/html.rs | 32 +++++++++++++++++++++++++++++++- 1 file changed, 31 insertions(+), 1 deletion(-) diff --git a/crates/formats/src/html.rs b/crates/formats/src/html.rs index 7f29a9bf2..838965e7a 100644 --- a/crates/formats/src/html.rs +++ b/crates/formats/src/html.rs @@ -506,12 +506,23 @@ fn css_len_pt(v: &str) -> Option { } } +fn strip_important(v: &str) -> &str { + let s = v.trim(); + if let Some(pos) = s.rfind('!') { + let after = s[pos + 1..].trim(); + if after.eq_ignore_ascii_case("important") { + return s[..pos].trim(); + } + } + s +} + /// Apply a `style` attribute to formatting / block properties. fn apply_style(css: &str, f: &mut Fmt, align: &mut Option, preserve: &mut bool, page_break: &mut bool) { for decl in css.split(';').take(64) { let Some((k, v)) = decl.split_once(':') else { continue }; let k = k.trim().to_ascii_lowercase(); - let v = v.trim().trim_end_matches("!important").trim(); + let v = strip_important(v); let lv = v.to_ascii_lowercase(); match k.as_str() { "font-weight" => f.bold = lv.starts_with("bold") || lv.parse::().is_ok_and(|w| w >= 600), @@ -1785,4 +1796,23 @@ mod tests { fn entities() { assert_eq!(unescape("a <b> AB &bogus; &"), "a AB &bogus; &"); } + + #[test] + fn css_important_casing_and_spacing() { + let f = parse("

Styled

"); + assert_eq!(f.blocks.len(), 1); + let p = match &f.blocks[0] { + FBlock::Para(p) => p, + b => panic!("expected para, got {b:?}"), + }; + assert_eq!(p.align, Some(Align::Center)); + match &p.inlines[0] { + Inline::Text(_, fmt) => { + assert_eq!(fmt.color, Some(wordcraft_doc::props::Rgb(0xFF, 0x00, 0x00))); + assert_eq!(fmt.size, Some(16.0)); + assert!(fmt.bold); + } + i => panic!("expected text inline, got {i:?}"), + } + } }