mirror of
https://github.com/zed-industries/zed.git
synced 2025-02-08 19:43:11 +00:00
WIP
This commit is contained in:
parent
84c36066bc
commit
c9193b586b
2 changed files with 60 additions and 26 deletions
|
@ -95,7 +95,7 @@ impl<V: Render> Element for View<V> {
|
|||
}
|
||||
|
||||
fn paint(&mut self, _: Bounds<Pixels>, element: &mut Self::State, cx: &mut WindowContext) {
|
||||
element.take().unwrap().paint(cx);
|
||||
cx.with_view_id(self.entity_id(), |cx| element.take().unwrap().paint(cx));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -272,33 +272,36 @@ impl Element for AnyView {
|
|||
}
|
||||
|
||||
fn paint(&mut self, bounds: Bounds<Pixels>, state: &mut Self::State, cx: &mut WindowContext) {
|
||||
if !self.cache {
|
||||
state.element.take().unwrap().paint(cx);
|
||||
return;
|
||||
}
|
||||
|
||||
if let Some(cache_key) = state.cache_key.as_mut() {
|
||||
if cache_key.bounds == bounds
|
||||
&& cache_key.content_mask == cx.content_mask()
|
||||
&& cache_key.stacking_order == *cx.stacking_order()
|
||||
&& cache_key.text_style == cx.text_style()
|
||||
{
|
||||
println!("could reuse geometry for view {}", self.entity_id());
|
||||
cx.with_view_id(self.entity_id(), |cx| {
|
||||
if !self.cache {
|
||||
state.element.take().unwrap().paint(cx);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
let mut element = state
|
||||
.element
|
||||
.take()
|
||||
.unwrap_or_else(|| (self.request_layout)(self, cx).1);
|
||||
element.draw(bounds.origin, bounds.size.into(), cx);
|
||||
if let Some(cache_key) = state.cache_key.as_mut() {
|
||||
if cache_key.bounds == bounds
|
||||
&& cache_key.content_mask == cx.content_mask()
|
||||
&& cache_key.stacking_order == *cx.stacking_order()
|
||||
&& cache_key.text_style == cx.text_style()
|
||||
&& !cx.window.dirty_views.contains(&self.entity_id())
|
||||
{
|
||||
println!("could reuse geometry for view {}", self.entity_id());
|
||||
}
|
||||
}
|
||||
|
||||
state.cache_key = Some(ViewCacheKey {
|
||||
bounds,
|
||||
stacking_order: cx.stacking_order().clone(),
|
||||
content_mask: cx.content_mask(),
|
||||
text_style: cx.text_style(),
|
||||
});
|
||||
let mut element = state
|
||||
.element
|
||||
.take()
|
||||
.unwrap_or_else(|| (self.request_layout)(self, cx).1);
|
||||
element.draw(bounds.origin, bounds.size.into(), cx);
|
||||
|
||||
state.cache_key = Some(ViewCacheKey {
|
||||
bounds,
|
||||
stacking_order: cx.stacking_order().clone(),
|
||||
content_mask: cx.content_mask(),
|
||||
text_style: cx.text_style(),
|
||||
});
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -12,7 +12,7 @@ use crate::{
|
|||
VisualContext, WeakView, WindowBounds, WindowOptions, SUBPIXEL_VARIANTS,
|
||||
};
|
||||
use anyhow::{anyhow, Context as _, Result};
|
||||
use collections::FxHashMap;
|
||||
use collections::{FxHashMap, FxHashSet};
|
||||
use derive_more::{Deref, DerefMut};
|
||||
use futures::{
|
||||
channel::{mpsc, oneshot},
|
||||
|
@ -256,6 +256,7 @@ pub struct Window {
|
|||
pub(crate) element_id_stack: GlobalElementId,
|
||||
pub(crate) rendered_frame: Frame,
|
||||
pub(crate) next_frame: Frame,
|
||||
pub(crate) dirty_views: FxHashSet<EntityId>,
|
||||
frame_arena: Arena,
|
||||
pub(crate) focus_handles: Arc<RwLock<SlotMap<FocusId, AtomicUsize>>>,
|
||||
focus_listeners: SubscriberSet<(), AnyWindowFocusListener>,
|
||||
|
@ -295,6 +296,8 @@ pub(crate) struct Frame {
|
|||
pub(crate) next_stacking_order_id: u32,
|
||||
content_mask_stack: Vec<ContentMask<Pixels>>,
|
||||
element_offset_stack: Vec<Point<Pixels>>,
|
||||
pub(crate) view_parents: FxHashMap<EntityId, EntityId>,
|
||||
pub(crate) view_stack: Vec<EntityId>,
|
||||
}
|
||||
|
||||
impl Frame {
|
||||
|
@ -310,6 +313,8 @@ impl Frame {
|
|||
depth_map: Default::default(),
|
||||
content_mask_stack: Vec::new(),
|
||||
element_offset_stack: Vec::new(),
|
||||
view_parents: FxHashMap::default(),
|
||||
view_stack: Vec::new(),
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -319,6 +324,8 @@ impl Frame {
|
|||
self.dispatch_tree.clear();
|
||||
self.depth_map.clear();
|
||||
self.next_stacking_order_id = 0;
|
||||
self.view_parents.clear();
|
||||
debug_assert!(self.view_stack.is_empty());
|
||||
}
|
||||
|
||||
fn focus_path(&self) -> SmallVec<[FocusId; 8]> {
|
||||
|
@ -404,6 +411,7 @@ impl Window {
|
|||
element_id_stack: GlobalElementId::default(),
|
||||
rendered_frame: Frame::new(DispatchTree::new(cx.keymap.clone(), cx.actions.clone())),
|
||||
next_frame: Frame::new(DispatchTree::new(cx.keymap.clone(), cx.actions.clone())),
|
||||
dirty_views: FxHashSet::default(),
|
||||
frame_arena: Arena::new(1024 * 1024),
|
||||
focus_handles: Arc::new(RwLock::new(SlotMap::with_key())),
|
||||
focus_listeners: SubscriberSet::new(),
|
||||
|
@ -1423,6 +1431,7 @@ impl<'a> WindowContext<'a> {
|
|||
}
|
||||
|
||||
self.window.drawing = false;
|
||||
self.window.dirty_views.clear();
|
||||
ELEMENT_ARENA.with_borrow_mut(|element_arena| element_arena.clear());
|
||||
|
||||
scene
|
||||
|
@ -2119,6 +2128,13 @@ pub trait BorrowWindow: BorrowMut<Window> + BorrowMut<AppContext> {
|
|||
result
|
||||
}
|
||||
|
||||
fn with_view_id<R>(&mut self, view_id: EntityId, f: impl FnOnce(&mut Self) -> R) -> R {
|
||||
self.window_mut().next_frame.view_stack.push(view_id);
|
||||
let result = f(self);
|
||||
self.window_mut().next_frame.view_stack.pop();
|
||||
result
|
||||
}
|
||||
|
||||
/// Update the global element offset relative to the current offset. This is used to implement
|
||||
/// scrolling.
|
||||
fn with_element_offset<R>(
|
||||
|
@ -2476,6 +2492,21 @@ impl<'a, V: 'static> ViewContext<'a, V> {
|
|||
}
|
||||
|
||||
pub fn notify(&mut self) {
|
||||
let mut dirty_view_id = Some(self.view.entity_id());
|
||||
while let Some(view_id) = dirty_view_id {
|
||||
if self.window_cx.window.dirty_views.insert(view_id) {
|
||||
dirty_view_id = self
|
||||
.window_cx
|
||||
.window
|
||||
.rendered_frame
|
||||
.view_parents
|
||||
.get(&view_id)
|
||||
.copied();
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if !self.window.drawing {
|
||||
self.window_cx.notify();
|
||||
self.window_cx.app.push_effect(Effect::Notify {
|
||||
|
|
Loading…
Reference in a new issue