element_cx.rs

   1use std::{
   2    any::{Any, TypeId},
   3    borrow::{Borrow, BorrowMut, Cow},
   4    mem,
   5    rc::Rc,
   6    sync::Arc,
   7};
   8
   9use anyhow::Result;
  10use collections::{FxHashMap, FxHashSet};
  11use derive_more::{Deref, DerefMut};
  12use media::core_video::CVImageBuffer;
  13use smallvec::SmallVec;
  14use util::post_inc;
  15
  16use crate::{
  17    prelude::*, size, AnyTooltip, AppContext, AvailableSpace, Bounds, BoxShadow, ContentMask,
  18    Corners, CursorStyle, DevicePixels, DispatchPhase, DispatchTree, ElementId, ElementStateBox,
  19    EntityId, FocusHandle, FocusId, FontId, GlobalElementId, GlyphId, Hsla, ImageData,
  20    InputHandler, IsZero, KeyContext, KeyEvent, LayoutId, MonochromeSprite, MouseEvent, PaintQuad,
  21    Path, Pixels, PlatformInputHandler, Point, PolychromeSprite, Quad, RenderGlyphParams,
  22    RenderImageParams, RenderSvgParams, Scene, Shadow, SharedString, Size, StackingContext,
  23    StackingOrder, Style, Surface, TextStyleRefinement, Underline, UnderlineStyle, Window,
  24    WindowContext, SUBPIXEL_VARIANTS,
  25};
  26
  27type AnyMouseListener = Box<dyn FnMut(&dyn Any, DispatchPhase, &mut ElementContext) + 'static>;
  28
  29pub(crate) struct RequestedInputHandler {
  30    pub(crate) view_id: EntityId,
  31    pub(crate) handler: Option<PlatformInputHandler>,
  32}
  33
  34pub(crate) struct TooltipRequest {
  35    pub(crate) view_id: EntityId,
  36    pub(crate) tooltip: AnyTooltip,
  37}
  38
  39pub(crate) struct Frame {
  40    pub(crate) focus: Option<FocusId>,
  41    pub(crate) window_active: bool,
  42    pub(crate) element_states: FxHashMap<GlobalElementId, ElementStateBox>,
  43    pub(crate) mouse_listeners: FxHashMap<TypeId, Vec<(StackingOrder, EntityId, AnyMouseListener)>>,
  44    pub(crate) dispatch_tree: DispatchTree,
  45    pub(crate) scene: Scene,
  46    pub(crate) depth_map: Vec<(StackingOrder, EntityId, Bounds<Pixels>)>,
  47    pub(crate) z_index_stack: StackingOrder,
  48    pub(crate) next_stacking_order_id: u16,
  49    pub(crate) next_root_z_index: u16,
  50    pub(crate) content_mask_stack: Vec<ContentMask<Pixels>>,
  51    pub(crate) element_offset_stack: Vec<Point<Pixels>>,
  52    pub(crate) requested_input_handler: Option<RequestedInputHandler>,
  53    pub(crate) tooltip_request: Option<TooltipRequest>,
  54    pub(crate) cursor_styles: FxHashMap<EntityId, CursorStyle>,
  55    pub(crate) requested_cursor_style: Option<CursorStyle>,
  56    pub(crate) view_stack: Vec<EntityId>,
  57    pub(crate) reused_views: FxHashSet<EntityId>,
  58
  59    #[cfg(any(test, feature = "test-support"))]
  60    pub(crate) debug_bounds: collections::FxHashMap<String, Bounds<Pixels>>,
  61}
  62
  63impl Frame {
  64    pub(crate) fn new(dispatch_tree: DispatchTree) -> Self {
  65        Frame {
  66            focus: None,
  67            window_active: false,
  68            element_states: FxHashMap::default(),
  69            mouse_listeners: FxHashMap::default(),
  70            dispatch_tree,
  71            scene: Scene::default(),
  72            depth_map: Vec::new(),
  73            z_index_stack: StackingOrder::default(),
  74            next_stacking_order_id: 0,
  75            next_root_z_index: 0,
  76            content_mask_stack: Vec::new(),
  77            element_offset_stack: Vec::new(),
  78            requested_input_handler: None,
  79            tooltip_request: None,
  80            cursor_styles: FxHashMap::default(),
  81            requested_cursor_style: None,
  82            view_stack: Vec::new(),
  83            reused_views: FxHashSet::default(),
  84
  85            #[cfg(any(test, feature = "test-support"))]
  86            debug_bounds: FxHashMap::default(),
  87        }
  88    }
  89
  90    pub(crate) fn clear(&mut self) {
  91        self.element_states.clear();
  92        self.mouse_listeners.values_mut().for_each(Vec::clear);
  93        self.dispatch_tree.clear();
  94        self.depth_map.clear();
  95        self.next_stacking_order_id = 0;
  96        self.next_root_z_index = 0;
  97        self.reused_views.clear();
  98        self.scene.clear();
  99        self.requested_input_handler.take();
 100        self.tooltip_request.take();
 101        self.cursor_styles.clear();
 102        self.requested_cursor_style.take();
 103        debug_assert_eq!(self.view_stack.len(), 0);
 104    }
 105
 106    pub(crate) fn focus_path(&self) -> SmallVec<[FocusId; 8]> {
 107        self.focus
 108            .map(|focus_id| self.dispatch_tree.focus_path(focus_id))
 109            .unwrap_or_default()
 110    }
 111
 112    pub(crate) fn finish(&mut self, prev_frame: &mut Self) {
 113        // Reuse mouse listeners that didn't change since the last frame.
 114        for (type_id, listeners) in &mut prev_frame.mouse_listeners {
 115            let next_listeners = self.mouse_listeners.entry(*type_id).or_default();
 116            for (order, view_id, listener) in listeners.drain(..) {
 117                if self.reused_views.contains(&view_id) {
 118                    next_listeners.push((order, view_id, listener));
 119                }
 120            }
 121        }
 122
 123        // Reuse entries in the depth map that didn't change since the last frame.
 124        for (order, view_id, bounds) in prev_frame.depth_map.drain(..) {
 125            if self.reused_views.contains(&view_id) {
 126                match self
 127                    .depth_map
 128                    .binary_search_by(|(level, _, _)| order.cmp(level))
 129                {
 130                    Ok(i) | Err(i) => self.depth_map.insert(i, (order, view_id, bounds)),
 131                }
 132            }
 133        }
 134
 135        // Retain element states for views that didn't change since the last frame.
 136        for (element_id, state) in prev_frame.element_states.drain() {
 137            if self.reused_views.contains(&state.parent_view_id) {
 138                self.element_states.entry(element_id).or_insert(state);
 139            }
 140        }
 141
 142        // Reuse geometry that didn't change since the last frame.
 143        self.scene
 144            .reuse_views(&self.reused_views, &mut prev_frame.scene);
 145        self.scene.finish();
 146    }
 147}
 148
 149/// This context is used for assisting in the implementation of the element trait
 150#[derive(Deref, DerefMut)]
 151pub struct ElementContext<'a> {
 152    pub(crate) cx: WindowContext<'a>,
 153}
 154
 155impl<'a> WindowContext<'a> {
 156    pub fn with_element_context<R>(&mut self, f: impl FnOnce(&mut ElementContext) -> R) -> R {
 157        f(&mut ElementContext {
 158            cx: WindowContext::new(self.app, self.window),
 159        })
 160    }
 161}
 162
 163impl<'a> Borrow<AppContext> for ElementContext<'a> {
 164    fn borrow(&self) -> &AppContext {
 165        self.cx.app
 166    }
 167}
 168
 169impl<'a> BorrowMut<AppContext> for ElementContext<'a> {
 170    fn borrow_mut(&mut self) -> &mut AppContext {
 171        self.cx.borrow_mut()
 172    }
 173}
 174
 175impl<'a> Borrow<WindowContext<'a>> for ElementContext<'a> {
 176    fn borrow(&self) -> &WindowContext<'a> {
 177        &self.cx
 178    }
 179}
 180
 181impl<'a> BorrowMut<WindowContext<'a>> for ElementContext<'a> {
 182    fn borrow_mut(&mut self) -> &mut WindowContext<'a> {
 183        &mut self.cx
 184    }
 185}
 186
 187impl<'a> Borrow<Window> for ElementContext<'a> {
 188    fn borrow(&self) -> &Window {
 189        self.cx.window
 190    }
 191}
 192
 193impl<'a> BorrowMut<Window> for ElementContext<'a> {
 194    fn borrow_mut(&mut self) -> &mut Window {
 195        self.cx.borrow_mut()
 196    }
 197}
 198
 199impl<'a> Context for ElementContext<'a> {
 200    type Result<T> = <WindowContext<'a> as Context>::Result<T>;
 201
 202    fn new_model<T: 'static>(
 203        &mut self,
 204        build_model: impl FnOnce(&mut crate::ModelContext<'_, T>) -> T,
 205    ) -> Self::Result<crate::Model<T>> {
 206        self.cx.new_model(build_model)
 207    }
 208
 209    fn update_model<T, R>(
 210        &mut self,
 211        handle: &crate::Model<T>,
 212        update: impl FnOnce(&mut T, &mut crate::ModelContext<'_, T>) -> R,
 213    ) -> Self::Result<R>
 214    where
 215        T: 'static,
 216    {
 217        self.cx.update_model(handle, update)
 218    }
 219
 220    fn read_model<T, R>(
 221        &self,
 222        handle: &crate::Model<T>,
 223        read: impl FnOnce(&T, &AppContext) -> R,
 224    ) -> Self::Result<R>
 225    where
 226        T: 'static,
 227    {
 228        self.cx.read_model(handle, read)
 229    }
 230
 231    fn update_window<T, F>(&mut self, window: crate::AnyWindowHandle, f: F) -> Result<T>
 232    where
 233        F: FnOnce(crate::AnyView, &mut WindowContext<'_>) -> T,
 234    {
 235        self.cx.update_window(window, f)
 236    }
 237
 238    fn read_window<T, R>(
 239        &self,
 240        window: &crate::WindowHandle<T>,
 241        read: impl FnOnce(crate::View<T>, &AppContext) -> R,
 242    ) -> Result<R>
 243    where
 244        T: 'static,
 245    {
 246        self.cx.read_window(window, read)
 247    }
 248}
 249
 250impl<'a> VisualContext for ElementContext<'a> {
 251    fn new_view<V>(
 252        &mut self,
 253        build_view: impl FnOnce(&mut crate::ViewContext<'_, V>) -> V,
 254    ) -> Self::Result<crate::View<V>>
 255    where
 256        V: 'static + Render,
 257    {
 258        self.cx.new_view(build_view)
 259    }
 260
 261    fn update_view<V: 'static, R>(
 262        &mut self,
 263        view: &crate::View<V>,
 264        update: impl FnOnce(&mut V, &mut crate::ViewContext<'_, V>) -> R,
 265    ) -> Self::Result<R> {
 266        self.cx.update_view(view, update)
 267    }
 268
 269    fn replace_root_view<V>(
 270        &mut self,
 271        build_view: impl FnOnce(&mut crate::ViewContext<'_, V>) -> V,
 272    ) -> Self::Result<crate::View<V>>
 273    where
 274        V: 'static + Render,
 275    {
 276        self.cx.replace_root_view(build_view)
 277    }
 278
 279    fn focus_view<V>(&mut self, view: &crate::View<V>) -> Self::Result<()>
 280    where
 281        V: crate::FocusableView,
 282    {
 283        self.cx.focus_view(view)
 284    }
 285
 286    fn dismiss_view<V>(&mut self, view: &crate::View<V>) -> Self::Result<()>
 287    where
 288        V: crate::ManagedView,
 289    {
 290        self.cx.dismiss_view(view)
 291    }
 292}
 293
 294impl<'a> ElementContext<'a> {
 295    pub(crate) fn reuse_view(&mut self, next_stacking_order_id: u16) {
 296        let view_id = self.parent_view_id();
 297        let grafted_view_ids = self
 298            .cx
 299            .window
 300            .next_frame
 301            .dispatch_tree
 302            .reuse_view(view_id, &mut self.cx.window.rendered_frame.dispatch_tree);
 303        for view_id in grafted_view_ids {
 304            assert!(self.window.next_frame.reused_views.insert(view_id));
 305
 306            // Reuse the previous input handler requested during painting of the reused view.
 307            if self
 308                .window
 309                .rendered_frame
 310                .requested_input_handler
 311                .as_ref()
 312                .map_or(false, |requested| requested.view_id == view_id)
 313            {
 314                self.window.next_frame.requested_input_handler =
 315                    self.window.rendered_frame.requested_input_handler.take();
 316            }
 317
 318            // Reuse the tooltip previously requested during painting of the reused view.
 319            if self
 320                .window
 321                .rendered_frame
 322                .tooltip_request
 323                .as_ref()
 324                .map_or(false, |requested| requested.view_id == view_id)
 325            {
 326                self.window.next_frame.tooltip_request =
 327                    self.window.rendered_frame.tooltip_request.take();
 328            }
 329
 330            // Reuse the cursor styles previously requested during painting of the reused view.
 331            if let Some(style) = self.window.rendered_frame.cursor_styles.remove(&view_id) {
 332                self.window.next_frame.cursor_styles.insert(view_id, style);
 333                self.window.next_frame.requested_cursor_style = Some(style);
 334            }
 335        }
 336
 337        debug_assert!(next_stacking_order_id >= self.window.next_frame.next_stacking_order_id);
 338        self.window.next_frame.next_stacking_order_id = next_stacking_order_id;
 339    }
 340
 341    pub fn with_text_style<F, R>(&mut self, style: Option<TextStyleRefinement>, f: F) -> R
 342    where
 343        F: FnOnce(&mut Self) -> R,
 344    {
 345        if let Some(style) = style {
 346            self.push_text_style(style);
 347            let result = f(self);
 348            self.pop_text_style();
 349            result
 350        } else {
 351            f(self)
 352        }
 353    }
 354
 355    /// Updates the cursor style at the platform level.
 356    pub fn set_cursor_style(&mut self, style: CursorStyle) {
 357        let view_id = self.parent_view_id();
 358        self.window.next_frame.cursor_styles.insert(view_id, style);
 359        self.window.next_frame.requested_cursor_style = Some(style);
 360    }
 361
 362    /// Sets a tooltip to be rendered for the upcoming frame
 363    pub fn set_tooltip(&mut self, tooltip: AnyTooltip) {
 364        let view_id = self.parent_view_id();
 365        self.window.next_frame.tooltip_request = Some(TooltipRequest { view_id, tooltip });
 366    }
 367
 368    /// Pushes the given element id onto the global stack and invokes the given closure
 369    /// with a `GlobalElementId`, which disambiguates the given id in the context of its ancestor
 370    /// ids. Because elements are discarded and recreated on each frame, the `GlobalElementId` is
 371    /// used to associate state with identified elements across separate frames.
 372    pub fn with_element_id<R>(
 373        &mut self,
 374        id: Option<impl Into<ElementId>>,
 375        f: impl FnOnce(&mut Self) -> R,
 376    ) -> R {
 377        if let Some(id) = id.map(Into::into) {
 378            let window = self.window_mut();
 379            window.element_id_stack.push(id);
 380            let result = f(self);
 381            let window: &mut Window = self.borrow_mut();
 382            window.element_id_stack.pop();
 383            result
 384        } else {
 385            f(self)
 386        }
 387    }
 388
 389    /// Invoke the given function with the given content mask after intersecting it
 390    /// with the current mask.
 391    pub fn with_content_mask<R>(
 392        &mut self,
 393        mask: Option<ContentMask<Pixels>>,
 394        f: impl FnOnce(&mut Self) -> R,
 395    ) -> R {
 396        if let Some(mask) = mask {
 397            let mask = mask.intersect(&self.content_mask());
 398            self.window_mut().next_frame.content_mask_stack.push(mask);
 399            let result = f(self);
 400            self.window_mut().next_frame.content_mask_stack.pop();
 401            result
 402        } else {
 403            f(self)
 404        }
 405    }
 406
 407    /// Invoke the given function with the content mask reset to that
 408    /// of the window.
 409    pub fn break_content_mask<R>(&mut self, f: impl FnOnce(&mut Self) -> R) -> R {
 410        let mask = ContentMask {
 411            bounds: Bounds {
 412                origin: Point::default(),
 413                size: self.window().viewport_size,
 414            },
 415        };
 416
 417        let new_root_z_index = post_inc(&mut self.window_mut().next_frame.next_root_z_index);
 418        let new_stacking_order_id =
 419            post_inc(&mut self.window_mut().next_frame.next_stacking_order_id);
 420        let new_context = StackingContext {
 421            z_index: new_root_z_index,
 422            id: new_stacking_order_id,
 423        };
 424
 425        let old_stacking_order = mem::take(&mut self.window_mut().next_frame.z_index_stack);
 426
 427        self.window_mut().next_frame.z_index_stack.push(new_context);
 428        self.window_mut().next_frame.content_mask_stack.push(mask);
 429        let result = f(self);
 430        self.window_mut().next_frame.content_mask_stack.pop();
 431        self.window_mut().next_frame.z_index_stack = old_stacking_order;
 432
 433        result
 434    }
 435
 436    /// Called during painting to invoke the given closure in a new stacking context. The given
 437    /// z-index is interpreted relative to the previous call to `stack`.
 438    pub fn with_z_index<R>(&mut self, z_index: u16, f: impl FnOnce(&mut Self) -> R) -> R {
 439        let new_stacking_order_id =
 440            post_inc(&mut self.window_mut().next_frame.next_stacking_order_id);
 441        let new_context = StackingContext {
 442            z_index,
 443            id: new_stacking_order_id,
 444        };
 445
 446        self.window_mut().next_frame.z_index_stack.push(new_context);
 447        let result = f(self);
 448        self.window_mut().next_frame.z_index_stack.pop();
 449
 450        result
 451    }
 452
 453    /// Updates the global element offset relative to the current offset. This is used to implement
 454    /// scrolling.
 455    pub fn with_element_offset<R>(
 456        &mut self,
 457        offset: Point<Pixels>,
 458        f: impl FnOnce(&mut Self) -> R,
 459    ) -> R {
 460        if offset.is_zero() {
 461            return f(self);
 462        };
 463
 464        let abs_offset = self.element_offset() + offset;
 465        self.with_absolute_element_offset(abs_offset, f)
 466    }
 467
 468    /// Updates the global element offset based on the given offset. This is used to implement
 469    /// drag handles and other manual painting of elements.
 470    pub fn with_absolute_element_offset<R>(
 471        &mut self,
 472        offset: Point<Pixels>,
 473        f: impl FnOnce(&mut Self) -> R,
 474    ) -> R {
 475        self.window_mut()
 476            .next_frame
 477            .element_offset_stack
 478            .push(offset);
 479        let result = f(self);
 480        self.window_mut().next_frame.element_offset_stack.pop();
 481        result
 482    }
 483
 484    /// Obtain the current element offset.
 485    pub fn element_offset(&self) -> Point<Pixels> {
 486        self.window()
 487            .next_frame
 488            .element_offset_stack
 489            .last()
 490            .copied()
 491            .unwrap_or_default()
 492    }
 493
 494    /// Obtain the current content mask.
 495    pub fn content_mask(&self) -> ContentMask<Pixels> {
 496        self.window()
 497            .next_frame
 498            .content_mask_stack
 499            .last()
 500            .cloned()
 501            .unwrap_or_else(|| ContentMask {
 502                bounds: Bounds {
 503                    origin: Point::default(),
 504                    size: self.window().viewport_size,
 505                },
 506            })
 507    }
 508
 509    /// The size of an em for the base font of the application. Adjusting this value allows the
 510    /// UI to scale, just like zooming a web page.
 511    pub fn rem_size(&self) -> Pixels {
 512        self.window().rem_size
 513    }
 514
 515    /// Updates or initializes state for an element with the given id that lives across multiple
 516    /// frames. If an element with this ID existed in the rendered frame, its state will be passed
 517    /// to the given closure. The state returned by the closure will be stored so it can be referenced
 518    /// when drawing the next frame.
 519    pub fn with_element_state<S, R>(
 520        &mut self,
 521        id: ElementId,
 522        f: impl FnOnce(Option<S>, &mut Self) -> (R, S),
 523    ) -> R
 524    where
 525        S: 'static,
 526    {
 527        self.with_element_id(Some(id), |cx| {
 528                let global_id = cx.window().element_id_stack.clone();
 529
 530                if let Some(any) = cx
 531                    .window_mut()
 532                    .next_frame
 533                    .element_states
 534                    .remove(&global_id)
 535                    .or_else(|| {
 536                        cx.window_mut()
 537                            .rendered_frame
 538                            .element_states
 539                            .remove(&global_id)
 540                    })
 541                {
 542                    let ElementStateBox {
 543                        inner,
 544                        parent_view_id,
 545                        #[cfg(debug_assertions)]
 546                        type_name
 547                    } = any;
 548                    // Using the extra inner option to avoid needing to reallocate a new box.
 549                    let mut state_box = inner
 550                        .downcast::<Option<S>>()
 551                        .map_err(|_| {
 552                            #[cfg(debug_assertions)]
 553                            {
 554                                anyhow::anyhow!(
 555                                    "invalid element state type for id, requested_type {:?}, actual type: {:?}",
 556                                    std::any::type_name::<S>(),
 557                                    type_name
 558                                )
 559                            }
 560
 561                            #[cfg(not(debug_assertions))]
 562                            {
 563                                anyhow::anyhow!(
 564                                    "invalid element state type for id, requested_type {:?}",
 565                                    std::any::type_name::<S>(),
 566                                )
 567                            }
 568                        })
 569                        .unwrap();
 570
 571                    // Actual: Option<AnyElement> <- View
 572                    // Requested: () <- AnyElement
 573                    let state = state_box
 574                        .take()
 575                        .expect("element state is already on the stack");
 576                    let (result, state) = f(Some(state), cx);
 577                    state_box.replace(state);
 578                    cx.window_mut()
 579                        .next_frame
 580                        .element_states
 581                        .insert(global_id, ElementStateBox {
 582                            inner: state_box,
 583                            parent_view_id,
 584                            #[cfg(debug_assertions)]
 585                            type_name
 586                        });
 587                    result
 588                } else {
 589                    let (result, state) = f(None, cx);
 590                    let parent_view_id = cx.parent_view_id();
 591                    cx.window_mut()
 592                        .next_frame
 593                        .element_states
 594                        .insert(global_id,
 595                            ElementStateBox {
 596                                inner: Box::new(Some(state)),
 597                                parent_view_id,
 598                                #[cfg(debug_assertions)]
 599                                type_name: std::any::type_name::<S>()
 600                            }
 601
 602                        );
 603                    result
 604                }
 605            })
 606    }
 607    /// Paint one or more drop shadows into the scene for the next frame at the current z-index.
 608    pub fn paint_shadows(
 609        &mut self,
 610        bounds: Bounds<Pixels>,
 611        corner_radii: Corners<Pixels>,
 612        shadows: &[BoxShadow],
 613    ) {
 614        let scale_factor = self.scale_factor();
 615        let content_mask = self.content_mask();
 616        let view_id = self.parent_view_id();
 617        let window = &mut *self.window;
 618        for shadow in shadows {
 619            let mut shadow_bounds = bounds;
 620            shadow_bounds.origin += shadow.offset;
 621            shadow_bounds.dilate(shadow.spread_radius);
 622            window.next_frame.scene.insert(
 623                &window.next_frame.z_index_stack,
 624                Shadow {
 625                    view_id: view_id.into(),
 626                    layer_id: 0,
 627                    order: 0,
 628                    bounds: shadow_bounds.scale(scale_factor),
 629                    content_mask: content_mask.scale(scale_factor),
 630                    corner_radii: corner_radii.scale(scale_factor),
 631                    color: shadow.color,
 632                    blur_radius: shadow.blur_radius.scale(scale_factor),
 633                },
 634            );
 635        }
 636    }
 637
 638    /// Paint one or more quads into the scene for the next frame at the current stacking context.
 639    /// Quads are colored rectangular regions with an optional background, border, and corner radius.
 640    /// see [`fill`], [`outline`], and [`quad`] to construct this type.
 641    pub fn paint_quad(&mut self, quad: PaintQuad) {
 642        let scale_factor = self.scale_factor();
 643        let content_mask = self.content_mask();
 644        let view_id = self.parent_view_id();
 645
 646        let window = &mut *self.window;
 647        window.next_frame.scene.insert(
 648            &window.next_frame.z_index_stack,
 649            Quad {
 650                view_id: view_id.into(),
 651                layer_id: 0,
 652                order: 0,
 653                bounds: quad.bounds.scale(scale_factor),
 654                content_mask: content_mask.scale(scale_factor),
 655                background: quad.background,
 656                border_color: quad.border_color,
 657                corner_radii: quad.corner_radii.scale(scale_factor),
 658                border_widths: quad.border_widths.scale(scale_factor),
 659            },
 660        );
 661    }
 662
 663    /// Paint the given `Path` into the scene for the next frame at the current z-index.
 664    pub fn paint_path(&mut self, mut path: Path<Pixels>, color: impl Into<Hsla>) {
 665        let scale_factor = self.scale_factor();
 666        let content_mask = self.content_mask();
 667        let view_id = self.parent_view_id();
 668
 669        path.content_mask = content_mask;
 670        path.color = color.into();
 671        path.view_id = view_id.into();
 672        let window = &mut *self.window;
 673        window
 674            .next_frame
 675            .scene
 676            .insert(&window.next_frame.z_index_stack, path.scale(scale_factor));
 677    }
 678
 679    /// Paint an underline into the scene for the next frame at the current z-index.
 680    pub fn paint_underline(
 681        &mut self,
 682        origin: Point<Pixels>,
 683        width: Pixels,
 684        style: &UnderlineStyle,
 685    ) {
 686        let scale_factor = self.scale_factor();
 687        let height = if style.wavy {
 688            style.thickness * 3.
 689        } else {
 690            style.thickness
 691        };
 692        let bounds = Bounds {
 693            origin,
 694            size: size(width, height),
 695        };
 696        let content_mask = self.content_mask();
 697        let view_id = self.parent_view_id();
 698
 699        let window = &mut *self.window;
 700        window.next_frame.scene.insert(
 701            &window.next_frame.z_index_stack,
 702            Underline {
 703                view_id: view_id.into(),
 704                layer_id: 0,
 705                order: 0,
 706                bounds: bounds.scale(scale_factor),
 707                content_mask: content_mask.scale(scale_factor),
 708                thickness: style.thickness.scale(scale_factor),
 709                color: style.color.unwrap_or_default(),
 710                wavy: style.wavy,
 711            },
 712        );
 713    }
 714
 715    /// Paint a monochrome (non-emoji) glyph into the scene for the next frame at the current z-index.
 716    /// The y component of the origin is the baseline of the glyph.
 717    pub fn paint_glyph(
 718        &mut self,
 719        origin: Point<Pixels>,
 720        font_id: FontId,
 721        glyph_id: GlyphId,
 722        font_size: Pixels,
 723        color: Hsla,
 724    ) -> Result<()> {
 725        let scale_factor = self.scale_factor();
 726        let glyph_origin = origin.scale(scale_factor);
 727        let subpixel_variant = Point {
 728            x: (glyph_origin.x.0.fract() * SUBPIXEL_VARIANTS as f32).floor() as u8,
 729            y: (glyph_origin.y.0.fract() * SUBPIXEL_VARIANTS as f32).floor() as u8,
 730        };
 731        let params = RenderGlyphParams {
 732            font_id,
 733            glyph_id,
 734            font_size,
 735            subpixel_variant,
 736            scale_factor,
 737            is_emoji: false,
 738        };
 739
 740        let raster_bounds = self.text_system().raster_bounds(&params)?;
 741        if !raster_bounds.is_zero() {
 742            let tile =
 743                self.window
 744                    .sprite_atlas
 745                    .get_or_insert_with(&params.clone().into(), &mut || {
 746                        let (size, bytes) = self.text_system().rasterize_glyph(&params)?;
 747                        Ok((size, Cow::Owned(bytes)))
 748                    })?;
 749            let bounds = Bounds {
 750                origin: glyph_origin.map(|px| px.floor()) + raster_bounds.origin.map(Into::into),
 751                size: tile.bounds.size.map(Into::into),
 752            };
 753            let content_mask = self.content_mask().scale(scale_factor);
 754            let view_id = self.parent_view_id();
 755            let window = &mut *self.window;
 756            window.next_frame.scene.insert(
 757                &window.next_frame.z_index_stack,
 758                MonochromeSprite {
 759                    view_id: view_id.into(),
 760                    layer_id: 0,
 761                    order: 0,
 762                    bounds,
 763                    content_mask,
 764                    color,
 765                    tile,
 766                },
 767            );
 768        }
 769        Ok(())
 770    }
 771
 772    /// Paint an emoji glyph into the scene for the next frame at the current z-index.
 773    /// The y component of the origin is the baseline of the glyph.
 774    pub fn paint_emoji(
 775        &mut self,
 776        origin: Point<Pixels>,
 777        font_id: FontId,
 778        glyph_id: GlyphId,
 779        font_size: Pixels,
 780    ) -> Result<()> {
 781        let scale_factor = self.scale_factor();
 782        let glyph_origin = origin.scale(scale_factor);
 783        let params = RenderGlyphParams {
 784            font_id,
 785            glyph_id,
 786            font_size,
 787            // We don't render emojis with subpixel variants.
 788            subpixel_variant: Default::default(),
 789            scale_factor,
 790            is_emoji: true,
 791        };
 792
 793        let raster_bounds = self.text_system().raster_bounds(&params)?;
 794        if !raster_bounds.is_zero() {
 795            let tile =
 796                self.window
 797                    .sprite_atlas
 798                    .get_or_insert_with(&params.clone().into(), &mut || {
 799                        let (size, bytes) = self.text_system().rasterize_glyph(&params)?;
 800                        Ok((size, Cow::Owned(bytes)))
 801                    })?;
 802            let bounds = Bounds {
 803                origin: glyph_origin.map(|px| px.floor()) + raster_bounds.origin.map(Into::into),
 804                size: tile.bounds.size.map(Into::into),
 805            };
 806            let content_mask = self.content_mask().scale(scale_factor);
 807            let view_id = self.parent_view_id();
 808            let window = &mut *self.window;
 809
 810            window.next_frame.scene.insert(
 811                &window.next_frame.z_index_stack,
 812                PolychromeSprite {
 813                    view_id: view_id.into(),
 814                    layer_id: 0,
 815                    order: 0,
 816                    bounds,
 817                    corner_radii: Default::default(),
 818                    content_mask,
 819                    tile,
 820                    grayscale: false,
 821                },
 822            );
 823        }
 824        Ok(())
 825    }
 826
 827    /// Paint a monochrome SVG into the scene for the next frame at the current stacking context.
 828    pub fn paint_svg(
 829        &mut self,
 830        bounds: Bounds<Pixels>,
 831        path: SharedString,
 832        color: Hsla,
 833    ) -> Result<()> {
 834        let scale_factor = self.scale_factor();
 835        let bounds = bounds.scale(scale_factor);
 836        // Render the SVG at twice the size to get a higher quality result.
 837        let params = RenderSvgParams {
 838            path,
 839            size: bounds
 840                .size
 841                .map(|pixels| DevicePixels::from((pixels.0 * 2.).ceil() as i32)),
 842        };
 843
 844        let tile =
 845            self.window
 846                .sprite_atlas
 847                .get_or_insert_with(&params.clone().into(), &mut || {
 848                    let bytes = self.svg_renderer.render(&params)?;
 849                    Ok((params.size, Cow::Owned(bytes)))
 850                })?;
 851        let content_mask = self.content_mask().scale(scale_factor);
 852        let view_id = self.parent_view_id();
 853
 854        let window = &mut *self.window;
 855        window.next_frame.scene.insert(
 856            &window.next_frame.z_index_stack,
 857            MonochromeSprite {
 858                view_id: view_id.into(),
 859                layer_id: 0,
 860                order: 0,
 861                bounds,
 862                content_mask,
 863                color,
 864                tile,
 865            },
 866        );
 867
 868        Ok(())
 869    }
 870
 871    /// Paint an image into the scene for the next frame at the current z-index.
 872    pub fn paint_image(
 873        &mut self,
 874        bounds: Bounds<Pixels>,
 875        corner_radii: Corners<Pixels>,
 876        data: Arc<ImageData>,
 877        grayscale: bool,
 878    ) -> Result<()> {
 879        let scale_factor = self.scale_factor();
 880        let bounds = bounds.scale(scale_factor);
 881        let params = RenderImageParams { image_id: data.id };
 882
 883        let tile = self
 884            .window
 885            .sprite_atlas
 886            .get_or_insert_with(&params.clone().into(), &mut || {
 887                Ok((data.size(), Cow::Borrowed(data.as_bytes())))
 888            })?;
 889        let content_mask = self.content_mask().scale(scale_factor);
 890        let corner_radii = corner_radii.scale(scale_factor);
 891        let view_id = self.parent_view_id();
 892
 893        let window = &mut *self.window;
 894        window.next_frame.scene.insert(
 895            &window.next_frame.z_index_stack,
 896            PolychromeSprite {
 897                view_id: view_id.into(),
 898                layer_id: 0,
 899                order: 0,
 900                bounds,
 901                content_mask,
 902                corner_radii,
 903                tile,
 904                grayscale,
 905            },
 906        );
 907        Ok(())
 908    }
 909
 910    /// Paint a surface into the scene for the next frame at the current z-index.
 911    pub fn paint_surface(&mut self, bounds: Bounds<Pixels>, image_buffer: CVImageBuffer) {
 912        let scale_factor = self.scale_factor();
 913        let bounds = bounds.scale(scale_factor);
 914        let content_mask = self.content_mask().scale(scale_factor);
 915        let view_id = self.parent_view_id();
 916        let window = &mut *self.window;
 917        window.next_frame.scene.insert(
 918            &window.next_frame.z_index_stack,
 919            Surface {
 920                view_id: view_id.into(),
 921                layer_id: 0,
 922                order: 0,
 923                bounds,
 924                content_mask,
 925                image_buffer,
 926            },
 927        );
 928    }
 929
 930    #[must_use]
 931    /// Add a node to the layout tree for the current frame. Takes the `Style` of the element for which
 932    /// layout is being requested, along with the layout ids of any children. This method is called during
 933    /// calls to the `Element::layout` trait method and enables any element to participate in layout.
 934    pub fn request_layout(
 935        &mut self,
 936        style: &Style,
 937        children: impl IntoIterator<Item = LayoutId>,
 938    ) -> LayoutId {
 939        self.app.layout_id_buffer.clear();
 940        self.app.layout_id_buffer.extend(children);
 941        let rem_size = self.rem_size();
 942
 943        self.cx
 944            .window
 945            .layout_engine
 946            .as_mut()
 947            .unwrap()
 948            .request_layout(style, rem_size, &self.cx.app.layout_id_buffer)
 949    }
 950
 951    /// Add a node to the layout tree for the current frame. Instead of taking a `Style` and children,
 952    /// this variant takes a function that is invoked during layout so you can use arbitrary logic to
 953    /// determine the element's size. One place this is used internally is when measuring text.
 954    ///
 955    /// The given closure is invoked at layout time with the known dimensions and available space and
 956    /// returns a `Size`.
 957    pub fn request_measured_layout<
 958        F: FnMut(Size<Option<Pixels>>, Size<AvailableSpace>, &mut WindowContext) -> Size<Pixels>
 959            + 'static,
 960    >(
 961        &mut self,
 962        style: Style,
 963        measure: F,
 964    ) -> LayoutId {
 965        let rem_size = self.rem_size();
 966        self.window
 967            .layout_engine
 968            .as_mut()
 969            .unwrap()
 970            .request_measured_layout(style, rem_size, measure)
 971    }
 972
 973    /// Compute the layout for the given id within the given available space.
 974    /// This method is called for its side effect, typically by the framework prior to painting.
 975    /// After calling it, you can request the bounds of the given layout node id or any descendant.
 976    pub fn compute_layout(&mut self, layout_id: LayoutId, available_space: Size<AvailableSpace>) {
 977        let mut layout_engine = self.window.layout_engine.take().unwrap();
 978        layout_engine.compute_layout(layout_id, available_space, self);
 979        self.window.layout_engine = Some(layout_engine);
 980    }
 981
 982    /// Obtain the bounds computed for the given LayoutId relative to the window. This method should not
 983    /// be invoked until the paint phase begins, and will usually be invoked by GPUI itself automatically
 984    /// in order to pass your element its `Bounds` automatically.
 985    pub fn layout_bounds(&mut self, layout_id: LayoutId) -> Bounds<Pixels> {
 986        let mut bounds = self
 987            .window
 988            .layout_engine
 989            .as_mut()
 990            .unwrap()
 991            .layout_bounds(layout_id)
 992            .map(Into::into);
 993        bounds.origin += self.element_offset();
 994        bounds
 995    }
 996
 997    pub(crate) fn layout_style(&self, layout_id: LayoutId) -> Option<&Style> {
 998        self.window
 999            .layout_engine
1000            .as_ref()
1001            .unwrap()
1002            .requested_style(layout_id)
1003    }
1004
1005    /// Called during painting to track which z-index is on top at each pixel position
1006    pub fn add_opaque_layer(&mut self, bounds: Bounds<Pixels>) {
1007        let stacking_order = self.window.next_frame.z_index_stack.clone();
1008        let view_id = self.parent_view_id();
1009        let depth_map = &mut self.window.next_frame.depth_map;
1010        match depth_map.binary_search_by(|(level, _, _)| stacking_order.cmp(level)) {
1011            Ok(i) | Err(i) => depth_map.insert(i, (stacking_order, view_id, bounds)),
1012        }
1013    }
1014
1015    /// Invoke the given function with the given focus handle present on the key dispatch stack.
1016    /// If you want an element to participate in key dispatch, use this method to push its key context and focus handle into the stack during paint.
1017    pub fn with_key_dispatch<R>(
1018        &mut self,
1019        context: Option<KeyContext>,
1020        focus_handle: Option<FocusHandle>,
1021        f: impl FnOnce(Option<FocusHandle>, &mut Self) -> R,
1022    ) -> R {
1023        let window = &mut self.window;
1024        let focus_id = focus_handle.as_ref().map(|handle| handle.id);
1025        window
1026            .next_frame
1027            .dispatch_tree
1028            .push_node(context.clone(), focus_id, None);
1029
1030        let result = f(focus_handle, self);
1031
1032        self.window.next_frame.dispatch_tree.pop_node();
1033
1034        result
1035    }
1036
1037    /// Invoke the given function with the given view id present on the view stack.
1038    /// This is a fairly low-level method used to layout views.
1039    pub fn with_view_id<R>(&mut self, view_id: EntityId, f: impl FnOnce(&mut Self) -> R) -> R {
1040        let text_system = self.text_system().clone();
1041        text_system.with_view(view_id, || {
1042            if self.window.next_frame.view_stack.last() == Some(&view_id) {
1043                return f(self);
1044            } else {
1045                self.window.next_frame.view_stack.push(view_id);
1046                let result = f(self);
1047                self.window.next_frame.view_stack.pop();
1048                result
1049            }
1050        })
1051    }
1052
1053    /// Invoke the given function with the given view id present on the view stack.
1054    /// This is a fairly low-level method used to paint views.
1055    pub fn paint_view<R>(&mut self, view_id: EntityId, f: impl FnOnce(&mut Self) -> R) -> R {
1056        let text_system = self.text_system().clone();
1057        text_system.with_view(view_id, || {
1058            if self.window.next_frame.view_stack.last() == Some(&view_id) {
1059                return f(self);
1060            } else {
1061                self.window.next_frame.view_stack.push(view_id);
1062                self.window
1063                    .next_frame
1064                    .dispatch_tree
1065                    .push_node(None, None, Some(view_id));
1066                let result = f(self);
1067                self.window.next_frame.dispatch_tree.pop_node();
1068                self.window.next_frame.view_stack.pop();
1069                result
1070            }
1071        })
1072    }
1073
1074    /// Sets an input handler, such as [`ElementInputHandler`][element_input_handler], which interfaces with the
1075    /// platform to receive textual input with proper integration with concerns such
1076    /// as IME interactions. This handler will be active for the upcoming frame until the following frame is
1077    /// rendered.
1078    ///
1079    /// [element_input_handler]: crate::ElementInputHandler
1080    pub fn handle_input(&mut self, focus_handle: &FocusHandle, input_handler: impl InputHandler) {
1081        if focus_handle.is_focused(self) {
1082            let view_id = self.parent_view_id();
1083            self.window.next_frame.requested_input_handler = Some(RequestedInputHandler {
1084                view_id,
1085                handler: Some(PlatformInputHandler::new(
1086                    self.to_async(),
1087                    Box::new(input_handler),
1088                )),
1089            })
1090        }
1091    }
1092
1093    /// Register a mouse event listener on the window for the next frame. The type of event
1094    /// is determined by the first parameter of the given listener. When the next frame is rendered
1095    /// the listener will be cleared.
1096    pub fn on_mouse_event<Event: MouseEvent>(
1097        &mut self,
1098        mut handler: impl FnMut(&Event, DispatchPhase, &mut ElementContext) + 'static,
1099    ) {
1100        let view_id = self.parent_view_id();
1101        let order = self.window.next_frame.z_index_stack.clone();
1102        self.window
1103            .next_frame
1104            .mouse_listeners
1105            .entry(TypeId::of::<Event>())
1106            .or_default()
1107            .push((
1108                order,
1109                view_id,
1110                Box::new(
1111                    move |event: &dyn Any, phase: DispatchPhase, cx: &mut ElementContext<'_>| {
1112                        handler(event.downcast_ref().unwrap(), phase, cx)
1113                    },
1114                ),
1115            ))
1116    }
1117
1118    /// Register a key event listener on the window for the next frame. The type of event
1119    /// is determined by the first parameter of the given listener. When the next frame is rendered
1120    /// the listener will be cleared.
1121    ///
1122    /// This is a fairly low-level method, so prefer using event handlers on elements unless you have
1123    /// a specific need to register a global listener.
1124    pub fn on_key_event<Event: KeyEvent>(
1125        &mut self,
1126        listener: impl Fn(&Event, DispatchPhase, &mut ElementContext) + 'static,
1127    ) {
1128        self.window.next_frame.dispatch_tree.on_key_event(Rc::new(
1129            move |event: &dyn Any, phase, cx: &mut ElementContext<'_>| {
1130                if let Some(event) = event.downcast_ref::<Event>() {
1131                    listener(event, phase, cx)
1132                }
1133            },
1134        ));
1135    }
1136}