///|
/// Block lines.
///
/// In CommonMark blocks, a "line" does not necessarily correspond to
/// a line in the source plain text. For example the lines of a
/// paragraph in a block quote are the lines stripped from the block
/// quote markers. We call the line resulting from stripping the
/// block structure preceeding a given block a {e block line}.
pub(all) struct BlockLine(Node[String])
///|
pub type BlockLineBlank = Node[Blanks]
///|
pub fn BlockLine::to_string(self : BlockLine) -> String {
self.0.v
}
///|
pub fn BlockLine::list_text_loc(ls : Seq[BlockLine]) -> TextLoc {
match ls.0 {
[] => TextLoc::none()
[head] => head.meta.loc
[head, .., last] => head.meta.loc.reloc(last.meta.loc)
}
}
///|
/// Tight block lines: a block line with its initial blanks trimmed but kept for layout.
pub(all) struct Tight {
blanks : Blanks
node : StringNode
} derive(Eq, Debug)
///|
#deprecated
#doc(hidden)
pub extend Tight with Eq::{not_equal, equal}
///|
#deprecated
#doc(hidden)
pub extend Tight with @debug.Debug::{to_repr}
///|
pub fn Tight::empty(meta~ : Meta = Meta::none()) -> Tight {
{ blanks: "", node: StringNode::empty(meta~), }
}
///|
pub fn Tight::to_string(self : Tight) -> String {
self.node.v
}
///|
pub fn Tight::list_text_loc(ls : Seq[Tight]) -> TextLoc {
match ls.0 {
[] => TextLoc::none()
[head] => head.node.meta.loc
[head, .., last] => head.node.meta.loc.reloc(last.node.meta.loc)
}
}
// fn BlockLine::flush(
// meta~ : Meta = Meta::none(),
// s : String,
// start : Int,
// last : Int,
// acc : Array[StringNode]
// ) -> Unit {
// acc.push({ meta, v: s.substring(start~, end=last + 1) })
// }
///|
fn BlockLine::flush_tight(
meta~ : Meta = Meta::none(),
s : String,
start : Int32,
last : Int32,
acc : Array[Tight],
) -> Unit {
// If [s] has newlines, blanks after newlines are layout
if start > last {
acc.push(Tight::empty(meta~))
return
}
// On the first line the blanks are legit
if acc.is_empty() {
acc.push({ blanks: "", node: { meta, v: s[start:last + 1].to_owned(), }, })
return
}
let nb = @cmark_base.first_non_blank(s, last~, start~)
acc.push({
blanks: s[start:nb].to_owned(),
node: { meta, v: s[nb:last + 1].to_owned(), },
})
}