This commit is contained in:
Nathan Sobo
2023-11-14 11:00:52 -07:00
parent e08f1690b3
commit bb584cc7c4
6 changed files with 82 additions and 70 deletions
@@ -32,7 +32,9 @@ pub struct CommandPalette {
impl CommandPalette {
fn register(workspace: &mut Workspace, _: &mut ViewContext<Workspace>) {
dbg!("registering command palette toggle");
workspace.register_action(|workspace, _: &Toggle, cx| {
dbg!("got cmd-shift-p");
let Some(previous_focus_handle) = cx.focused() else {
return;
};
+57 -57
View File
@@ -2446,7 +2446,7 @@ impl Element<Editor> for EditorElement {
type ElementState = ();
fn element_id(&self) -> Option<gpui::ElementId> {
None
None // todo! can we change the element trait to return an id here from the view context?
}
fn initialize(
@@ -2456,6 +2456,41 @@ impl Element<Editor> for EditorElement {
cx: &mut gpui::ViewContext<Editor>,
) -> Self::ElementState {
editor.style = Some(self.style.clone()); // Long-term, we'd like to eliminate this.
}
fn layout(
&mut self,
editor: &mut Editor,
element_state: &mut Self::ElementState,
cx: &mut gpui::ViewContext<Editor>,
) -> gpui::LayoutId {
let rem_size = cx.rem_size();
let mut style = Style::default();
style.size.width = relative(1.).into();
style.size.height = match editor.mode {
EditorMode::SingleLine => self.style.text.line_height_in_pixels(cx.rem_size()).into(),
EditorMode::AutoHeight { .. } => todo!(),
EditorMode::Full => relative(1.).into(),
};
cx.request_layout(&style, None)
}
fn paint(
&mut self,
bounds: Bounds<gpui::Pixels>,
editor: &mut Editor,
element_state: &mut Self::ElementState,
cx: &mut gpui::ViewContext<Editor>,
) {
let mut layout = self.compute_layout(editor, cx, bounds);
let gutter_bounds = Bounds {
origin: bounds.origin,
size: layout.gutter_size,
};
let text_bounds = Bounds {
origin: gutter_bounds.upper_right(),
size: layout.text_size,
};
let dispatch_context = editor.dispatch_context(cx);
cx.with_element_id(Some(cx.view().entity_id()), |cx| {
@@ -2621,63 +2656,28 @@ impl Element<Editor> for EditorElement {
register_action(cx, Editor::context_menu_prev);
register_action(cx, Editor::context_menu_next);
register_action(cx, Editor::context_menu_last);
// We call with_z_index to establish a new stacking context.
cx.with_z_index(0, |cx| {
cx.with_content_mask(Some(ContentMask { bounds }), |cx| {
self.paint_mouse_listeners(
bounds,
gutter_bounds,
text_bounds,
&layout.position_map,
cx,
);
self.paint_background(gutter_bounds, text_bounds, &layout, cx);
if layout.gutter_size.width > Pixels::ZERO {
self.paint_gutter(gutter_bounds, &mut layout, editor, cx);
}
self.paint_text(text_bounds, &mut layout, editor, cx);
let input_handler = ElementInputHandler::new(bounds, cx);
cx.handle_input(&editor.focus_handle, input_handler);
});
});
},
)
});
}
fn layout(
&mut self,
editor: &mut Editor,
element_state: &mut Self::ElementState,
cx: &mut gpui::ViewContext<Editor>,
) -> gpui::LayoutId {
let rem_size = cx.rem_size();
let mut style = Style::default();
style.size.width = relative(1.).into();
style.size.height = match editor.mode {
EditorMode::SingleLine => self.style.text.line_height_in_pixels(cx.rem_size()).into(),
EditorMode::AutoHeight { .. } => todo!(),
EditorMode::Full => relative(1.).into(),
};
cx.request_layout(&style, None)
}
fn paint(
&mut self,
bounds: Bounds<gpui::Pixels>,
editor: &mut Editor,
element_state: &mut Self::ElementState,
cx: &mut gpui::ViewContext<Editor>,
) {
let mut layout = self.compute_layout(editor, cx, bounds);
let gutter_bounds = Bounds {
origin: bounds.origin,
size: layout.gutter_size,
};
let text_bounds = Bounds {
origin: gutter_bounds.upper_right(),
size: layout.text_size,
};
// We call with_z_index to establish a new stacking context.
cx.with_z_index(0, |cx| {
cx.with_content_mask(Some(ContentMask { bounds }), |cx| {
self.paint_mouse_listeners(
bounds,
gutter_bounds,
text_bounds,
&layout.position_map,
cx,
);
self.paint_background(gutter_bounds, text_bounds, &layout, cx);
if layout.gutter_size.width > Pixels::ZERO {
self.paint_gutter(gutter_bounds, &mut layout, editor, cx);
}
self.paint_text(text_bounds, &mut layout, editor, cx);
let input_handler = ElementInputHandler::new(bounds, cx);
cx.handle_input(&editor.focus_handle, input_handler);
});
);
});
}
}
+6 -5
View File
@@ -612,6 +612,7 @@ impl<V: 'static> Element<V> for Div<V> {
let interactive_state = self
.interactivity
.initialize(element_state.map(|s| s.interactive_state), cx);
for child in &mut self.children {
child.initialize(view_state, cx);
}
@@ -763,6 +764,7 @@ where
.unwrap_or_else(|| cx.focus_handle())
});
}
element_state
}
@@ -773,11 +775,7 @@ where
f: impl FnOnce(Style, &mut ViewContext<V>) -> LayoutId,
) -> LayoutId {
let style = self.compute_style(None, element_state, cx);
cx.with_key_dispatch(
self.key_context.clone(),
self.tracked_focus_handle.clone(),
|_, cx| f(style, cx),
)
f(style, cx)
}
pub fn paint(
@@ -1078,6 +1076,9 @@ where
})
}
if !self.key_context.is_empty() {
dbg!(&self.key_context, self.action_listeners.len());
}
for (action_type, listener) in self.action_listeners.drain(..) {
cx.on_action(action_type, listener)
}
+11 -6
View File
@@ -286,8 +286,8 @@ pub struct FocusEvent {
#[cfg(test)]
mod test {
use crate::{
self as gpui, div, Div, FocusHandle, InteractiveComponent, KeyBinding, Keystroke,
ParentComponent, Render, Stateful, TestAppContext, VisualContext,
self as gpui, div, Component, Div, FocusHandle, InteractiveComponent, KeyBinding,
Keystroke, ParentComponent, Render, Stateful, TestAppContext, ViewContext, VisualContext,
};
struct TestView {
@@ -304,10 +304,15 @@ mod test {
fn render(&mut self, _: &mut gpui::ViewContext<Self>) -> Self::Element {
div().id("testview").child(
div()
.key_context("test")
.track_focus(&self.focus_handle)
.key_context("parent")
.on_key_down(|this: &mut TestView, _, _, _| this.saw_key_down = true)
.on_action(|this: &mut TestView, _: &TestAction, _| this.saw_action = true),
.on_action(|this: &mut TestView, _: &TestAction, _| this.saw_action = true)
.child(|this: &mut Self, _cx: &mut ViewContext<Self>| {
div()
.key_context("nested")
.track_focus(&this.focus_handle)
.render()
}),
)
}
}
@@ -325,7 +330,7 @@ mod test {
});
cx.update(|cx| {
cx.bind_keys(vec![KeyBinding::new("ctrl-g", TestAction, None)]);
cx.bind_keys(vec![KeyBinding::new("ctrl-g", TestAction, Some("parent"))]);
});
window
+1
View File
@@ -97,6 +97,7 @@ impl KeystrokeMatcher {
}
}
#[derive(Debug)]
pub enum KeyMatch {
None,
Pending,
+5 -2
View File
@@ -1309,6 +1309,7 @@ impl<'a> WindowContext<'a> {
.current_frame
.dispatch_tree
.dispatch_path(node_id);
dbg!(node_id, &dispatch_path, self.propagate_event);
// Capture phase
for node_id in &dispatch_path {
@@ -1328,6 +1329,8 @@ impl<'a> WindowContext<'a> {
}
}
dbg!(node_id, &dispatch_path, self.propagate_event);
// Bubble phase
for node_id in dispatch_path.iter().rev() {
let node = self.window.current_frame.dispatch_tree.node(*node_id);
@@ -1337,6 +1340,7 @@ impl<'a> WindowContext<'a> {
} in node.action_listeners.clone()
{
let any_action = action.as_any();
dbg!(action_type, any_action.type_id());
if action_type == any_action.type_id() {
self.propagate_event = false; // Actions stop propagation by default during the bubble phase
listener(any_action, DispatchPhase::Bubble, self);
@@ -2082,11 +2086,10 @@ impl<'a, V: 'static> ViewContext<'a, V> {
f: impl FnOnce(Option<FocusHandle>, &mut Self) -> R,
) -> R {
let window = &mut self.window;
window
.current_frame
.dispatch_tree
.push_node(context, &mut window.previous_frame.dispatch_tree);
.push_node(context.clone(), &mut window.previous_frame.dispatch_tree);
if let Some(focus_handle) = focus_handle.as_ref() {
window
.current_frame