From 642e149464341e3cf1856dda51d7f7a5b387081e Mon Sep 17 00:00:00 2001 From: Laurenz Date: Wed, 9 Feb 2022 17:45:04 +0100 Subject: [PATCH] Incremental bug fixes Co-Authored-By: Martin Haug --- src/layout/mod.rs | 2 +- src/parse/incremental.rs | 25 +++++++++++++++++++------ src/source.rs | 14 ++++++++++---- src/util/prehashed.rs | 4 +++- 4 files changed, 33 insertions(+), 12 deletions(-) diff --git a/src/layout/mod.rs b/src/layout/mod.rs index 139d027aa..7755f84c0 100644 --- a/src/layout/mod.rs +++ b/src/layout/mod.rs @@ -172,7 +172,7 @@ impl Layout for LayoutNode { let styles = styles.barred(self.id()); #[cfg(not(feature = "layout-cache"))] - return self.node.layout(ctx, regions, styles); + return self.0.layout(ctx, regions, styles); #[cfg(feature = "layout-cache")] let hash = { diff --git a/src/parse/incremental.rs b/src/parse/incremental.rs index 33aa12be2..7418dd584 100644 --- a/src/parse/incremental.rs +++ b/src/parse/incremental.rs @@ -176,7 +176,9 @@ impl Reparser<'_> { let child = &mut green.children_mut()[superseded_range.start]; let prev_len = child.len(); - if last_kind.succession_rule() != SuccessionRule::Unsafe { + if last_kind.succession_rule() != SuccessionRule::Unsafe + && !matches!(last_kind, NodeKind::Strong | NodeKind::Emph) + { if let Some(range) = match child { Green::Node(node) => self.reparse_step( Arc::make_mut(node), @@ -384,11 +386,21 @@ fn validate( } if child.kind().neighbour_rule() == NeighbourRule::AtStart { - let child_col = s.column(child_pos); + let child_col = s.column(child_pos) + + match child.kind() { + NodeKind::Heading => child + .children() + .iter() + .filter(|n| n.kind() == &NodeKind::Eq) + .count(), + NodeKind::List => 1, + NodeKind::Enum => child.children().first().unwrap().len(), + _ => 0, + }; let mut right_pos = newborn_span.end; for child in &superseded[superseded_range.end ..] { - if child.kind().is_trivia() { + if child.kind().is_trivia() || child.kind() == &NodeKind::Parbreak { right_pos += child.len(); continue; } @@ -439,6 +451,7 @@ impl NodeKind { match self { // These are all replaceable by other tokens. Self::Linebreak + | Self::Parbreak | Self::Text(_) | Self::TextInLine(_) | Self::NonBreakingSpace @@ -574,9 +587,6 @@ impl NodeKind { | Self::Include | Self::From => SuccessionRule::Unsafe, - // This can affect whether strong or emph content ends. - Self::Parbreak => SuccessionRule::Unsafe, - // This element always has to remain in the same column so better // reparse the whole parent. Self::Raw(_) => SuccessionRule::Unsafe, @@ -635,6 +645,9 @@ mod tests { test("", 0..0, "do it", 0..5); test("a d e", 1 .. 3, " b c d", 0 .. 9); test("a #f() e", 1 .. 6, " b c d", 0 .. 9); + test("a\nb\nc\nd\ne\n", 5..5, "c", 3..8); + test("a\n\nb\n\nc\n\nd\n\ne\n", 7..7, "c", 4..11); + test("a\nb\nc *hel a b lo* d\nd\ne", 13..13, "c ", 6..20); test("{a}", 1 .. 2, "b", 1 .. 2); test("{(0, 1, 2)}", 5 .. 6, "11pt", 5 .. 9); test("\n= A heading", 3 .. 3, "n evocative", 1 .. 23); diff --git a/src/source.rs b/src/source.rs index 0e7b4c635..2a134d9a2 100644 --- a/src/source.rs +++ b/src/source.rs @@ -108,11 +108,17 @@ impl SourceStore { /// Edit a source file by replacing the given range. /// - /// This panics if no source file with this `id` exists or if the `replace` - /// range is out of bounds for the source file identified by `id`. + /// Returns the range of the section in the new source that was ultimately + /// reparsed. This panics if no source file with this `id` exists or if the + /// `replace` range is out of bounds. #[track_caller] - pub fn edit(&mut self, id: SourceId, replace: Range, with: &str) { - self.sources[id.0 as usize].edit(replace, with); + pub fn edit( + &mut self, + id: SourceId, + replace: Range, + with: &str, + ) -> Range { + self.sources[id.0 as usize].edit(replace, with) } } diff --git a/src/util/prehashed.rs b/src/util/prehashed.rs index bab1c8f80..866bda5bf 100644 --- a/src/util/prehashed.rs +++ b/src/util/prehashed.rs @@ -1,8 +1,10 @@ -use std::any::Any; use std::fmt::{self, Debug, Formatter}; use std::hash::{Hash, Hasher}; use std::ops::Deref; +#[cfg(feature = "layout-cache")] +use std::any::Any; + /// A wrapper around a type that precomputes its hash. #[derive(Copy, Clone)] pub struct Prehashed {