diff --git a/crates/editor/src/display_map.rs b/crates/editor/src/display_map.rs index 5644d63c37..9a7178e195 100644 --- a/crates/editor/src/display_map.rs +++ b/crates/editor/src/display_map.rs @@ -285,20 +285,29 @@ impl DisplayMap { .update(cx, |map, cx| map.set_wrap_width(width, cx)) } - pub fn splice_inlay_hints( + pub fn splice_inlays( &mut self, new_hints: &HashMap>, cx: &mut ModelContext, ) { - let multi_buffer = self.buffer.read(cx); - let multi_snapshot = multi_buffer.snapshot(cx); + let buffer_snapshot = self.buffer.read(cx).snapshot(cx); + let edits = self.buffer_subscription.consume().into_inner(); + let tab_size = Self::tab_size(&self.buffer, cx); + let (snapshot, edits) = self.fold_map.read(buffer_snapshot.clone(), edits); + let (snapshot, edits) = self.suggestion_map.sync(snapshot, edits); + let (snapshot, edits) = self.inlay_map.sync(snapshot, edits); + let (snapshot, edits) = self.tab_map.sync(snapshot, edits, tab_size); + let (snapshot, edits) = self + .wrap_map + .update(cx, |map, cx| map.sync(snapshot, edits, cx)); + self.block_map.read(snapshot, edits); - let mut hints_to_add = Vec::new(); + let mut new_inlays = Vec::new(); for (&location, hints) in new_hints { for hint in hints { let hint_anchor = - multi_snapshot.anchor_in_excerpt(location.excerpt_id, hint.position); - hints_to_add.push(( + buffer_snapshot.anchor_in_excerpt(location.excerpt_id, hint.position); + new_inlays.push(( location, InlayProperties { position: hint_anchor, @@ -308,11 +317,16 @@ impl DisplayMap { } } - self.inlay_map.splice( + let (snapshot, edits, _) = self.inlay_map.splice( // TODO kb this is wrong, calc diffs in the editor instead. self.inlay_map.inlays.keys().copied().collect(), - hints_to_add, + new_inlays, ); + let (snapshot, edits) = self.tab_map.sync(snapshot, edits, tab_size); + let (snapshot, edits) = self + .wrap_map + .update(cx, |map, cx| map.sync(snapshot, edits, cx)); + self.block_map.read(snapshot, edits); } fn tab_size(buffer: &ModelHandle, cx: &mut ModelContext) -> NonZeroU32 { diff --git a/crates/editor/src/display_map/inlay_map.rs b/crates/editor/src/display_map/inlay_map.rs index 66be89b5e4..c2b5dcc0d2 100644 --- a/crates/editor/src/display_map/inlay_map.rs +++ b/crates/editor/src/display_map/inlay_map.rs @@ -23,6 +23,7 @@ use parking_lot::Mutex; use project::InlayHint; use rand::Rng; use sum_tree::{Bias, Cursor, SumTree}; +use text::Patch; use util::post_inc; #[derive(Clone, Copy, Debug, Default, PartialEq, Eq, PartialOrd, Ord, Hash)] @@ -372,10 +373,11 @@ impl InlayMap { } } + let mut inlay_edits = Patch::default(); let mut new_transforms = SumTree::new(); let mut cursor = snapshot .transforms - .cursor::<(InlayPoint, SuggestionPoint)>(); + .cursor::<(InlayPoint, (SuggestionPoint, InlayOffset))>(); for ((inlay_point, inlay_id), inlay) in inlays { new_transforms.push_tree(cursor.slice(&inlay_point, Bias::Right, &()), &()); while let Some(transform) = cursor.item() { @@ -387,6 +389,11 @@ impl InlayMap { cursor.next(&()); } else { if inlay.id == inlay_id.0 { + let new_start = InlayOffset(new_transforms.summary().output.len); + inlay_edits.push(Edit { + old: cursor.start().1 .1..cursor.end(&()).1 .1, + new: new_start..new_start, + }); cursor.next(&()); } break; @@ -396,11 +403,14 @@ impl InlayMap { } if let Some(inlay) = inlay { + let new_start = InlayOffset(new_transforms.summary().output.len); + let new_end = InlayOffset(new_start.0 + inlay.properties.text.len()); if let Some(Transform::Isomorphic(transform)) = cursor.item() { let prefix = inlay_point.0 - cursor.start().0 .0; if !prefix.is_zero() { - let prefix_suggestion_start = cursor.start().1; - let prefix_suggestion_end = SuggestionPoint(cursor.start().1 .0 + prefix); + let prefix_suggestion_start = cursor.start().1 .0; + let prefix_suggestion_end = + SuggestionPoint(cursor.start().1 .0 .0 + prefix); new_transforms.push( Transform::Isomorphic( snapshot.suggestion_snapshot.text_summary_for_range( @@ -413,8 +423,8 @@ impl InlayMap { new_transforms.push(Transform::Inlay(inlay), &()); - let suffix_suggestion_start = SuggestionPoint(cursor.start().1 .0 + prefix); - let suffix_suggestion_end = cursor.end(&()).1; + let suffix_suggestion_start = SuggestionPoint(cursor.start().1 .0 .0 + prefix); + let suffix_suggestion_end = cursor.end(&()).1 .0; new_transforms.push( Transform::Isomorphic(snapshot.suggestion_snapshot.text_summary_for_range( suffix_suggestion_start..suffix_suggestion_end, @@ -426,6 +436,12 @@ impl InlayMap { } else { new_transforms.push(Transform::Inlay(inlay), &()); } + + let old_start = snapshot.to_offset(inlay_point); + inlay_edits.push(Edit { + old: old_start..old_start, + new: new_start..new_end, + }); } } @@ -434,7 +450,7 @@ impl InlayMap { snapshot.transforms = new_transforms; snapshot.version += 1; - (snapshot.clone(), Vec::new(), new_ids) + (snapshot.clone(), inlay_edits.into_inner(), new_ids) } } diff --git a/crates/editor/src/editor.rs b/crates/editor/src/editor.rs index 9560aa707e..b73a02d9c3 100644 --- a/crates/editor/src/editor.rs +++ b/crates/editor/src/editor.rs @@ -2702,7 +2702,7 @@ impl Editor { editor .update(&mut cx, |editor, cx| { editor.display_map.update(cx, |display_map, cx| { - display_map.splice_inlay_hints(&new_hints, cx); + display_map.splice_inlays(&new_hints, cx); }); }) .log_err()