aboutsummaryrefslogtreecommitdiffstats
path: root/src/construct/partial_title.rs
diff options
context:
space:
mode:
authorLibravatar Titus Wormer <tituswormer@gmail.com>2022-06-28 14:18:17 +0200
committerLibravatar Titus Wormer <tituswormer@gmail.com>2022-06-28 14:18:17 +0200
commitdfd11b1bc155ae1fba9975a90c2dc83dc07697b4 (patch)
tree0dd150365a6ae1df4c4845518efafe02ab61cb77 /src/construct/partial_title.rs
parenta3dd207e3b1ebcbcb6cec0f703a695e51ae4ece0 (diff)
downloadmarkdown-rs-dfd11b1bc155ae1fba9975a90c2dc83dc07697b4.tar.gz
markdown-rs-dfd11b1bc155ae1fba9975a90c2dc83dc07697b4.tar.bz2
markdown-rs-dfd11b1bc155ae1fba9975a90c2dc83dc07697b4.zip
Fix jumps in `edit_map`
* Use resolve more often (e.g., heading (atx, setext)) * Fix to link whole phrasing (e.g., one big chunk of text in heading (atx, setext), titles, labels) * Replace `ChunkText`, `ChunkString`, with `event.content_type: Option<ContentType>` * Refactor to externalize `edit_map` from `label`
Diffstat (limited to 'src/construct/partial_title.rs')
-rw-r--r--src/construct/partial_title.rs67
1 files changed, 25 insertions, 42 deletions
diff --git a/src/construct/partial_title.rs b/src/construct/partial_title.rs
index 78ae311..b102f7e 100644
--- a/src/construct/partial_title.rs
+++ b/src/construct/partial_title.rs
@@ -31,9 +31,11 @@
//!
//! <!-- To do: link label end. -->
-use crate::construct::partial_space_or_tab::space_or_tab;
-use crate::subtokenize::link_to;
-use crate::tokenizer::{Code, State, StateFnResult, TokenType, Tokenizer};
+use super::partial_space_or_tab::{
+ space_or_tab_one_line_ending_with_options, OneLineEndingOptions,
+};
+use crate::subtokenize::link;
+use crate::tokenizer::{Code, ContentType, State, StateFnResult, TokenType, Tokenizer};
/// Configuration.
///
@@ -108,8 +110,8 @@ impl Kind {
/// State needed to parse titles.
#[derive(Debug)]
struct Info {
- /// Whether we’ve seen our first `ChunkString`.
- connect_index: Option<usize>,
+ /// Whether we’ve seen data.
+ connect: bool,
/// Kind of title.
kind: Kind,
/// Configuration.
@@ -127,7 +129,7 @@ pub fn start(tokenizer: &mut Tokenizer, code: Code, options: Options) -> StateFn
match code {
Code::Char(char) if char == '"' || char == '\'' || char == '(' => {
let info = Info {
- connect_index: None,
+ connect: false,
kind: Kind::from_char(char),
options,
};
@@ -181,14 +183,24 @@ fn at_break(tokenizer: &mut Tokenizer, code: Code, mut info: Info) -> StateFnRes
begin(tokenizer, code, info)
}
Code::None => (State::Nok, None),
+ Code::CarriageReturnLineFeed | Code::Char('\r' | '\n') => tokenizer.go(
+ space_or_tab_one_line_ending_with_options(OneLineEndingOptions {
+ content_type: Some(ContentType::String),
+ connect: info.connect,
+ }),
+ |t, c| {
+ info.connect = true;
+ at_break(t, c, info)
+ },
+ )(tokenizer, code),
_ => {
- tokenizer.enter(TokenType::ChunkString);
+ tokenizer.enter_with_content(TokenType::Data, Some(ContentType::String));
- if let Some(connect_index) = info.connect_index {
+ if info.connect {
let index = tokenizer.events.len() - 1;
- link_to(&mut tokenizer.events, connect_index, index);
+ link(&mut tokenizer.events, index);
} else {
- info.connect_index = Some(tokenizer.events.len() - 1);
+ info.connect = true;
}
title(tokenizer, code, info)
@@ -196,30 +208,6 @@ fn at_break(tokenizer: &mut Tokenizer, code: Code, mut info: Info) -> StateFnRes
}
}
-/// After a line ending.
-///
-/// ```markdown
-/// "a
-/// |b"
-/// ```
-fn line_start(tokenizer: &mut Tokenizer, code: Code, info: Info) -> StateFnResult {
- tokenizer.attempt_opt(space_or_tab(), |t, c| line_begin(t, c, info))(tokenizer, code)
-}
-
-/// After a line ending, after optional whitespace.
-///
-/// ```markdown
-/// "a
-/// |b"
-/// ```
-fn line_begin(tokenizer: &mut Tokenizer, code: Code, info: Info) -> StateFnResult {
- match code {
- // Blank line not allowed.
- Code::CarriageReturnLineFeed | Code::Char('\r' | '\n') => (State::Nok, None),
- _ => at_break(tokenizer, code, info),
- }
-}
-
/// In title text.
///
/// ```markdown
@@ -228,18 +216,13 @@ fn line_begin(tokenizer: &mut Tokenizer, code: Code, info: Info) -> StateFnResul
fn title(tokenizer: &mut Tokenizer, code: Code, info: Info) -> StateFnResult {
match code {
Code::Char(char) if char == info.kind.as_char() => {
- tokenizer.exit(TokenType::ChunkString);
+ tokenizer.exit(TokenType::Data);
at_break(tokenizer, code, info)
}
- Code::None => {
- tokenizer.exit(TokenType::ChunkString);
+ Code::None | Code::CarriageReturnLineFeed | Code::Char('\r' | '\n') => {
+ tokenizer.exit(TokenType::Data);
at_break(tokenizer, code, info)
}
- Code::CarriageReturnLineFeed | Code::Char('\r' | '\n') => {
- tokenizer.consume(code);
- tokenizer.exit(TokenType::ChunkString);
- (State::Fn(Box::new(|t, c| line_start(t, c, info))), None)
- }
Code::Char('\\') => {
tokenizer.consume(code);
(State::Fn(Box::new(|t, c| escape(t, c, info))), None)