mirror of
https://github.com/typst/typst
synced 2025-08-10 13:17:55 +08:00
Support quotes in HTML output.
This commit is contained in:
parent
265df6c29f
commit
8b1328de62
@ -2,8 +2,9 @@ use crate::diag::SourceResult;
|
|||||||
use crate::engine::Engine;
|
use crate::engine::Engine;
|
||||||
use crate::foundations::{
|
use crate::foundations::{
|
||||||
cast, elem, Content, Depth, Label, NativeElement, Packed, Show, ShowSet, Smart,
|
cast, elem, Content, Depth, Label, NativeElement, Packed, Show, ShowSet, Smart,
|
||||||
StyleChain, Styles,
|
StyleChain, Styles, TargetElem,
|
||||||
};
|
};
|
||||||
|
use crate::html::{tag, HtmlElem};
|
||||||
use crate::introspection::Locatable;
|
use crate::introspection::Locatable;
|
||||||
use crate::layout::{
|
use crate::layout::{
|
||||||
Alignment, BlockBody, BlockElem, Em, HElem, PadElem, Spacing, VElem,
|
Alignment, BlockBody, BlockElem, Em, HElem, PadElem, Spacing, VElem,
|
||||||
@ -158,6 +159,7 @@ impl Show for Packed<QuoteElem> {
|
|||||||
fn show(&self, _: &mut Engine, styles: StyleChain) -> SourceResult<Content> {
|
fn show(&self, _: &mut Engine, styles: StyleChain) -> SourceResult<Content> {
|
||||||
let mut realized = self.body().clone();
|
let mut realized = self.body().clone();
|
||||||
let block = self.block(styles);
|
let block = self.block(styles);
|
||||||
|
let html = TargetElem::target_in(styles).is_html();
|
||||||
|
|
||||||
if self.quotes(styles) == Smart::Custom(true) || !block {
|
if self.quotes(styles) == Smart::Custom(true) || !block {
|
||||||
let quotes = SmartQuotes::get(
|
let quotes = SmartQuotes::get(
|
||||||
@ -171,49 +173,51 @@ impl Show for Packed<QuoteElem> {
|
|||||||
let Depth(depth) = QuoteElem::depth_in(styles);
|
let Depth(depth) = QuoteElem::depth_in(styles);
|
||||||
let double = depth % 2 == 0;
|
let double = depth % 2 == 0;
|
||||||
|
|
||||||
// Add zero-width weak spacing to make the quotes "sticky".
|
if !html {
|
||||||
let hole = HElem::hole().pack();
|
// Add zero-width weak spacing to make the quotes "sticky".
|
||||||
|
let hole = HElem::hole().pack();
|
||||||
|
realized = Content::sequence([hole.clone(), realized, hole]);
|
||||||
|
}
|
||||||
realized = Content::sequence([
|
realized = Content::sequence([
|
||||||
TextElem::packed(quotes.open(double)),
|
TextElem::packed(quotes.open(double)),
|
||||||
hole.clone(),
|
|
||||||
realized,
|
realized,
|
||||||
hole,
|
|
||||||
TextElem::packed(quotes.close(double)),
|
TextElem::packed(quotes.close(double)),
|
||||||
])
|
])
|
||||||
.styled(QuoteElem::set_depth(Depth(1)));
|
.styled(QuoteElem::set_depth(Depth(1)));
|
||||||
}
|
}
|
||||||
|
|
||||||
if block {
|
if block {
|
||||||
realized = BlockElem::new()
|
realized = if html {
|
||||||
.with_body(Some(BlockBody::Content(realized)))
|
HtmlElem::new(tag::blockquote).with_body(Some(realized)).pack()
|
||||||
.pack()
|
} else {
|
||||||
.spanned(self.span());
|
BlockElem::new().with_body(Some(BlockBody::Content(realized))).pack()
|
||||||
|
}
|
||||||
|
.spanned(self.span());
|
||||||
|
|
||||||
if let Some(attribution) = self.attribution(styles).as_ref() {
|
if let Some(attribution) = self.attribution(styles).as_ref() {
|
||||||
let mut seq = vec![TextElem::packed('—'), SpaceElem::shared().clone()];
|
let attribution = match attribution {
|
||||||
|
Attribution::Content(content) => content.clone(),
|
||||||
|
Attribution::Label(label) => CiteElem::new(*label)
|
||||||
|
.with_form(Some(CitationForm::Prose))
|
||||||
|
.pack()
|
||||||
|
.spanned(self.span()),
|
||||||
|
};
|
||||||
|
let attribution =
|
||||||
|
[TextElem::packed('—'), SpaceElem::shared().clone(), attribution];
|
||||||
|
|
||||||
match attribution {
|
if !html {
|
||||||
Attribution::Content(content) => {
|
// Use v(0.9em, weak: true) to bring the attribution closer
|
||||||
seq.push(content.clone());
|
// to the quote.
|
||||||
}
|
let gap = Spacing::Rel(Em::new(0.9).into());
|
||||||
Attribution::Label(label) => {
|
let v = VElem::new(gap).with_weak(true).pack();
|
||||||
seq.push(
|
realized += v;
|
||||||
CiteElem::new(*label)
|
|
||||||
.with_form(Some(CitationForm::Prose))
|
|
||||||
.pack()
|
|
||||||
.spanned(self.span()),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
realized += Content::sequence(attribution).aligned(Alignment::END);
|
||||||
// Use v(0.9em, weak: true) bring the attribution closer to the
|
|
||||||
// quote.
|
|
||||||
let gap = Spacing::Rel(Em::new(0.9).into());
|
|
||||||
let v = VElem::new(gap).with_weak(true).pack();
|
|
||||||
realized += v + Content::sequence(seq).aligned(Alignment::END);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
realized = PadElem::new(realized).pack();
|
if !html {
|
||||||
|
realized = PadElem::new(realized).pack();
|
||||||
|
}
|
||||||
} else if let Some(Attribution::Label(label)) = self.attribution(styles) {
|
} else if let Some(Attribution::Label(label)) = self.attribution(styles) {
|
||||||
realized += SpaceElem::shared().clone()
|
realized += SpaceElem::shared().clone()
|
||||||
+ CiteElem::new(*label).pack().spanned(self.span());
|
+ CiteElem::new(*label).pack().spanned(self.span());
|
||||||
|
Loading…
x
Reference in New Issue
Block a user