Detailed changes
@@ -33,6 +33,26 @@ pub trait IdentifiedElement: Element {
#[derive(Deref, DerefMut, Default, Clone, Debug, Eq, PartialEq, Hash)]
pub(crate) struct GlobalElementId(SmallVec<[ElementId; 8]>);
+pub trait ElementKind: 'static + Send + Sync {
+ fn id(&self) -> Option<ElementId>;
+}
+
+pub struct IdentifiedElementKind(pub(crate) ElementId);
+pub struct AnonymousElementKind;
+
+impl ElementKind for IdentifiedElementKind {
+ fn id(&self) -> Option<ElementId> {
+ Some(self.0.clone())
+ }
+}
+
+impl ElementKind for AnonymousElementKind {
+ fn id(&self) -> Option<ElementId> {
+ None
+ }
+}
+
+
pub trait ParentElement: Element {
fn children_mut(&mut self) -> &mut SmallVec<[AnyElement<Self::ViewState>; 2]>;
fn group_mut(&mut self) -> &mut Option<SharedString>;
@@ -1,16 +1,9 @@
-mod clickable;
mod div;
-mod hoverable;
mod img;
-mod layout_node;
mod svg;
mod text;
-mod div2;
-pub use clickable::*;
pub use div::*;
-pub use hoverable::*;
pub use img::*;
-pub use layout_node::*;
pub use svg::*;
pub use text::*;
@@ -1,230 +0,0 @@
-use crate::{
- AnyElement, Bounds, DispatchPhase, Element, ElementId, Hoverable, IdentifiedElement,
- IntoAnyElement, LayoutId, MouseDownEvent, MouseUpEvent, ParentElement, Pixels, SharedString,
- StyleRefinement, Styled, ViewContext,
-};
-use parking_lot::Mutex;
-use refineable::CascadeSlot;
-use smallvec::SmallVec;
-use std::sync::Arc;
-
-pub trait Clickable: Element + Sized {
- fn active_style(&mut self) -> &mut StyleRefinement;
- fn listeners(&mut self) -> &mut ClickListeners<Self::ViewState>;
-
- fn on_click(
- &mut self,
- f: impl Fn(&mut Self::ViewState, &MouseClickEvent, &mut ViewContext<Self::ViewState>)
- + 'static
- + Send
- + Sync,
- ) where
- Self: Sized,
- {
- self.listeners().push(Arc::new(f));
- }
-
- fn active(mut self, f: impl FnOnce(&mut StyleRefinement) -> &mut StyleRefinement) -> Self
- where
- Self: Sized,
- {
- f(self.active_style());
- self
- }
-}
-
-pub type ClickListeners<V> =
- SmallVec<[Arc<dyn Fn(&mut V, &MouseClickEvent, &mut ViewContext<V>) + Send + Sync>; 1]>;
-
-pub struct ClickableElementState<E: 'static + Send + Sync> {
- mouse_down: Arc<Mutex<Option<MouseDownEvent>>>,
- child_state: E,
-}
-
-pub struct MouseClickEvent {
- pub down: MouseDownEvent,
- pub up: MouseUpEvent,
-}
-
-pub struct ClickableElement<E: Element> {
- child: E,
- listeners: ClickListeners<E::ViewState>,
- active_style: StyleRefinement,
- cascade_slot: CascadeSlot,
-}
-
-impl<E: Styled + Element> ClickableElement<E> {
- pub fn new(mut child: E) -> Self {
- let cascade_slot = child.style_cascade().reserve();
- ClickableElement {
- child,
- listeners: Default::default(),
- active_style: Default::default(),
- cascade_slot,
- }
- }
-
- pub fn replace_child<E2: Element<ViewState = E::ViewState>>(
- self,
- replace: impl FnOnce(E) -> E2,
- ) -> ClickableElement<E2> {
- ClickableElement {
- child: replace(self.child),
- listeners: self.listeners,
- active_style: self.active_style,
- cascade_slot: self.cascade_slot,
- }
- }
-}
-
-impl<E> IntoAnyElement<E::ViewState> for ClickableElement<E>
-where
- E: Styled + Element,
-{
- fn into_any(self) -> AnyElement<E::ViewState> {
- AnyElement::new(self)
- }
-}
-
-impl<E> Element for ClickableElement<E>
-where
- E: Styled + Element,
-{
- type ViewState = E::ViewState;
- type ElementState = ClickableElementState<E::ElementState>;
-
- fn id(&self) -> Option<ElementId> {
- self.child.id()
- }
-
- fn layout(
- &mut self,
- state: &mut Self::ViewState,
- element_state: Option<Self::ElementState>,
- cx: &mut ViewContext<Self::ViewState>,
- ) -> (LayoutId, Self::ElementState) {
- if let Some(element_state) = element_state {
- if element_state.mouse_down.lock().is_some() {
- self.child
- .style_cascade()
- .set(self.cascade_slot, Some(self.active_style.clone()));
- }
-
- let (layout_id, child_state) =
- self.child
- .layout(state, Some(element_state.child_state), cx);
- (
- layout_id,
- ClickableElementState {
- mouse_down: element_state.mouse_down,
- child_state,
- },
- )
- } else {
- let (layout_id, child_state) = self.child.layout(state, None, cx);
- (
- layout_id,
- ClickableElementState {
- mouse_down: Default::default(),
- child_state,
- },
- )
- }
- }
-
- fn paint(
- &mut self,
- bounds: Bounds<Pixels>,
- state: &mut Self::ViewState,
- element_state: &mut Self::ElementState,
- cx: &mut ViewContext<Self::ViewState>,
- ) {
- if !self.listeners.is_empty() || self.active_style.is_some() {
- if let Some(mouse_down) = element_state.mouse_down.lock().clone() {
- self.child
- .style_cascade()
- .set(self.cascade_slot, Some(self.active_style.clone()));
- let listeners = self.listeners.clone();
- let mouse_down_mutex = element_state.mouse_down.clone();
- cx.on_mouse_event(move |view, up: &MouseUpEvent, phase, cx| {
- if phase == DispatchPhase::Bubble && bounds.contains_point(up.position) {
- for listener in &*listeners {
- listener(
- view,
- &MouseClickEvent {
- down: mouse_down.clone(),
- up: up.clone(),
- },
- cx,
- );
- }
- }
-
- mouse_down_mutex.lock().take();
- cx.notify();
- });
- } else {
- let mouse_down_mutex = element_state.mouse_down.clone();
- cx.on_mouse_event(move |_view, down: &MouseDownEvent, phase, cx| {
- if phase == DispatchPhase::Bubble && bounds.contains_point(down.position) {
- *mouse_down_mutex.lock() = Some(down.clone());
- cx.notify();
- }
- });
- }
- }
-
- self.child
- .paint(bounds, state, &mut element_state.child_state, cx);
- }
-}
-
-impl<E: Styled + IdentifiedElement> IdentifiedElement for ClickableElement<E> {}
-
-impl<E> ParentElement for ClickableElement<E>
-where
- E: Styled + ParentElement,
-{
- fn children_mut(&mut self) -> &mut SmallVec<[AnyElement<Self::ViewState>; 2]> {
- self.child.children_mut()
- }
-
- fn group_mut(&mut self) -> &mut Option<SharedString> {
- self.child.group_mut()
- }
-}
-
-impl<E> Styled for ClickableElement<E>
-where
- E: Styled + Element,
-{
- fn style_cascade(&mut self) -> &mut crate::StyleCascade {
- self.child.style_cascade()
- }
-
- fn computed_style(&mut self) -> &crate::Style {
- self.child.computed_style()
- }
-}
-
-impl<E> Hoverable for ClickableElement<E>
-where
- E: Element + Hoverable,
-{
- fn hover_style(&mut self) -> &mut StyleRefinement {
- self.child.hover_style()
- }
-}
-
-impl<E> Clickable for ClickableElement<E>
-where
- E: Styled + IdentifiedElement,
-{
- fn active_style(&mut self) -> &mut StyleRefinement {
- &mut self.active_style
- }
-
- fn listeners(&mut self) -> &mut ClickListeners<Self::ViewState> {
- &mut self.listeners
- }
-}
@@ -1,14 +1,43 @@
use crate::{
- AnonymousElementKind, AnyElement, Bounds, ClickListeners, Clickable, ClickableElement,
- ClickableElementState, Element, ElementId, ElementKind, Hoverable, HoverableElement,
- IdentifiedElement, IdentifiedElementKind, IntoAnyElement, LayoutId, LayoutNodeElement,
- Overflow, ParentElement, Pixels, Point, SharedString, Style, StyleCascade, StyleRefinement,
- Styled, ViewContext,
+ AnonymousElementKind, AnyElement, AppContext, BorrowWindow, Bounds, DispatchPhase, Element,
+ ElementId, ElementKind, IdentifiedElement, IdentifiedElementKind, IntoAnyElement, LayoutId,
+ MouseButton, MouseDownEvent, MouseMoveEvent, MouseUpEvent, Overflow, Pixels, Point,
+ ScrollWheelEvent, SharedString, Style, StyleRefinement, Styled, ViewContext,
};
+use collections::HashMap;
use parking_lot::Mutex;
+use refineable::Refineable;
use smallvec::SmallVec;
use std::sync::Arc;
+#[derive(Default)]
+pub struct DivState {
+ active_state: Arc<Mutex<ActiveState>>,
+ pending_click: Arc<Mutex<Option<MouseDownEvent>>>,
+}
+
+#[derive(Copy, Clone, Default, Eq, PartialEq)]
+struct ActiveState {
+ group: bool,
+ element: bool,
+}
+
+impl ActiveState {
+ pub fn is_none(&self) -> bool {
+ !self.group && !self.element
+ }
+}
+
+#[derive(Default)]
+struct GroupBounds(HashMap<SharedString, SmallVec<[Bounds<Pixels>; 1]>>);
+
+pub fn group_bounds(name: &SharedString, cx: &mut AppContext) -> Option<Bounds<Pixels>> {
+ cx.default_global::<GroupBounds>()
+ .0
+ .get(name)
+ .and_then(|bounds_stack| bounds_stack.last().cloned())
+}
+
#[derive(Default, Clone)]
pub struct ScrollState(Arc<Mutex<Point<Pixels>>>);
@@ -34,126 +63,358 @@ pub fn div<S>() -> Div<S, AnonymousElementKind>
where
S: 'static + Send + Sync,
{
- Div(ClickableElement::new(HoverableElement::new(
- LayoutNodeElement::new(),
- )))
+ Div {
+ kind: AnonymousElementKind,
+ children: SmallVec::new(),
+ group: None,
+ base_style: StyleRefinement::default(),
+ hover_style: StyleRefinement::default(),
+ group_hover: None,
+ active_style: StyleRefinement::default(),
+ group_active: None,
+ listeners: MouseEventListeners::default(),
+ }
+}
+
+pub struct Div<V: 'static + Send + Sync, K: ElementKind = AnonymousElementKind> {
+ kind: K,
+ children: SmallVec<[AnyElement<V>; 2]>,
+ group: Option<SharedString>,
+ base_style: StyleRefinement,
+ hover_style: StyleRefinement,
+ group_hover: Option<GroupStyle>,
+ active_style: StyleRefinement,
+ group_active: Option<GroupStyle>,
+ listeners: MouseEventListeners<V>,
+}
+
+struct GroupStyle {
+ group: SharedString,
+ style: StyleRefinement,
}
-pub struct Div<V: 'static + Send + Sync, K: ElementKind = AnonymousElementKind>(
- ClickableElement<HoverableElement<LayoutNodeElement<V, K>>>,
-);
+impl<V> Div<V, AnonymousElementKind>
+where
+ V: 'static + Send + Sync,
+{
+ pub fn id(self, id: impl Into<ElementId>) -> Div<V, IdentifiedElementKind> {
+ Div {
+ kind: IdentifiedElementKind(id.into()),
+ children: self.children,
+ group: self.group,
+ base_style: self.base_style,
+ hover_style: self.hover_style,
+ group_hover: self.group_hover,
+ active_style: self.active_style,
+ group_active: self.group_active,
+ listeners: self.listeners,
+ }
+ }
+}
+
+impl<V> Div<V, IdentifiedElementKind>
+where
+ V: 'static + Send + Sync,
+{
+ pub fn on_mouse_down(
+ mut self,
+ button: MouseButton,
+ handler: impl Fn(&mut V, &MouseDownEvent, &mut ViewContext<V>) + Send + Sync + 'static,
+ ) -> Self {
+ self.listeners
+ .mouse_down
+ .push(Arc::new(move |view, event, bounds, phase, cx| {
+ if phase == DispatchPhase::Bubble
+ && event.button == button
+ && bounds.contains_point(&event.position)
+ {
+ handler(view, event, cx)
+ }
+ }));
+ self
+ }
+
+ pub fn on_mouse_up(
+ mut self,
+ button: MouseButton,
+ handler: impl Fn(&mut V, &MouseUpEvent, &mut ViewContext<V>) + Send + Sync + 'static,
+ ) -> Self {
+ self.listeners
+ .mouse_up
+ .push(Arc::new(move |view, event, bounds, phase, cx| {
+ if phase == DispatchPhase::Bubble
+ && event.button == button
+ && bounds.contains_point(&event.position)
+ {
+ handler(view, event, cx)
+ }
+ }));
+ self
+ }
+
+ pub fn on_mouse_down_out(
+ mut self,
+ button: MouseButton,
+ handler: impl Fn(&mut V, &MouseDownEvent, &mut ViewContext<V>) + Send + Sync + 'static,
+ ) -> Self {
+ self.listeners
+ .mouse_down
+ .push(Arc::new(move |view, event, bounds, phase, cx| {
+ if phase == DispatchPhase::Capture
+ && event.button == button
+ && !bounds.contains_point(&event.position)
+ {
+ handler(view, event, cx)
+ }
+ }));
+ self
+ }
+
+ pub fn on_mouse_up_out(
+ mut self,
+ button: MouseButton,
+ handler: impl Fn(&mut V, &MouseUpEvent, &mut ViewContext<V>) + Send + Sync + 'static,
+ ) -> Self {
+ self.listeners
+ .mouse_up
+ .push(Arc::new(move |view, event, bounds, phase, cx| {
+ if phase == DispatchPhase::Capture
+ && event.button == button
+ && !bounds.contains_point(&event.position)
+ {
+ handler(view, event, cx);
+ }
+ }));
+ self
+ }
+
+ pub fn on_mouse_move(
+ mut self,
+ handler: impl Fn(&mut V, &MouseMoveEvent, &mut ViewContext<V>) + Send + Sync + 'static,
+ ) -> Self {
+ self.listeners
+ .mouse_move
+ .push(Arc::new(move |view, event, bounds, phase, cx| {
+ if phase == DispatchPhase::Bubble && bounds.contains_point(&event.position) {
+ handler(view, event, cx);
+ }
+ }));
+ self
+ }
-impl<V: 'static + Send + Sync, K: ElementKind> Div<V, K> {
+ pub fn on_scroll_wheel(
+ mut self,
+ handler: impl Fn(&mut V, &ScrollWheelEvent, &mut ViewContext<V>) + Send + Sync + 'static,
+ ) -> Self {
+ self.listeners
+ .scroll_wheel
+ .push(Arc::new(move |view, event, bounds, phase, cx| {
+ if phase == DispatchPhase::Bubble && bounds.contains_point(&event.position) {
+ handler(view, event, cx);
+ }
+ }));
+ self
+ }
+}
+
+impl<V, K> Div<V, K>
+where
+ V: 'static + Send + Sync,
+ K: ElementKind,
+{
pub fn group(mut self, group: impl Into<SharedString>) -> Self {
- *self.0.group_mut() = Some(group.into());
+ self.group = Some(group.into());
self
}
pub fn z_index(mut self, z_index: u32) -> Self {
- self.base_style().z_index = Some(z_index);
+ self.base_style.z_index = Some(z_index);
self
}
pub fn overflow_hidden(mut self) -> Self {
- self.base_style().overflow.x = Some(Overflow::Hidden);
- self.base_style().overflow.y = Some(Overflow::Hidden);
+ self.base_style.overflow.x = Some(Overflow::Hidden);
+ self.base_style.overflow.y = Some(Overflow::Hidden);
self
}
pub fn overflow_hidden_x(mut self) -> Self {
- self.base_style().overflow.x = Some(Overflow::Hidden);
+ self.base_style.overflow.x = Some(Overflow::Hidden);
self
}
pub fn overflow_hidden_y(mut self) -> Self {
- self.base_style().overflow.y = Some(Overflow::Hidden);
+ self.base_style.overflow.y = Some(Overflow::Hidden);
self
}
pub fn overflow_scroll(mut self, _scroll_state: ScrollState) -> Self {
// todo!("impl scrolling")
// self.scroll_state = Some(scroll_state);
- self.base_style().overflow.x = Some(Overflow::Scroll);
- self.base_style().overflow.y = Some(Overflow::Scroll);
+ self.base_style.overflow.x = Some(Overflow::Scroll);
+ self.base_style.overflow.y = Some(Overflow::Scroll);
self
}
pub fn overflow_x_scroll(mut self, _scroll_state: ScrollState) -> Self {
// todo!("impl scrolling")
// self.scroll_state = Some(scroll_state);
- self.base_style().overflow.x = Some(Overflow::Scroll);
+ self.base_style.overflow.x = Some(Overflow::Scroll);
self
}
pub fn overflow_y_scroll(mut self, _scroll_state: ScrollState) -> Self {
// todo!("impl scrolling")
// self.scroll_state = Some(scroll_state);
- self.base_style().overflow.y = Some(Overflow::Scroll);
+ self.base_style.overflow.y = Some(Overflow::Scroll);
self
}
- fn base_style(&mut self) -> &mut StyleRefinement {
- self.style_cascade().base()
+ fn with_element_id<R>(
+ &mut self,
+ cx: &mut ViewContext<V>,
+ f: impl FnOnce(&mut Self, &mut ViewContext<V>) -> R,
+ ) -> R {
+ if let Some(id) = self.id() {
+ cx.with_element_id(id, |cx| f(self, cx))
+ } else {
+ f(self, cx)
+ }
}
-}
-impl<V: 'static + Send + Sync> Div<V, AnonymousElementKind> {
- pub fn id(self, id: impl Into<ElementId>) -> Div<V, IdentifiedElementKind> {
- Div(self.0.replace_child(|hoverable| {
- hoverable.replace_child(|layout_node| layout_node.identify(id))
- }))
- }
-}
+ pub fn compute_style(
+ &self,
+ bounds: Bounds<Pixels>,
+ state: &DivState,
+ cx: &mut ViewContext<V>,
+ ) -> Style {
+ let mut computed_style = Style::default();
+ computed_style.refine(&self.base_style);
-impl<V: 'static + Send + Sync> IdentifiedElement for Div<V, IdentifiedElementKind> {
- fn id(&self) -> ElementId {
- IdentifiedElement::id(&self.0)
- }
-}
+ let mouse_position = cx.mouse_position();
-impl<V: 'static + Send + Sync, K: ElementKind> ParentElement for Div<V, K> {
- fn children_mut(&mut self) -> &mut SmallVec<[AnyElement<V>; 2]> {
- self.0.children_mut()
- }
+ if let Some(group_hover) = self.group_hover.as_ref() {
+ if let Some(group_bounds) = group_bounds(&group_hover.group, cx) {
+ if group_bounds.contains_point(&mouse_position) {
+ computed_style.refine(&group_hover.style);
+ }
+ }
+ }
+ if bounds.contains_point(&mouse_position) {
+ computed_style.refine(&self.hover_style);
+ }
- fn group_mut(&mut self) -> &mut Option<SharedString> {
- self.0.group_mut()
- }
-}
+ let active_state = *state.active_state.lock();
+ if active_state.group {
+ if let Some(GroupStyle { style, .. }) = self.group_active.as_ref() {
+ computed_style.refine(style);
+ }
+ }
-impl<V: 'static + Send + Sync, K: ElementKind> Styled for Div<V, K> {
- fn style_cascade(&mut self) -> &mut StyleCascade {
- self.0.style_cascade()
- }
+ if active_state.element {
+ computed_style.refine(&self.active_style);
+ }
- fn computed_style(&mut self) -> &Style {
- self.0.computed_style()
+ computed_style
}
-}
-impl<V: 'static + Send + Sync, K: ElementKind> Hoverable for Div<V, K> {
- fn hover_style(&mut self) -> &mut StyleRefinement {
- self.0.hover_style()
- }
-}
+ fn paint_hover_listeners(
+ &self,
+ bounds: Bounds<Pixels>,
+ group_bounds: Option<Bounds<Pixels>>,
+ cx: &mut ViewContext<V>,
+ ) {
+ if let Some(group_bounds) = group_bounds {
+ paint_hover_listener(group_bounds, cx);
+ }
-impl<V: 'static + Send + Sync> Clickable for Div<V, IdentifiedElementKind> {
- fn active_style(&mut self) -> &mut StyleRefinement {
- self.0.active_style()
+ if self.hover_style.is_some() {
+ paint_hover_listener(bounds, cx);
+ }
}
- fn listeners(&mut self) -> &mut ClickListeners<V> {
- self.0.listeners()
+ fn paint_active_listener(
+ &self,
+ bounds: Bounds<Pixels>,
+ group_bounds: Option<Bounds<Pixels>>,
+ active_state: Arc<Mutex<ActiveState>>,
+ cx: &mut ViewContext<V>,
+ ) {
+ if active_state.lock().is_none() {
+ cx.on_mouse_event(move |_view, down: &MouseDownEvent, phase, cx| {
+ if phase == DispatchPhase::Bubble {
+ let group =
+ group_bounds.map_or(false, |bounds| bounds.contains_point(&down.position));
+ let element = bounds.contains_point(&down.position);
+ if group || element {
+ *active_state.lock() = ActiveState { group, element };
+ cx.notify();
+ }
+ }
+ });
+ } else {
+ cx.on_mouse_event(move |_, _: &MouseUpEvent, phase, cx| {
+ if phase == DispatchPhase::Capture {
+ *active_state.lock() = ActiveState::default();
+ cx.notify();
+ }
+ });
+ }
}
-}
-impl<V, K> IntoAnyElement<V> for Div<V, K>
-where
- V: 'static + Send + Sync,
- K: ElementKind,
-{
- fn into_any(self) -> AnyElement<V> {
- AnyElement::new(self)
+ fn paint_event_listeners(
+ &self,
+ bounds: Bounds<Pixels>,
+ pending_click: Arc<Mutex<Option<MouseDownEvent>>>,
+ cx: &mut ViewContext<V>,
+ ) {
+ let click_listeners = self.listeners.mouse_click.clone();
+ let mouse_down = pending_click.lock().clone();
+ if let Some(mouse_down) = mouse_down {
+ cx.on_mouse_event(move |state, event: &MouseUpEvent, phase, cx| {
+ if phase == DispatchPhase::Bubble && bounds.contains_point(&event.position) {
+ let mouse_click = MouseClickEvent {
+ down: mouse_down.clone(),
+ up: event.clone(),
+ };
+ for listener in &click_listeners {
+ listener(state, &mouse_click, &bounds, cx);
+ }
+ }
+
+ *pending_click.lock() = None;
+ });
+ } else {
+ cx.on_mouse_event(move |_state, event: &MouseDownEvent, phase, _cx| {
+ if phase == DispatchPhase::Bubble && bounds.contains_point(&event.position) {
+ *pending_click.lock() = Some(event.clone());
+ }
+ });
+ }
+
+ for listener in self.listeners.mouse_down.iter().cloned() {
+ cx.on_mouse_event(move |state, event: &MouseDownEvent, phase, cx| {
+ listener(state, event, &bounds, phase, cx);
+ })
+ }
+
+ for listener in self.listeners.mouse_up.iter().cloned() {
+ cx.on_mouse_event(move |state, event: &MouseUpEvent, phase, cx| {
+ listener(state, event, &bounds, phase, cx);
+ })
+ }
+
+ for listener in self.listeners.mouse_move.iter().cloned() {
+ cx.on_mouse_event(move |state, event: &MouseMoveEvent, phase, cx| {
+ listener(state, event, &bounds, phase, cx);
+ })
+ }
+
+ for listener in self.listeners.scroll_wheel.iter().cloned() {
+ cx.on_mouse_event(move |state, event: &ScrollWheelEvent, phase, cx| {
+ listener(state, event, &bounds, phase, cx);
+ })
+ }
}
}
@@ -163,28 +424,185 @@ where
K: ElementKind,
{
type ViewState = V;
- type ElementState = ClickableElementState<()>;
+ type ElementState = DivState;
fn id(&self) -> Option<ElementId> {
- self.0.id()
+ self.kind.id()
}
fn layout(
&mut self,
- state: &mut Self::ViewState,
+ view_state: &mut Self::ViewState,
element_state: Option<Self::ElementState>,
cx: &mut ViewContext<Self::ViewState>,
) -> (LayoutId, Self::ElementState) {
- self.0.layout(state, element_state, cx)
+ self.with_element_id(cx, |this, cx| {
+ let layout_ids = this
+ .children
+ .iter_mut()
+ .map(|child| child.layout(view_state, cx))
+ .collect::<Vec<_>>();
+
+ let element_state = element_state.unwrap_or_default();
+ let style = this.compute_style(Bounds::default(), &element_state, cx);
+ let layout_id = cx.request_layout(&style, layout_ids);
+ (layout_id, element_state)
+ })
}
fn paint(
&mut self,
bounds: Bounds<Pixels>,
- state: &mut Self::ViewState,
+ view_state: &mut Self::ViewState,
element_state: &mut Self::ElementState,
cx: &mut ViewContext<Self::ViewState>,
) {
- self.0.paint(bounds, state, element_state, cx);
+ self.with_element_id(cx, |this, cx| {
+ if let Some(group) = this.group.clone() {
+ cx.default_global::<GroupBounds>()
+ .0
+ .entry(group)
+ .or_default()
+ .push(bounds);
+ }
+
+ let hover_group_bounds = this
+ .group_hover
+ .as_ref()
+ .and_then(|group_hover| group_bounds(&group_hover.group, cx));
+ let active_group_bounds = this
+ .group_active
+ .as_ref()
+ .and_then(|group_active| group_bounds(&group_active.group, cx));
+ let style = this.compute_style(bounds, element_state, cx);
+ let z_index = style.z_index.unwrap_or(0);
+
+ // Paint background and event handlers.
+ cx.stack(z_index, |cx| {
+ cx.stack(0, |cx| {
+ style.paint(bounds, cx);
+ this.paint_hover_listeners(bounds, hover_group_bounds, cx);
+ this.paint_active_listener(
+ bounds,
+ active_group_bounds,
+ element_state.active_state.clone(),
+ cx,
+ );
+ this.paint_event_listeners(bounds, element_state.pending_click.clone(), cx);
+ });
+ });
+
+ style.apply_text_style(cx, |cx| {
+ style.apply_overflow(bounds, cx, |cx| {
+ cx.stack(z_index + 1, |cx| {
+ for child in &mut this.children {
+ child.paint(view_state, None, cx);
+ }
+ })
+ })
+ });
+
+ if let Some(group) = this.group.as_ref() {
+ cx.default_global::<GroupBounds>()
+ .0
+ .get_mut(group)
+ .unwrap()
+ .pop();
+ }
+ })
+ }
+}
+
+impl<V: 'static + Send + Sync> IdentifiedElement for Div<V, IdentifiedElementKind> {
+ fn id(&self) -> ElementId {
+ self.kind.0.clone()
}
}
+
+impl<V, K> IntoAnyElement<V> for Div<V, K>
+where
+ V: 'static + Send + Sync,
+ K: ElementKind,
+{
+ fn into_any(self) -> AnyElement<V> {
+ AnyElement::new(self)
+ }
+}
+
+impl<V, K> Styled for Div<V, K>
+where
+ V: 'static + Send + Sync,
+ K: ElementKind,
+{
+ fn style(&mut self) -> &mut StyleRefinement {
+ &mut self.base_style
+ }
+}
+
+pub struct MouseClickEvent {
+ pub down: MouseDownEvent,
+ pub up: MouseUpEvent,
+}
+
+type MouseDownHandler<V> = Arc<
+ dyn Fn(&mut V, &MouseDownEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
+ + Send
+ + Sync
+ + 'static,
+>;
+type MouseUpHandler<V> = Arc<
+ dyn Fn(&mut V, &MouseUpEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
+ + Send
+ + Sync
+ + 'static,
+>;
+type MouseClickHandler<V> = Arc<
+ dyn Fn(&mut V, &MouseClickEvent, &Bounds<Pixels>, &mut ViewContext<V>) + Send + Sync + 'static,
+>;
+
+type MouseMoveHandler<V> = Arc<
+ dyn Fn(&mut V, &MouseMoveEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
+ + Send
+ + Sync
+ + 'static,
+>;
+type ScrollWheelHandler<V> = Arc<
+ dyn Fn(&mut V, &ScrollWheelEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
+ + Send
+ + Sync
+ + 'static,
+>;
+
+pub struct MouseEventListeners<V: 'static> {
+ mouse_down: SmallVec<[MouseDownHandler<V>; 2]>,
+ mouse_up: SmallVec<[MouseUpHandler<V>; 2]>,
+ mouse_click: SmallVec<[MouseClickHandler<V>; 2]>,
+ mouse_move: SmallVec<[MouseMoveHandler<V>; 2]>,
+ scroll_wheel: SmallVec<[ScrollWheelHandler<V>; 2]>,
+}
+
+impl<V> Default for MouseEventListeners<V> {
+ fn default() -> Self {
+ Self {
+ mouse_down: SmallVec::new(),
+ mouse_up: SmallVec::new(),
+ mouse_click: SmallVec::new(),
+ mouse_move: SmallVec::new(),
+ scroll_wheel: SmallVec::new(),
+ }
+ }
+}
+
+fn paint_hover_listener<V>(bounds: Bounds<Pixels>, cx: &mut ViewContext<V>)
+where
+ V: 'static + Send + Sync,
+{
+ let hovered = bounds.contains_point(&cx.mouse_position());
+ cx.on_mouse_event(move |_, event: &MouseMoveEvent, phase, cx| {
+ if phase == DispatchPhase::Capture {
+ if bounds.contains_point(&event.position) != hovered {
+ cx.notify();
+ }
+ }
+ });
+}
@@ -1,498 +0,0 @@
-use crate::{
- AnonymousElementKind, AnyElement, AppContext, BorrowWindow, Bounds, DispatchPhase, Element,
- ElementId, ElementKind, IdentifiedElement, IdentifiedElementKind, IntoAnyElement, LayoutId,
- MouseDownEvent, MouseMoveEvent, MouseUpEvent, Overflow, Pixels, Point, ScrollWheelEvent,
- SharedString, Style, StyleRefinement, ViewContext,
-};
-use collections::HashMap;
-use parking_lot::Mutex;
-use refineable::Refineable;
-use smallvec::SmallVec;
-use std::sync::Arc;
-
-#[derive(Default)]
-pub struct DivState {
- active_state: Arc<Mutex<ActiveState>>,
- pending_click: Arc<Mutex<Option<MouseDownEvent>>>,
-}
-
-#[derive(Copy, Clone, Default, Eq, PartialEq)]
-struct ActiveState {
- group: bool,
- element: bool,
-}
-
-impl ActiveState {
- pub fn is_none(&self) -> bool {
- !self.group && !self.element
- }
-}
-
-#[derive(Default)]
-struct GroupBounds(HashMap<SharedString, SmallVec<[Bounds<Pixels>; 1]>>);
-
-pub fn group_bounds(name: &SharedString, cx: &mut AppContext) -> Option<Bounds<Pixels>> {
- cx.default_global::<GroupBounds>()
- .0
- .get(name)
- .and_then(|bounds_stack| bounds_stack.last().cloned())
-}
-
-#[derive(Default, Clone)]
-pub struct ScrollState(Arc<Mutex<Point<Pixels>>>);
-
-impl ScrollState {
- pub fn x(&self) -> Pixels {
- self.0.lock().x
- }
-
- pub fn set_x(&self, value: Pixels) {
- self.0.lock().x = value;
- }
-
- pub fn y(&self) -> Pixels {
- self.0.lock().y
- }
-
- pub fn set_y(&self, value: Pixels) {
- self.0.lock().y = value;
- }
-}
-
-pub fn div<S>() -> Div<S, AnonymousElementKind>
-where
- S: 'static + Send + Sync,
-{
- Div {
- kind: AnonymousElementKind,
- children: SmallVec::new(),
- group: None,
- base_style: StyleRefinement::default(),
- hover_style: StyleRefinement::default(),
- group_hover: None,
- active_style: StyleRefinement::default(),
- group_active: None,
- listeners: MouseEventListeners::default(),
- }
-}
-
-pub struct Div<V: 'static + Send + Sync, K: ElementKind = AnonymousElementKind> {
- kind: K,
- children: SmallVec<[AnyElement<V>; 2]>,
- group: Option<SharedString>,
- base_style: StyleRefinement,
- hover_style: StyleRefinement,
- group_hover: Option<GroupStyle>,
- active_style: StyleRefinement,
- group_active: Option<GroupStyle>,
- listeners: MouseEventListeners<V>,
-}
-
-struct GroupStyle {
- group: SharedString,
- style: StyleRefinement,
-}
-
-impl<V> Div<V, AnonymousElementKind>
-where
- V: 'static + Send + Sync,
-{
- pub fn id(self, id: ElementId) -> Div<V, IdentifiedElementKind> {
- Div {
- kind: IdentifiedElementKind(id),
- children: self.children,
- group: self.group,
- base_style: self.base_style,
- hover_style: self.hover_style,
- group_hover: self.group_hover,
- active_style: self.active_style,
- group_active: self.group_active,
- listeners: self.listeners,
- }
- }
-}
-
-impl<V, K> Div<V, K>
-where
- V: 'static + Send + Sync,
- K: ElementKind,
-{
- pub fn group(mut self, group: impl Into<SharedString>) -> Self {
- self.group = Some(group.into());
- self
- }
-
- pub fn z_index(mut self, z_index: u32) -> Self {
- self.base_style.z_index = Some(z_index);
- self
- }
-
- pub fn overflow_hidden(mut self) -> Self {
- self.base_style.overflow.x = Some(Overflow::Hidden);
- self.base_style.overflow.y = Some(Overflow::Hidden);
- self
- }
-
- pub fn overflow_hidden_x(mut self) -> Self {
- self.base_style.overflow.x = Some(Overflow::Hidden);
- self
- }
-
- pub fn overflow_hidden_y(mut self) -> Self {
- self.base_style.overflow.y = Some(Overflow::Hidden);
- self
- }
-
- pub fn overflow_scroll(mut self, _scroll_state: ScrollState) -> Self {
- // todo!("impl scrolling")
- // self.scroll_state = Some(scroll_state);
- self.base_style.overflow.x = Some(Overflow::Scroll);
- self.base_style.overflow.y = Some(Overflow::Scroll);
- self
- }
-
- pub fn overflow_x_scroll(mut self, _scroll_state: ScrollState) -> Self {
- // todo!("impl scrolling")
- // self.scroll_state = Some(scroll_state);
- self.base_style.overflow.x = Some(Overflow::Scroll);
- self
- }
-
- pub fn overflow_y_scroll(mut self, _scroll_state: ScrollState) -> Self {
- // todo!("impl scrolling")
- // self.scroll_state = Some(scroll_state);
- self.base_style.overflow.y = Some(Overflow::Scroll);
- self
- }
-
- fn with_element_id<R>(
- &mut self,
- cx: &mut ViewContext<V>,
- f: impl FnOnce(&mut Self, &mut ViewContext<V>) -> R,
- ) -> R {
- if let Some(id) = self.id() {
- cx.with_element_id(id, |cx| f(self, cx))
- } else {
- f(self, cx)
- }
- }
-
- fn compute_style(
- &self,
- bounds: Bounds<Pixels>,
- group_bounds: Option<Bounds<Pixels>>,
- active_state: ActiveState,
- cx: &mut ViewContext<V>,
- ) -> Style {
- let mut computed_style = Style::default();
- computed_style.refine(&self.base_style);
-
- let mouse_position = cx.mouse_position();
- if let Some(group_bounds) = group_bounds {
- if group_bounds.contains_point(mouse_position) {
- if let Some(GroupStyle { style, .. }) = self.group_hover.as_ref() {
- computed_style.refine(style);
- }
- }
- }
- if bounds.contains_point(mouse_position) {
- computed_style.refine(&self.hover_style);
- }
-
- if active_state.group {
- if let Some(GroupStyle { style, .. }) = self.group_active.as_ref() {
- computed_style.refine(style);
- }
- }
-
- if active_state.element {
- computed_style.refine(&self.active_style);
- }
-
- computed_style
- }
-
- fn paint_hover_listeners(
- &self,
- bounds: Bounds<Pixels>,
- group_bounds: Option<Bounds<Pixels>>,
- cx: &mut ViewContext<V>,
- ) {
- if let Some(group_bounds) = group_bounds {
- paint_hover_listener(group_bounds, cx);
- }
-
- if self.hover_style.is_some() {
- paint_hover_listener(bounds, cx);
- }
- }
-
- fn paint_active_listener(
- &self,
- bounds: Bounds<Pixels>,
- group_bounds: Option<Bounds<Pixels>>,
- active_state: Arc<Mutex<ActiveState>>,
- cx: &mut ViewContext<V>,
- ) {
- if active_state.lock().is_none() {
- cx.on_mouse_event(move |_view, down: &MouseDownEvent, phase, cx| {
- if phase == DispatchPhase::Bubble {
- let group =
- group_bounds.map_or(false, |bounds| bounds.contains_point(down.position));
- let element = bounds.contains_point(down.position);
- if group || element {
- *active_state.lock() = ActiveState { group, element };
- cx.notify();
- }
- }
- });
- } else {
- cx.on_mouse_event(move |_, _: &MouseUpEvent, phase, cx| {
- if phase == DispatchPhase::Capture {
- *active_state.lock() = ActiveState::default();
- cx.notify();
- }
- });
- }
- }
-
- fn paint_event_listeners(
- &self,
- bounds: Bounds<Pixels>,
- pending_click: Arc<Mutex<Option<MouseDownEvent>>>,
- cx: &mut ViewContext<V>,
- ) {
- let click_listeners = self.listeners.mouse_click.clone();
- let mouse_down = pending_click.lock().clone();
- if let Some(mouse_down) = mouse_down {
- cx.on_mouse_event(move |state, event: &MouseUpEvent, phase, cx| {
- if phase == DispatchPhase::Bubble && bounds.contains_point(event.position) {
- let mouse_click = MouseClickEvent {
- down: mouse_down.clone(),
- up: event.clone(),
- };
- for listener in &click_listeners {
- listener(state, &mouse_click, &bounds, cx);
- }
- }
-
- *pending_click.lock() = None;
- });
- } else {
- cx.on_mouse_event(move |_state, event: &MouseDownEvent, phase, _cx| {
- if phase == DispatchPhase::Bubble && bounds.contains_point(event.position) {
- *pending_click.lock() = Some(event.clone());
- }
- });
- }
-
- for listener in self.listeners.mouse_down.iter().cloned() {
- cx.on_mouse_event(move |state, event: &MouseDownEvent, phase, cx| {
- listener(state, event, &bounds, phase, cx);
- })
- }
-
- for listener in self.listeners.mouse_up.iter().cloned() {
- cx.on_mouse_event(move |state, event: &MouseUpEvent, phase, cx| {
- listener(state, event, &bounds, phase, cx);
- })
- }
-
- for listener in self.listeners.mouse_move.iter().cloned() {
- cx.on_mouse_event(move |state, event: &MouseMoveEvent, phase, cx| {
- listener(state, event, &bounds, phase, cx);
- })
- }
-
- for listener in self.listeners.scroll_wheel.iter().cloned() {
- cx.on_mouse_event(move |state, event: &ScrollWheelEvent, phase, cx| {
- listener(state, event, &bounds, phase, cx);
- })
- }
- }
-}
-
-impl<V, K> Element for Div<V, K>
-where
- V: 'static + Send + Sync,
- K: ElementKind,
-{
- type ViewState = V;
- type ElementState = DivState;
-
- fn id(&self) -> Option<ElementId> {
- self.kind.id()
- }
-
- fn layout(
- &mut self,
- view_state: &mut Self::ViewState,
- element_state: Option<Self::ElementState>,
- cx: &mut ViewContext<Self::ViewState>,
- ) -> (LayoutId, Self::ElementState) {
- self.with_element_id(cx, |this, cx| {
- let layout_ids = this
- .children
- .iter_mut()
- .map(|child| child.layout(view_state, cx))
- .collect::<Vec<_>>();
-
- let element_state = element_state.unwrap_or_default();
- let style = this.compute_style(
- Bounds::default(),
- None,
- *element_state.active_state.lock(),
- cx,
- );
- let layout_id = cx.request_layout(&style, layout_ids);
- (layout_id, element_state)
- })
- }
-
- fn paint(
- &mut self,
- bounds: Bounds<Pixels>,
- view_state: &mut Self::ViewState,
- element_state: &mut Self::ElementState,
- cx: &mut ViewContext<Self::ViewState>,
- ) {
- self.with_element_id(cx, |this, cx| {
- if let Some(group) = this.group.clone() {
- cx.default_global::<GroupBounds>()
- .0
- .entry(group)
- .or_default()
- .push(bounds);
- }
-
- let hover_group_bounds = this
- .group_hover
- .as_ref()
- .and_then(|group_hover| group_bounds(&group_hover.group, cx));
- let active_group_bounds = this
- .group_active
- .as_ref()
- .and_then(|group_active| group_bounds(&group_active.group, cx));
- let active_state = *element_state.active_state.lock();
- let style = this.compute_style(bounds, hover_group_bounds, active_state, cx);
- let z_index = style.z_index.unwrap_or(0);
-
- // Paint background and event handlers.
- cx.stack(z_index, |cx| {
- cx.stack(0, |cx| {
- style.paint(bounds, cx);
- this.paint_hover_listeners(bounds, hover_group_bounds, cx);
- this.paint_active_listener(
- bounds,
- active_group_bounds,
- element_state.active_state.clone(),
- cx,
- );
- this.paint_event_listeners(bounds, element_state.pending_click.clone(), cx);
- });
- });
-
- style.apply_text_style(cx, |cx| {
- style.apply_overflow(bounds, cx, |cx| {
- cx.stack(z_index + 1, |cx| {
- for child in &mut this.children {
- child.paint(view_state, None, cx);
- }
- })
- })
- });
-
- if let Some(group) = this.group.as_ref() {
- cx.default_global::<GroupBounds>()
- .0
- .get_mut(group)
- .unwrap()
- .pop();
- }
- })
- }
-}
-
-impl<V: 'static + Send + Sync> IdentifiedElement for Div<V, IdentifiedElementKind> {
- fn id(&self) -> ElementId {
- self.kind.0.clone()
- }
-}
-
-impl<V, K> IntoAnyElement<V> for Div<V, K>
-where
- V: 'static + Send + Sync,
- K: ElementKind,
-{
- fn into_any(self) -> AnyElement<V> {
- AnyElement::new(self)
- }
-}
-
-pub struct MouseClickEvent {
- pub down: MouseDownEvent,
- pub up: MouseUpEvent,
-}
-
-type MouseDownHandler<V> = Arc<
- dyn Fn(&mut V, &MouseDownEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
- + Send
- + Sync
- + 'static,
->;
-type MouseUpHandler<V> = Arc<
- dyn Fn(&mut V, &MouseUpEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
- + Send
- + Sync
- + 'static,
->;
-type MouseClickHandler<V> = Arc<
- dyn Fn(&mut V, &MouseClickEvent, &Bounds<Pixels>, &mut ViewContext<V>) + Send + Sync + 'static,
->;
-
-type MouseMoveHandler<V> = Arc<
- dyn Fn(&mut V, &MouseMoveEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
- + Send
- + Sync
- + 'static,
->;
-type ScrollWheelHandler<V> = Arc<
- dyn Fn(&mut V, &ScrollWheelEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
- + Send
- + Sync
- + 'static,
->;
-
-pub struct MouseEventListeners<V: 'static> {
- mouse_down: SmallVec<[MouseDownHandler<V>; 2]>,
- mouse_up: SmallVec<[MouseUpHandler<V>; 2]>,
- mouse_click: SmallVec<[MouseClickHandler<V>; 2]>,
- mouse_move: SmallVec<[MouseMoveHandler<V>; 2]>,
- scroll_wheel: SmallVec<[ScrollWheelHandler<V>; 2]>,
-}
-
-impl<V> Default for MouseEventListeners<V> {
- fn default() -> Self {
- Self {
- mouse_down: SmallVec::new(),
- mouse_up: SmallVec::new(),
- mouse_click: SmallVec::new(),
- mouse_move: SmallVec::new(),
- scroll_wheel: SmallVec::new(),
- }
- }
-}
-
-fn paint_hover_listener<V>(bounds: Bounds<Pixels>, cx: &mut ViewContext<V>)
-where
- V: 'static + Send + Sync,
-{
- let hovered = bounds.contains_point(cx.mouse_position());
- cx.on_mouse_event(move |_, event: &MouseMoveEvent, phase, cx| {
- if phase == DispatchPhase::Capture {
- if bounds.contains_point(event.position) != hovered {
- cx.notify();
- }
- }
- });
-}
@@ -1,149 +0,0 @@
-use crate::{
- group_bounds, AnyElement, Bounds, DispatchPhase, Element, ElementId, IdentifiedElement,
- IntoAnyElement, LayoutId, MouseMoveEvent, ParentElement, Pixels, SharedString, Style,
- StyleCascade, StyleRefinement, Styled, ViewContext,
-};
-use refineable::CascadeSlot;
-use std::sync::{
- atomic::{AtomicBool, Ordering::SeqCst},
- Arc,
-};
-
-pub trait Hoverable {
- fn hover_style(&mut self) -> &mut StyleRefinement;
-
- fn hover(mut self, f: impl FnOnce(&mut StyleRefinement) -> &mut StyleRefinement) -> Self
- where
- Self: Sized,
- {
- f(self.hover_style());
- self
- }
-}
-
-pub struct HoverableElement<E> {
- hover_style: StyleRefinement,
- group: Option<SharedString>,
- cascade_slot: CascadeSlot,
- hovered: Arc<AtomicBool>,
- child: E,
-}
-
-impl<E: Styled + Element> HoverableElement<E> {
- pub fn new(mut child: E) -> Self {
- let cascade_slot = child.style_cascade().reserve();
- HoverableElement {
- hover_style: StyleRefinement::default(),
- group: None,
- cascade_slot,
- hovered: Arc::new(AtomicBool::new(false)),
- child,
- }
- }
-
- pub fn replace_child<E2: Element<ViewState = E::ViewState>>(
- self,
- replace: impl FnOnce(E) -> E2,
- ) -> HoverableElement<E2> {
- HoverableElement {
- hover_style: self.hover_style,
- group: self.group,
- cascade_slot: self.cascade_slot,
- hovered: self.hovered,
- child: replace(self.child),
- }
- }
-}
-
-impl<E> IntoAnyElement<E::ViewState> for HoverableElement<E>
-where
- E: Styled + Element,
-{
- fn into_any(self) -> AnyElement<E::ViewState> {
- AnyElement::new(self)
- }
-}
-
-impl<E> Element for HoverableElement<E>
-where
- E: Styled + Element,
-{
- type ViewState = E::ViewState;
- type ElementState = E::ElementState;
-
- fn id(&self) -> Option<ElementId> {
- self.child.id()
- }
-
- fn layout(
- &mut self,
- state: &mut Self::ViewState,
- element_state: Option<Self::ElementState>,
- cx: &mut ViewContext<Self::ViewState>,
- ) -> (LayoutId, Self::ElementState) {
- self.child.layout(state, element_state, cx)
- }
-
- fn paint(
- &mut self,
- bounds: Bounds<Pixels>,
- state: &mut Self::ViewState,
- element_state: &mut Self::ElementState,
- cx: &mut ViewContext<Self::ViewState>,
- ) {
- let target_bounds = self
- .group
- .as_ref()
- .and_then(|group| group_bounds(group, cx))
- .unwrap_or(bounds);
-
- let hovered = target_bounds.contains_point(cx.mouse_position());
-
- let slot = self.cascade_slot;
- let style = hovered.then_some(self.hover_style.clone());
- self.child.style_cascade().set(slot, style);
- self.hovered.store(hovered, SeqCst);
-
- let hovered = self.hovered.clone();
- cx.on_mouse_event(move |_, event: &MouseMoveEvent, phase, cx| {
- if phase == DispatchPhase::Capture {
- if target_bounds.contains_point(event.position) != hovered.load(SeqCst) {
- cx.notify();
- }
- }
- });
-
- self.child.paint(bounds, state, element_state, cx);
- }
-}
-
-impl<E> ParentElement for HoverableElement<E>
-where
- E: Styled + ParentElement,
-{
- fn children_mut(&mut self) -> &mut smallvec::SmallVec<[AnyElement<E::ViewState>; 2]> {
- self.child.children_mut()
- }
-
- fn group_mut(&mut self) -> &mut Option<SharedString> {
- self.child.group_mut()
- }
-}
-
-impl<E: Styled + Element> Hoverable for HoverableElement<E> {
- fn hover_style(&mut self) -> &mut StyleRefinement {
- &mut self.hover_style
- }
-}
-
-impl<E: Styled + Element> Styled for HoverableElement<E> {
- fn style_cascade(&mut self) -> &mut StyleCascade {
- self.child.style_cascade()
- }
-
- fn computed_style(&mut self) -> &Style {
- self.child.computed_style()
- }
-}
-
-impl<E: Styled + IdentifiedElement> IdentifiedElement for HoverableElement<E> {}
@@ -1,15 +1,13 @@
use crate::{
- AnonymousElementKind, AnyElement, BorrowWindow, Bounds, ClickListeners, Clickable,
- ClickableElement, ClickableElementState, Element, ElementId, ElementKind, Hoverable,
- HoverableElement, IdentifiedElement, IdentifiedElementKind, IntoAnyElement, LayoutId,
- LayoutNodeElement, Pixels, SharedString, Style, StyleRefinement, Styled, ViewContext,
+ div, AnonymousElementKind, AnyElement, BorrowWindow, Bounds, Div, DivState, Element, ElementId,
+ ElementKind, IdentifiedElement, IdentifiedElementKind, IntoAnyElement, LayoutId, Pixels,
+ SharedString, StyleRefinement, Styled, ViewContext,
};
use futures::FutureExt;
-use refineable::Cascade;
use util::ResultExt;
pub struct Img<V: 'static + Send + Sync, K: ElementKind = AnonymousElementKind> {
- layout_node: ClickableElement<HoverableElement<LayoutNodeElement<V, K>>>,
+ base: Div<V, K>,
uri: Option<SharedString>,
grayscale: bool,
}
@@ -19,7 +17,7 @@ where
V: 'static + Send + Sync,
{
Img {
- layout_node: ClickableElement::new(HoverableElement::new(LayoutNodeElement::new())),
+ base: div(),
uri: None,
grayscale: false,
}
@@ -44,9 +42,7 @@ where
impl<V: 'static + Send + Sync> Img<V, AnonymousElementKind> {
pub fn id(self, id: impl Into<ElementId>) -> Img<V, IdentifiedElementKind> {
Img {
- layout_node: self.layout_node.replace_child(|hoverable| {
- hoverable.replace_child(|layout_node| layout_node.identify(id))
- }),
+ base: self.base.id(id),
uri: self.uri,
grayscale: self.grayscale,
}
@@ -69,10 +65,10 @@ where
K: ElementKind,
{
type ViewState = V;
- type ElementState = ClickableElementState<()>;
+ type ElementState = DivState;
fn id(&self) -> Option<crate::ElementId> {
- self.layout_node.id()
+ self.base.id()
}
fn layout(
@@ -84,7 +80,7 @@ where
where
Self: Sized,
{
- self.layout_node.layout(view_state, element_state, cx)
+ self.base.layout(view_state, element_state, cx)
}
fn paint(
@@ -95,10 +91,10 @@ where
cx: &mut ViewContext<Self::ViewState>,
) {
cx.stack(1, |cx| {
- self.layout_node.paint(bounds, view, element_state, cx);
+ self.base.paint(bounds, view, element_state, cx);
});
- let style = self.computed_style();
+ let style = self.base.compute_style(bounds, element_state, cx);
let corner_radii = style.corner_radii;
if let Some(uri) = self.uri.clone() {
@@ -127,7 +123,7 @@ where
impl<V: 'static + Send + Sync> IdentifiedElement for Img<V, IdentifiedElementKind> {
fn id(&self) -> ElementId {
- IdentifiedElement::id(&self.layout_node)
+ IdentifiedElement::id(&self.base)
}
}
@@ -136,27 +132,7 @@ where
V: 'static + Send + Sync,
K: ElementKind,
{
- fn style_cascade(&mut self) -> &mut Cascade<Style> {
- self.layout_node.style_cascade()
- }
-
- fn computed_style(&mut self) -> &Style {
- self.layout_node.computed_style()
- }
-}
-
-impl<V: 'static + Send + Sync, K: ElementKind> Hoverable for Img<V, K> {
- fn hover_style(&mut self) -> &mut StyleRefinement {
- self.layout_node.hover_style()
- }
-}
-
-impl<V: 'static + Send + Sync> Clickable for Img<V, IdentifiedElementKind> {
- fn active_style(&mut self) -> &mut StyleRefinement {
- self.layout_node.active_style()
- }
-
- fn listeners(&mut self) -> &mut ClickListeners<V> {
- self.layout_node.listeners()
+ fn style(&mut self) -> &mut StyleRefinement {
+ self.base.style()
}
}
@@ -1,193 +0,0 @@
-use crate::{
- AnyElement, AppContext, BorrowWindow, Bounds, Element, ElementId, IdentifiedElement,
- IntoAnyElement, LayoutId, ParentElement, Pixels, SharedString, Style, StyleCascade, Styled,
- ViewContext,
-};
-use collections::HashMap;
-use refineable::Refineable;
-use smallvec::SmallVec;
-
-#[derive(Default)]
-struct GroupBounds(HashMap<SharedString, SmallVec<[Bounds<Pixels>; 1]>>);
-
-pub fn group_bounds(name: &SharedString, cx: &mut AppContext) -> Option<Bounds<Pixels>> {
- cx.default_global::<GroupBounds>()
- .0
- .get(name)
- .and_then(|bounds_stack| bounds_stack.last().cloned())
-}
-
-pub trait ElementKind: 'static + Send + Sync {
- fn id(&self) -> Option<ElementId>;
-}
-
-pub struct IdentifiedElementKind(pub(crate) ElementId);
-pub struct AnonymousElementKind;
-
-impl ElementKind for IdentifiedElementKind {
- fn id(&self) -> Option<ElementId> {
- Some(self.0.clone())
- }
-}
-
-impl ElementKind for AnonymousElementKind {
- fn id(&self) -> Option<ElementId> {
- None
- }
-}
-
-pub struct LayoutNodeElement<V: 'static + Send + Sync, K: ElementKind> {
- style_cascade: StyleCascade,
- computed_style: Option<Style>,
- children: SmallVec<[AnyElement<V>; 2]>,
- kind: K,
- group: Option<SharedString>,
-}
-
-impl<V: 'static + Send + Sync> LayoutNodeElement<V, AnonymousElementKind> {
- pub fn new() -> LayoutNodeElement<V, AnonymousElementKind> {
- LayoutNodeElement {
- style_cascade: StyleCascade::default(),
- computed_style: None,
- children: SmallVec::new(),
- kind: AnonymousElementKind,
- group: None,
- }
- }
-
- pub fn identify(self, id: impl Into<ElementId>) -> LayoutNodeElement<V, IdentifiedElementKind> {
- LayoutNodeElement {
- style_cascade: self.style_cascade,
- computed_style: self.computed_style,
- children: self.children,
- kind: IdentifiedElementKind(id.into()),
- group: self.group,
- }
- }
-}
-
-impl<V: 'static + Send + Sync, E: ElementKind> LayoutNodeElement<V, E> {
- pub fn set_group(&mut self, group: impl Into<SharedString>) {
- self.group = Some(group.into());
- }
-
- fn with_element_id<R>(
- &mut self,
- cx: &mut ViewContext<V>,
- f: impl FnOnce(&mut Self, &mut ViewContext<V>) -> R,
- ) -> R {
- if let Some(id) = self.id() {
- cx.with_element_id(id, |cx| f(self, cx))
- } else {
- f(self, cx)
- }
- }
-}
-
-impl<V: 'static + Send + Sync, K: ElementKind> Styled for LayoutNodeElement<V, K> {
- fn style_cascade(&mut self) -> &mut StyleCascade {
- &mut self.style_cascade
- }
-
- fn computed_style(&mut self) -> &Style {
- self.computed_style
- .get_or_insert_with(|| Style::default().refined(self.style_cascade.merged()))
- }
-}
-
-impl<V: 'static + Send + Sync> IdentifiedElement for LayoutNodeElement<V, IdentifiedElementKind> {
- fn id(&self) -> ElementId {
- self.kind.0.clone()
- }
-}
-
-impl<V, K> IntoAnyElement<V> for LayoutNodeElement<V, K>
-where
- V: 'static + Send + Sync,
- K: ElementKind,
-{
- fn into_any(self) -> AnyElement<V> {
- AnyElement::new(self)
- }
-}
-
-impl<V: 'static + Send + Sync, K: ElementKind> Element for LayoutNodeElement<V, K> {
- type ViewState = V;
- type ElementState = ();
-
- fn id(&self) -> Option<ElementId> {
- self.kind.id()
- }
-
- fn layout(
- &mut self,
- state: &mut Self::ViewState,
- _: Option<Self::ElementState>,
- cx: &mut ViewContext<Self::ViewState>,
- ) -> (LayoutId, Self::ElementState) {
- self.with_element_id(cx, |this, cx| {
- let layout_ids = this
- .children
- .iter_mut()
- .map(|child| child.layout(state, cx))
- .collect::<Vec<_>>();
-
- let style = this.computed_style();
- let layout_id = cx.request_layout(style, layout_ids);
- (layout_id, ())
- })
- }
-
- fn paint(
- &mut self,
- bounds: Bounds<Pixels>,
- state: &mut Self::ViewState,
- _: &mut Self::ElementState,
- cx: &mut ViewContext<Self::ViewState>,
- ) {
- self.with_element_id(cx, |this, cx| {
- if let Some(group) = this.group.clone() {
- cx.default_global::<GroupBounds>()
- .0
- .entry(group)
- .or_default()
- .push(bounds);
- }
-
- let style = this.computed_style().clone();
- let z_index = style.z_index.unwrap_or(0);
- cx.stack(z_index, |cx| style.paint(bounds, cx));
-
- // todo!("implement overflow")
- // let overflow = &style.overflow;
-
- style.apply_text_style(cx, |cx| {
- cx.stack(z_index + 1, |cx| {
- style.apply_overflow(bounds, cx, |cx| {
- for child in &mut this.children {
- child.paint(state, None, cx);
- }
- })
- })
- });
-
- if let Some(group) = this.group.as_ref() {
- cx.default_global::<GroupBounds>()
- .0
- .get_mut(group)
- .unwrap()
- .pop();
- }
- })
- }
-}
-
-impl<V: 'static + Send + Sync, K: ElementKind> ParentElement for LayoutNodeElement<V, K> {
- fn children_mut(&mut self) -> &mut SmallVec<[AnyElement<V>; 2]> {
- &mut self.children
- }
-
- fn group_mut(&mut self) -> &mut Option<SharedString> {
- &mut self.group
- }
-}
@@ -1,14 +1,12 @@
use crate::{
- AnonymousElementKind, AnyElement, Bounds, ClickListeners, Clickable, ClickableElement,
- ClickableElementState, Element, ElementId, ElementKind, Hoverable, HoverableElement,
- IdentifiedElement, IdentifiedElementKind, IntoAnyElement, LayoutId, LayoutNodeElement, Pixels,
- SharedString, Style, StyleRefinement, Styled,
+ div, AnonymousElementKind, AnyElement, Bounds, Div, DivState, Element, ElementId, ElementKind,
+ IdentifiedElement, IdentifiedElementKind, IntoAnyElement, LayoutId, Pixels, SharedString,
+ StyleRefinement, Styled,
};
-use refineable::Cascade;
use util::ResultExt;
pub struct Svg<V: 'static + Send + Sync, K: ElementKind = AnonymousElementKind> {
- layout_node: ClickableElement<HoverableElement<LayoutNodeElement<V, K>>>,
+ base: Div<V, K>,
path: Option<SharedString>,
}
@@ -17,7 +15,7 @@ where
V: 'static + Send + Sync,
{
Svg {
- layout_node: ClickableElement::new(HoverableElement::new(LayoutNodeElement::new())),
+ base: div(),
path: None,
}
}
@@ -36,9 +34,7 @@ where
impl<V: 'static + Send + Sync> Svg<V, AnonymousElementKind> {
pub fn id(self, id: impl Into<ElementId>) -> Svg<V, IdentifiedElementKind> {
Svg {
- layout_node: self.layout_node.replace_child(|hoverable| {
- hoverable.replace_child(|layout_node| layout_node.identify(id))
- }),
+ base: self.base.id(id),
path: self.path,
}
}
@@ -60,10 +56,10 @@ where
K: ElementKind,
{
type ViewState = V;
- type ElementState = ClickableElementState<()>;
+ type ElementState = DivState;
fn id(&self) -> Option<crate::ElementId> {
- self.layout_node.id()
+ self.base.id()
}
fn layout(
@@ -75,7 +71,7 @@ where
where
Self: Sized,
{
- self.layout_node.layout(view, element_state, cx)
+ self.base.layout(view, element_state, cx)
}
fn paint(
@@ -87,9 +83,10 @@ where
) where
Self: Sized,
{
- self.layout_node.paint(bounds, view, element_state, cx);
+ self.base.paint(bounds, view, element_state, cx);
let fill_color = self
- .computed_style()
+ .base
+ .compute_style(bounds, element_state, cx)
.fill
.as_ref()
.and_then(|fill| fill.color());
@@ -101,7 +98,7 @@ where
impl<V: 'static + Send + Sync> IdentifiedElement for Svg<V, IdentifiedElementKind> {
fn id(&self) -> ElementId {
- IdentifiedElement::id(&self.layout_node)
+ IdentifiedElement::id(&self.base)
}
}
@@ -110,27 +107,7 @@ where
V: 'static + Send + Sync,
K: ElementKind,
{
- fn style_cascade(&mut self) -> &mut Cascade<Style> {
- self.layout_node.style_cascade()
- }
-
- fn computed_style(&mut self) -> &Style {
- self.layout_node.computed_style()
- }
-}
-
-impl<V: 'static + Send + Sync, K: ElementKind> Hoverable for Svg<V, K> {
- fn hover_style(&mut self) -> &mut StyleRefinement {
- self.layout_node.hover_style()
- }
-}
-
-impl<V: 'static + Send + Sync> Clickable for Svg<V, IdentifiedElementKind> {
- fn active_style(&mut self) -> &mut StyleRefinement {
- self.layout_node.active_style()
- }
-
- fn listeners(&mut self) -> &mut ClickListeners<V> {
- self.layout_node.listeners()
+ fn style(&mut self) -> &mut StyleRefinement {
+ self.base.style()
}
}
@@ -413,7 +413,7 @@ impl<T> Bounds<T>
where
T: Add<T, Output = T> + PartialOrd + Clone + Default + Debug,
{
- pub fn contains_point(&self, point: Point<T>) -> bool {
+ pub fn contains_point(&self, point: &Point<T>) -> bool {
point.x >= self.origin.x
&& point.x <= self.origin.x.clone() + self.size.width.clone()
&& point.y >= self.origin.y
@@ -7,7 +7,6 @@ mod events;
mod executor;
mod geometry;
mod image_cache;
-mod interactive;
mod platform;
mod scene;
mod style;
@@ -31,7 +30,6 @@ pub use executor::*;
pub use geometry::*;
pub use gpui3_macros::*;
pub use image_cache::*;
-pub use interactive::*;
pub use platform::*;
pub use refineable::*;
pub use scene::*;
@@ -1,198 +0,0 @@
-use crate::{
- Bounds, DispatchPhase, MouseButton, MouseDownEvent, MouseMoveEvent, MouseUpEvent, Pixels,
- ScrollWheelEvent, ViewContext,
-};
-use smallvec::SmallVec;
-use std::sync::Arc;
-
-pub trait Interactive<S: 'static + Send + Sync> {
- fn listeners(&mut self) -> &mut MouseEventListeners<S>;
-
- fn on_mouse_down(
- mut self,
- button: MouseButton,
- handler: impl Fn(&mut S, &MouseDownEvent, &mut ViewContext<S>) + Send + Sync + 'static,
- ) -> Self
- where
- Self: Sized,
- {
- self.listeners()
- .mouse_down
- .push(Arc::new(move |view, event, bounds, phase, cx| {
- if phase == DispatchPhase::Bubble
- && event.button == button
- && bounds.contains_point(event.position)
- {
- handler(view, event, cx)
- }
- }));
- self
- }
-
- fn on_mouse_up(
- mut self,
- button: MouseButton,
- handler: impl Fn(&mut S, &MouseUpEvent, &mut ViewContext<S>) + Send + Sync + 'static,
- ) -> Self
- where
- Self: Sized,
- {
- self.listeners()
- .mouse_up
- .push(Arc::new(move |view, event, bounds, phase, cx| {
- if phase == DispatchPhase::Bubble
- && event.button == button
- && bounds.contains_point(event.position)
- {
- handler(view, event, cx)
- }
- }));
- self
- }
-
- fn on_mouse_down_out(
- mut self,
- button: MouseButton,
- handler: impl Fn(&mut S, &MouseDownEvent, &mut ViewContext<S>) + Send + Sync + 'static,
- ) -> Self
- where
- Self: Sized,
- {
- self.listeners()
- .mouse_down
- .push(Arc::new(move |view, event, bounds, phase, cx| {
- if phase == DispatchPhase::Capture
- && event.button == button
- && !bounds.contains_point(event.position)
- {
- handler(view, event, cx)
- }
- }));
- self
- }
-
- fn on_mouse_up_out(
- mut self,
- button: MouseButton,
- handler: impl Fn(&mut S, &MouseUpEvent, &mut ViewContext<S>) + Send + Sync + 'static,
- ) -> Self
- where
- Self: Sized,
- {
- self.listeners()
- .mouse_up
- .push(Arc::new(move |view, event, bounds, phase, cx| {
- if phase == DispatchPhase::Capture
- && event.button == button
- && !bounds.contains_point(event.position)
- {
- handler(view, event, cx);
- }
- }));
- self
- }
-
- fn on_mouse_move(
- mut self,
- handler: impl Fn(&mut S, &MouseMoveEvent, &mut ViewContext<S>) + Send + Sync + 'static,
- ) -> Self
- where
- Self: Sized,
- {
- self.listeners()
- .mouse_move
- .push(Arc::new(move |view, event, bounds, phase, cx| {
- if phase == DispatchPhase::Bubble && bounds.contains_point(event.position) {
- handler(view, event, cx);
- }
- }));
- self
- }
-
- fn on_scroll_wheel(
- mut self,
- handler: impl Fn(&mut S, &ScrollWheelEvent, &mut ViewContext<S>) + Send + Sync + 'static,
- ) -> Self
- where
- Self: Sized,
- {
- self.listeners()
- .scroll_wheel
- .push(Arc::new(move |view, event, bounds, phase, cx| {
- if phase == DispatchPhase::Bubble && bounds.contains_point(event.position) {
- handler(view, event, cx);
- }
- }));
- self
- }
-}
-
-type MouseDownHandler<V> = Arc<
- dyn Fn(&mut V, &MouseDownEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
- + Send
- + Sync
- + 'static,
->;
-type MouseUpHandler<V> = Arc<
- dyn Fn(&mut V, &MouseUpEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
- + Send
- + Sync
- + 'static,
->;
-
-type MouseMoveHandler<V> = Arc<
- dyn Fn(&mut V, &MouseMoveEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
- + Send
- + Sync
- + 'static,
->;
-type ScrollWheelHandler<V> = Arc<
- dyn Fn(&mut V, &ScrollWheelEvent, &Bounds<Pixels>, DispatchPhase, &mut ViewContext<V>)
- + Send
- + Sync
- + 'static,
->;
-
-pub struct MouseEventListeners<V: 'static> {
- mouse_down: SmallVec<[MouseDownHandler<V>; 2]>,
- mouse_up: SmallVec<[MouseUpHandler<V>; 2]>,
- mouse_move: SmallVec<[MouseMoveHandler<V>; 2]>,
- scroll_wheel: SmallVec<[ScrollWheelHandler<V>; 2]>,
-}
-
-impl<S: Send + Sync + 'static> MouseEventListeners<S> {
- pub fn paint(&self, bounds: Bounds<Pixels>, cx: &mut ViewContext<S>) {
- for handler in self.mouse_down.iter().cloned() {
- cx.on_mouse_event(move |view, event: &MouseDownEvent, phase, cx| {
- handler(view, event, &bounds, phase, cx);
- })
- }
- for handler in self.mouse_up.iter().cloned() {
- cx.on_mouse_event(move |view, event: &MouseUpEvent, phase, cx| {
- handler(view, event, &bounds, phase, cx);
- })
- }
- for handler in self.mouse_move.iter().cloned() {
- cx.on_mouse_event(move |view, event: &MouseMoveEvent, phase, cx| {
- handler(view, event, &bounds, phase, cx);
- })
- }
-
- for handler in self.scroll_wheel.iter().cloned() {
- cx.on_mouse_event(move |view, event: &ScrollWheelEvent, phase, cx| {
- handler(view, event, &bounds, phase, cx);
- })
- }
- }
-}
-
-impl<V> Default for MouseEventListeners<V> {
- fn default() -> Self {
- Self {
- mouse_down: Default::default(),
- mouse_up: Default::default(),
- mouse_move: Default::default(),
- scroll_wheel: Default::default(),
- }
- }
-}
@@ -1,16 +1,12 @@
use crate::{
self as gpui3, hsla, point, px, relative, rems, AlignItems, Display, Fill, FlexDirection, Hsla,
- JustifyContent, Length, Position, SharedString, Style, StyleCascade, StyleRefinement,
+ JustifyContent, Length, Position, SharedString, StyleRefinement,
};
use crate::{BoxShadow, TextStyleRefinement};
use smallvec::smallvec;
pub trait Styled {
- fn style_cascade(&mut self) -> &mut StyleCascade;
- fn computed_style(&mut self) -> &Style;
- fn base_style(&mut self) -> &mut StyleRefinement {
- self.style_cascade().base()
- }
+ fn style(&mut self) -> &mut StyleRefinement;
gpui3_macros::style_helpers!();
@@ -18,8 +14,8 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().size.width = Some(relative(1.).into());
- self.base_style().size.height = Some(relative(1.).into());
+ self.style().size.width = Some(relative(1.).into());
+ self.style().size.height = Some(relative(1.).into());
self
}
@@ -27,7 +23,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().position = Some(Position::Relative);
+ self.style().position = Some(Position::Relative);
self
}
@@ -35,7 +31,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().position = Some(Position::Absolute);
+ self.style().position = Some(Position::Absolute);
self
}
@@ -43,7 +39,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().display = Some(Display::Block);
+ self.style().display = Some(Display::Block);
self
}
@@ -51,7 +47,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().display = Some(Display::Flex);
+ self.style().display = Some(Display::Flex);
self
}
@@ -59,7 +55,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().flex_direction = Some(FlexDirection::Column);
+ self.style().flex_direction = Some(FlexDirection::Column);
self
}
@@ -67,7 +63,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().flex_direction = Some(FlexDirection::Row);
+ self.style().flex_direction = Some(FlexDirection::Row);
self
}
@@ -75,9 +71,9 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().flex_grow = Some(1.);
- self.base_style().flex_shrink = Some(1.);
- self.base_style().flex_basis = Some(relative(0.).into());
+ self.style().flex_grow = Some(1.);
+ self.style().flex_shrink = Some(1.);
+ self.style().flex_basis = Some(relative(0.).into());
self
}
@@ -85,9 +81,9 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().flex_grow = Some(1.);
- self.base_style().flex_shrink = Some(1.);
- self.base_style().flex_basis = Some(Length::Auto);
+ self.style().flex_grow = Some(1.);
+ self.style().flex_shrink = Some(1.);
+ self.style().flex_basis = Some(Length::Auto);
self
}
@@ -95,9 +91,9 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().flex_grow = Some(0.);
- self.base_style().flex_shrink = Some(1.);
- self.base_style().flex_basis = Some(Length::Auto);
+ self.style().flex_grow = Some(0.);
+ self.style().flex_shrink = Some(1.);
+ self.style().flex_basis = Some(Length::Auto);
self
}
@@ -105,8 +101,8 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().flex_grow = Some(0.);
- self.base_style().flex_shrink = Some(0.);
+ self.style().flex_grow = Some(0.);
+ self.style().flex_shrink = Some(0.);
self
}
@@ -114,7 +110,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().flex_grow = Some(1.);
+ self.style().flex_grow = Some(1.);
self
}
@@ -122,7 +118,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().align_items = Some(AlignItems::FlexStart);
+ self.style().align_items = Some(AlignItems::FlexStart);
self
}
@@ -130,7 +126,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().align_items = Some(AlignItems::FlexEnd);
+ self.style().align_items = Some(AlignItems::FlexEnd);
self
}
@@ -138,7 +134,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().align_items = Some(AlignItems::Center);
+ self.style().align_items = Some(AlignItems::Center);
self
}
@@ -146,7 +142,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().justify_content = Some(JustifyContent::SpaceBetween);
+ self.style().justify_content = Some(JustifyContent::SpaceBetween);
self
}
@@ -154,7 +150,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().justify_content = Some(JustifyContent::Center);
+ self.style().justify_content = Some(JustifyContent::Center);
self
}
@@ -162,7 +158,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().justify_content = Some(JustifyContent::Start);
+ self.style().justify_content = Some(JustifyContent::Start);
self
}
@@ -170,7 +166,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().justify_content = Some(JustifyContent::End);
+ self.style().justify_content = Some(JustifyContent::End);
self
}
@@ -178,7 +174,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().justify_content = Some(JustifyContent::SpaceAround);
+ self.style().justify_content = Some(JustifyContent::SpaceAround);
self
}
@@ -187,7 +183,7 @@ pub trait Styled {
F: Into<Fill>,
Self: Sized,
{
- self.base_style().fill = Some(fill.into());
+ self.style().fill = Some(fill.into());
self
}
@@ -196,7 +192,7 @@ pub trait Styled {
C: Into<Hsla>,
Self: Sized,
{
- self.base_style().border_color = Some(border_color.into());
+ self.style().border_color = Some(border_color.into());
self
}
@@ -204,7 +200,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().box_shadow = Some(smallvec![
+ self.style().box_shadow = Some(smallvec![
BoxShadow {
color: hsla(0., 0., 0., 0.1),
offset: point(px(0.), px(1.)),
@@ -225,7 +221,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().box_shadow = Some(Default::default());
+ self.style().box_shadow = Some(Default::default());
self
}
@@ -233,7 +229,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().box_shadow = Some(smallvec::smallvec![BoxShadow {
+ self.style().box_shadow = Some(smallvec::smallvec![BoxShadow {
color: hsla(0., 0., 0., 0.05),
offset: point(px(0.), px(1.)),
blur_radius: px(2.),
@@ -246,7 +242,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().box_shadow = Some(smallvec![
+ self.style().box_shadow = Some(smallvec![
BoxShadow {
color: hsla(0.5, 0., 0., 0.1),
offset: point(px(0.), px(4.)),
@@ -267,7 +263,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().box_shadow = Some(smallvec![
+ self.style().box_shadow = Some(smallvec![
BoxShadow {
color: hsla(0., 0., 0., 0.1),
offset: point(px(0.), px(10.)),
@@ -288,7 +284,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().box_shadow = Some(smallvec![
+ self.style().box_shadow = Some(smallvec![
BoxShadow {
color: hsla(0., 0., 0., 0.1),
offset: point(px(0.), px(20.)),
@@ -309,7 +305,7 @@ pub trait Styled {
where
Self: Sized,
{
- self.base_style().box_shadow = Some(smallvec![BoxShadow {
+ self.style().box_shadow = Some(smallvec![BoxShadow {
color: hsla(0., 0., 0., 0.25),
offset: point(px(0.), px(25.)),
blur_radius: px(50.),
@@ -319,7 +315,7 @@ pub trait Styled {
}
fn text_style(&mut self) -> &mut Option<TextStyleRefinement> {
- let style: &mut StyleRefinement = self.base_style();
+ let style: &mut StyleRefinement = self.style();
&mut style.text
}
@@ -129,7 +129,7 @@ fn generate_predefined_setter(
let method = quote! {
#[doc = #doc_string]
fn #method_name(mut self) -> Self where Self: std::marker::Sized {
- let mut style = self.base_style();
+ let style = self.style();
#(#field_assignments)*
self
}
@@ -160,7 +160,7 @@ fn generate_custom_value_setter(
let method = quote! {
fn #method_name(mut self, length: impl std::clone::Clone + Into<gpui3::#length_type>) -> Self where Self: std::marker::Sized {
- let mut style = self.base_style();
+ let style = self.style();
#(#field_assignments)*
self
}