element_cx.rs

   1//! The element context is the main interface for interacting with the frame during a paint.
   2//!
   3//! Elements are hierarchical and with a few exceptions the context accumulates state in a stack
   4//! as it processes all of the elements in the frame. The methods that interact with this stack
   5//! are generally marked with `with_*`, and take a callback to denote the region of code that
   6//! should be executed with that state.
   7//!
   8//! The other main interface is the `paint_*` family of methods, which push basic drawing commands
   9//! to the GPU. Everything in a GPUI app is drawn with these methods.
  10//!
  11//! There are also several internal methods that GPUI uses, such as [`ElementContext::with_element_state`]
  12//! to call the paint and layout methods on elements. These have been included as they're often useful
  13//! for taking manual control of the layouting or painting of specialized elements.
  14
  15use std::{
  16    any::{Any, TypeId},
  17    borrow::{Borrow, BorrowMut, Cow},
  18    cmp, mem,
  19    ops::Range,
  20    rc::Rc,
  21    sync::Arc,
  22};
  23
  24use anyhow::Result;
  25use collections::FxHashMap;
  26use derive_more::{Deref, DerefMut};
  27use futures::{future::Shared, FutureExt};
  28#[cfg(target_os = "macos")]
  29use media::core_video::CVImageBuffer;
  30use smallvec::SmallVec;
  31use util::post_inc;
  32
  33use crate::{
  34    hash, point, prelude::*, px, size, AnyElement, AnyTooltip, AppContext, Asset, AvailableSpace,
  35    Bounds, BoxShadow, ContentMask, Corners, CursorStyle, DevicePixels, DispatchNodeId,
  36    DispatchPhase, DispatchTree, DrawPhase, ElementId, ElementStateBox, EntityId, FocusHandle,
  37    FocusId, FontId, GlobalElementId, GlyphId, Hsla, ImageData, InputHandler, IsZero, KeyContext,
  38    KeyEvent, LayoutId, LineLayoutIndex, ModifiersChangedEvent, MonochromeSprite, MouseEvent,
  39    PaintQuad, Path, Pixels, PlatformInputHandler, Point, PolychromeSprite, Quad,
  40    RenderGlyphParams, RenderImageParams, RenderSvgParams, Scene, Shadow, SharedString, Size,
  41    StrikethroughStyle, Style, Task, TextStyleRefinement, TransformationMatrix, Underline,
  42    UnderlineStyle, Window, WindowContext, SUBPIXEL_VARIANTS,
  43};
  44
  45pub(crate) type AnyMouseListener =
  46    Box<dyn FnMut(&dyn Any, DispatchPhase, &mut ElementContext) + 'static>;
  47
  48#[derive(Clone)]
  49pub(crate) struct CursorStyleRequest {
  50    pub(crate) hitbox_id: HitboxId,
  51    pub(crate) style: CursorStyle,
  52}
  53
  54/// An identifier for a [Hitbox].
  55#[derive(Copy, Clone, Debug, Default, Eq, PartialEq)]
  56pub struct HitboxId(usize);
  57
  58impl HitboxId {
  59    /// Checks if the hitbox with this id is currently hovered.
  60    pub fn is_hovered(&self, cx: &WindowContext) -> bool {
  61        cx.window.mouse_hit_test.0.contains(self)
  62    }
  63}
  64
  65/// A rectangular region that potentially blocks hitboxes inserted prior.
  66/// See [ElementContext::insert_hitbox] for more details.
  67#[derive(Clone, Debug, Deref)]
  68pub struct Hitbox {
  69    /// A unique identifier for the hitbox.
  70    pub id: HitboxId,
  71    /// The bounds of the hitbox.
  72    #[deref]
  73    pub bounds: Bounds<Pixels>,
  74    /// The content mask when the hitbox was inserted.
  75    pub content_mask: ContentMask<Pixels>,
  76    /// Whether the hitbox occludes other hitboxes inserted prior.
  77    pub opaque: bool,
  78}
  79
  80impl Hitbox {
  81    /// Checks if the hitbox is currently hovered.
  82    pub fn is_hovered(&self, cx: &WindowContext) -> bool {
  83        self.id.is_hovered(cx)
  84    }
  85}
  86
  87#[derive(Default, Eq, PartialEq)]
  88pub(crate) struct HitTest(SmallVec<[HitboxId; 8]>);
  89
  90/// An identifier for a tooltip.
  91#[derive(Copy, Clone, Debug, Default, Eq, PartialEq)]
  92pub struct TooltipId(usize);
  93
  94impl TooltipId {
  95    /// Checks if the tooltip is currently hovered.
  96    pub fn is_hovered(&self, cx: &WindowContext) -> bool {
  97        cx.window
  98            .tooltip_bounds
  99            .as_ref()
 100            .map_or(false, |tooltip_bounds| {
 101                tooltip_bounds.id == *self && tooltip_bounds.bounds.contains(&cx.mouse_position())
 102            })
 103    }
 104}
 105
 106pub(crate) struct TooltipBounds {
 107    id: TooltipId,
 108    bounds: Bounds<Pixels>,
 109}
 110
 111#[derive(Clone)]
 112pub(crate) struct TooltipRequest {
 113    id: TooltipId,
 114    tooltip: AnyTooltip,
 115}
 116
 117pub(crate) struct DeferredDraw {
 118    priority: usize,
 119    parent_node: DispatchNodeId,
 120    element_id_stack: GlobalElementId,
 121    text_style_stack: Vec<TextStyleRefinement>,
 122    element: Option<AnyElement>,
 123    absolute_offset: Point<Pixels>,
 124    prepaint_range: Range<PrepaintStateIndex>,
 125    paint_range: Range<PaintIndex>,
 126}
 127
 128pub(crate) struct Frame {
 129    pub(crate) focus: Option<FocusId>,
 130    pub(crate) window_active: bool,
 131    pub(crate) element_states: FxHashMap<(GlobalElementId, TypeId), ElementStateBox>,
 132    accessed_element_states: Vec<(GlobalElementId, TypeId)>,
 133    pub(crate) mouse_listeners: Vec<Option<AnyMouseListener>>,
 134    pub(crate) dispatch_tree: DispatchTree,
 135    pub(crate) scene: Scene,
 136    pub(crate) hitboxes: Vec<Hitbox>,
 137    pub(crate) deferred_draws: Vec<DeferredDraw>,
 138    pub(crate) input_handlers: Vec<Option<PlatformInputHandler>>,
 139    pub(crate) tooltip_requests: Vec<Option<TooltipRequest>>,
 140    pub(crate) cursor_styles: Vec<CursorStyleRequest>,
 141    #[cfg(any(test, feature = "test-support"))]
 142    pub(crate) debug_bounds: FxHashMap<String, Bounds<Pixels>>,
 143}
 144
 145#[derive(Clone, Default)]
 146pub(crate) struct PrepaintStateIndex {
 147    hitboxes_index: usize,
 148    tooltips_index: usize,
 149    deferred_draws_index: usize,
 150    dispatch_tree_index: usize,
 151    accessed_element_states_index: usize,
 152    line_layout_index: LineLayoutIndex,
 153}
 154
 155#[derive(Clone, Default)]
 156pub(crate) struct PaintIndex {
 157    scene_index: usize,
 158    mouse_listeners_index: usize,
 159    input_handlers_index: usize,
 160    cursor_styles_index: usize,
 161    accessed_element_states_index: usize,
 162    line_layout_index: LineLayoutIndex,
 163}
 164
 165impl Frame {
 166    pub(crate) fn new(dispatch_tree: DispatchTree) -> Self {
 167        Frame {
 168            focus: None,
 169            window_active: false,
 170            element_states: FxHashMap::default(),
 171            accessed_element_states: Vec::new(),
 172            mouse_listeners: Vec::new(),
 173            dispatch_tree,
 174            scene: Scene::default(),
 175            hitboxes: Vec::new(),
 176            deferred_draws: Vec::new(),
 177            input_handlers: Vec::new(),
 178            tooltip_requests: Vec::new(),
 179            cursor_styles: Vec::new(),
 180
 181            #[cfg(any(test, feature = "test-support"))]
 182            debug_bounds: FxHashMap::default(),
 183        }
 184    }
 185
 186    pub(crate) fn clear(&mut self) {
 187        self.element_states.clear();
 188        self.accessed_element_states.clear();
 189        self.mouse_listeners.clear();
 190        self.dispatch_tree.clear();
 191        self.scene.clear();
 192        self.input_handlers.clear();
 193        self.tooltip_requests.clear();
 194        self.cursor_styles.clear();
 195        self.hitboxes.clear();
 196        self.deferred_draws.clear();
 197    }
 198
 199    pub(crate) fn hit_test(&self, position: Point<Pixels>) -> HitTest {
 200        let mut hit_test = HitTest::default();
 201        for hitbox in self.hitboxes.iter().rev() {
 202            let bounds = hitbox.bounds.intersect(&hitbox.content_mask.bounds);
 203            if bounds.contains(&position) {
 204                hit_test.0.push(hitbox.id);
 205                if hitbox.opaque {
 206                    break;
 207                }
 208            }
 209        }
 210        hit_test
 211    }
 212
 213    pub(crate) fn focus_path(&self) -> SmallVec<[FocusId; 8]> {
 214        self.focus
 215            .map(|focus_id| self.dispatch_tree.focus_path(focus_id))
 216            .unwrap_or_default()
 217    }
 218
 219    pub(crate) fn finish(&mut self, prev_frame: &mut Self) {
 220        for element_state_key in &self.accessed_element_states {
 221            if let Some(element_state) = prev_frame.element_states.remove(element_state_key) {
 222                self.element_states
 223                    .insert(element_state_key.clone(), element_state);
 224            }
 225        }
 226
 227        self.scene.finish();
 228    }
 229}
 230
 231/// This context is used for assisting in the implementation of the element trait
 232#[derive(Deref, DerefMut)]
 233pub struct ElementContext<'a> {
 234    pub(crate) cx: WindowContext<'a>,
 235}
 236
 237impl<'a> WindowContext<'a> {
 238    /// Convert this window context into an ElementContext in this callback.
 239    /// If you need to use this method, you're probably intermixing the imperative
 240    /// and declarative APIs, which is not recommended.
 241    pub fn with_element_context<R>(&mut self, f: impl FnOnce(&mut ElementContext) -> R) -> R {
 242        f(&mut ElementContext {
 243            cx: WindowContext::new(self.app, self.window),
 244        })
 245    }
 246}
 247
 248impl<'a> Borrow<AppContext> for ElementContext<'a> {
 249    fn borrow(&self) -> &AppContext {
 250        self.cx.app
 251    }
 252}
 253
 254impl<'a> BorrowMut<AppContext> for ElementContext<'a> {
 255    fn borrow_mut(&mut self) -> &mut AppContext {
 256        self.cx.borrow_mut()
 257    }
 258}
 259
 260impl<'a> Borrow<WindowContext<'a>> for ElementContext<'a> {
 261    fn borrow(&self) -> &WindowContext<'a> {
 262        &self.cx
 263    }
 264}
 265
 266impl<'a> BorrowMut<WindowContext<'a>> for ElementContext<'a> {
 267    fn borrow_mut(&mut self) -> &mut WindowContext<'a> {
 268        &mut self.cx
 269    }
 270}
 271
 272impl<'a> Borrow<Window> for ElementContext<'a> {
 273    fn borrow(&self) -> &Window {
 274        self.cx.window
 275    }
 276}
 277
 278impl<'a> BorrowMut<Window> for ElementContext<'a> {
 279    fn borrow_mut(&mut self) -> &mut Window {
 280        self.cx.borrow_mut()
 281    }
 282}
 283
 284impl<'a> Context for ElementContext<'a> {
 285    type Result<T> = <WindowContext<'a> as Context>::Result<T>;
 286
 287    fn new_model<T: 'static>(
 288        &mut self,
 289        build_model: impl FnOnce(&mut crate::ModelContext<'_, T>) -> T,
 290    ) -> Self::Result<crate::Model<T>> {
 291        self.cx.new_model(build_model)
 292    }
 293
 294    fn reserve_model<T: 'static>(&mut self) -> Self::Result<crate::Reservation<T>> {
 295        self.cx.reserve_model()
 296    }
 297
 298    fn insert_model<T: 'static>(
 299        &mut self,
 300        reservation: crate::Reservation<T>,
 301        build_model: impl FnOnce(&mut crate::ModelContext<'_, T>) -> T,
 302    ) -> Self::Result<crate::Model<T>> {
 303        self.cx.insert_model(reservation, build_model)
 304    }
 305
 306    fn update_model<T, R>(
 307        &mut self,
 308        handle: &crate::Model<T>,
 309        update: impl FnOnce(&mut T, &mut crate::ModelContext<'_, T>) -> R,
 310    ) -> Self::Result<R>
 311    where
 312        T: 'static,
 313    {
 314        self.cx.update_model(handle, update)
 315    }
 316
 317    fn read_model<T, R>(
 318        &self,
 319        handle: &crate::Model<T>,
 320        read: impl FnOnce(&T, &AppContext) -> R,
 321    ) -> Self::Result<R>
 322    where
 323        T: 'static,
 324    {
 325        self.cx.read_model(handle, read)
 326    }
 327
 328    fn update_window<T, F>(&mut self, window: crate::AnyWindowHandle, f: F) -> Result<T>
 329    where
 330        F: FnOnce(crate::AnyView, &mut WindowContext<'_>) -> T,
 331    {
 332        self.cx.update_window(window, f)
 333    }
 334
 335    fn read_window<T, R>(
 336        &self,
 337        window: &crate::WindowHandle<T>,
 338        read: impl FnOnce(crate::View<T>, &AppContext) -> R,
 339    ) -> Result<R>
 340    where
 341        T: 'static,
 342    {
 343        self.cx.read_window(window, read)
 344    }
 345}
 346
 347impl<'a> VisualContext for ElementContext<'a> {
 348    fn new_view<V>(
 349        &mut self,
 350        build_view: impl FnOnce(&mut crate::ViewContext<'_, V>) -> V,
 351    ) -> Self::Result<crate::View<V>>
 352    where
 353        V: 'static + Render,
 354    {
 355        self.cx.new_view(build_view)
 356    }
 357
 358    fn update_view<V: 'static, R>(
 359        &mut self,
 360        view: &crate::View<V>,
 361        update: impl FnOnce(&mut V, &mut crate::ViewContext<'_, V>) -> R,
 362    ) -> Self::Result<R> {
 363        self.cx.update_view(view, update)
 364    }
 365
 366    fn replace_root_view<V>(
 367        &mut self,
 368        build_view: impl FnOnce(&mut crate::ViewContext<'_, V>) -> V,
 369    ) -> Self::Result<crate::View<V>>
 370    where
 371        V: 'static + Render,
 372    {
 373        self.cx.replace_root_view(build_view)
 374    }
 375
 376    fn focus_view<V>(&mut self, view: &crate::View<V>) -> Self::Result<()>
 377    where
 378        V: crate::FocusableView,
 379    {
 380        self.cx.focus_view(view)
 381    }
 382
 383    fn dismiss_view<V>(&mut self, view: &crate::View<V>) -> Self::Result<()>
 384    where
 385        V: crate::ManagedView,
 386    {
 387        self.cx.dismiss_view(view)
 388    }
 389}
 390
 391impl<'a> ElementContext<'a> {
 392    pub(crate) fn draw_roots(&mut self) {
 393        self.window.draw_phase = DrawPhase::Layout;
 394        self.window.tooltip_bounds.take();
 395
 396        // Layout all root elements.
 397        let mut root_element = self.window.root_view.as_ref().unwrap().clone().into_any();
 398        root_element.prepaint_as_root(Point::default(), self.window.viewport_size.into(), self);
 399
 400        let mut sorted_deferred_draws =
 401            (0..self.window.next_frame.deferred_draws.len()).collect::<SmallVec<[_; 8]>>();
 402        sorted_deferred_draws.sort_by_key(|ix| self.window.next_frame.deferred_draws[*ix].priority);
 403        self.prepaint_deferred_draws(&sorted_deferred_draws);
 404
 405        let mut prompt_element = None;
 406        let mut active_drag_element = None;
 407        let mut tooltip_element = None;
 408        if let Some(prompt) = self.window.prompt.take() {
 409            let mut element = prompt.view.any_view().into_any();
 410            element.prepaint_as_root(Point::default(), self.window.viewport_size.into(), self);
 411            prompt_element = Some(element);
 412            self.window.prompt = Some(prompt);
 413        } else if let Some(active_drag) = self.app.active_drag.take() {
 414            let mut element = active_drag.view.clone().into_any();
 415            let offset = self.mouse_position() - active_drag.cursor_offset;
 416            element.prepaint_as_root(offset, AvailableSpace::min_size(), self);
 417            active_drag_element = Some(element);
 418            self.app.active_drag = Some(active_drag);
 419        } else {
 420            tooltip_element = self.prepaint_tooltip();
 421        }
 422
 423        self.window.mouse_hit_test = self.window.next_frame.hit_test(self.window.mouse_position);
 424
 425        // Now actually paint the elements.
 426        self.window.draw_phase = DrawPhase::Paint;
 427        root_element.paint(self);
 428
 429        self.paint_deferred_draws(&sorted_deferred_draws);
 430
 431        if let Some(mut prompt_element) = prompt_element {
 432            prompt_element.paint(self)
 433        } else if let Some(mut drag_element) = active_drag_element {
 434            drag_element.paint(self);
 435        } else if let Some(mut tooltip_element) = tooltip_element {
 436            tooltip_element.paint(self);
 437        }
 438    }
 439
 440    fn prepaint_tooltip(&mut self) -> Option<AnyElement> {
 441        let tooltip_request = self.window.next_frame.tooltip_requests.last().cloned()?;
 442        let tooltip_request = tooltip_request.unwrap();
 443        let mut element = tooltip_request.tooltip.view.clone().into_any();
 444        let mouse_position = tooltip_request.tooltip.mouse_position;
 445        let tooltip_size = element.layout_as_root(AvailableSpace::min_size(), self);
 446
 447        let mut tooltip_bounds = Bounds::new(mouse_position + point(px(1.), px(1.)), tooltip_size);
 448        let window_bounds = Bounds {
 449            origin: Point::default(),
 450            size: self.viewport_size(),
 451        };
 452
 453        if tooltip_bounds.right() > window_bounds.right() {
 454            let new_x = mouse_position.x - tooltip_bounds.size.width - px(1.);
 455            if new_x >= Pixels::ZERO {
 456                tooltip_bounds.origin.x = new_x;
 457            } else {
 458                tooltip_bounds.origin.x = cmp::max(
 459                    Pixels::ZERO,
 460                    tooltip_bounds.origin.x - tooltip_bounds.right() - window_bounds.right(),
 461                );
 462            }
 463        }
 464
 465        if tooltip_bounds.bottom() > window_bounds.bottom() {
 466            let new_y = mouse_position.y - tooltip_bounds.size.height - px(1.);
 467            if new_y >= Pixels::ZERO {
 468                tooltip_bounds.origin.y = new_y;
 469            } else {
 470                tooltip_bounds.origin.y = cmp::max(
 471                    Pixels::ZERO,
 472                    tooltip_bounds.origin.y - tooltip_bounds.bottom() - window_bounds.bottom(),
 473                );
 474            }
 475        }
 476
 477        self.with_absolute_element_offset(tooltip_bounds.origin, |cx| element.prepaint(cx));
 478
 479        self.window.tooltip_bounds = Some(TooltipBounds {
 480            id: tooltip_request.id,
 481            bounds: tooltip_bounds,
 482        });
 483        Some(element)
 484    }
 485
 486    fn prepaint_deferred_draws(&mut self, deferred_draw_indices: &[usize]) {
 487        assert_eq!(self.window.element_id_stack.len(), 0);
 488
 489        let mut deferred_draws = mem::take(&mut self.window.next_frame.deferred_draws);
 490        for deferred_draw_ix in deferred_draw_indices {
 491            let deferred_draw = &mut deferred_draws[*deferred_draw_ix];
 492            self.window.element_id_stack = deferred_draw.element_id_stack.clone();
 493            self.window.text_style_stack = deferred_draw.text_style_stack.clone();
 494            self.window
 495                .next_frame
 496                .dispatch_tree
 497                .set_active_node(deferred_draw.parent_node);
 498
 499            let prepaint_start = self.prepaint_index();
 500            if let Some(element) = deferred_draw.element.as_mut() {
 501                self.with_absolute_element_offset(deferred_draw.absolute_offset, |cx| {
 502                    element.prepaint(cx)
 503                });
 504            } else {
 505                self.reuse_prepaint(deferred_draw.prepaint_range.clone());
 506            }
 507            let prepaint_end = self.prepaint_index();
 508            deferred_draw.prepaint_range = prepaint_start..prepaint_end;
 509        }
 510        assert_eq!(
 511            self.window.next_frame.deferred_draws.len(),
 512            0,
 513            "cannot call defer_draw during deferred drawing"
 514        );
 515        self.window.next_frame.deferred_draws = deferred_draws;
 516        self.window.element_id_stack.clear();
 517        self.window.text_style_stack.clear();
 518    }
 519
 520    fn paint_deferred_draws(&mut self, deferred_draw_indices: &[usize]) {
 521        assert_eq!(self.window.element_id_stack.len(), 0);
 522
 523        let mut deferred_draws = mem::take(&mut self.window.next_frame.deferred_draws);
 524        for deferred_draw_ix in deferred_draw_indices {
 525            let mut deferred_draw = &mut deferred_draws[*deferred_draw_ix];
 526            self.window.element_id_stack = deferred_draw.element_id_stack.clone();
 527            self.window
 528                .next_frame
 529                .dispatch_tree
 530                .set_active_node(deferred_draw.parent_node);
 531
 532            let paint_start = self.paint_index();
 533            if let Some(element) = deferred_draw.element.as_mut() {
 534                element.paint(self);
 535            } else {
 536                self.reuse_paint(deferred_draw.paint_range.clone());
 537            }
 538            let paint_end = self.paint_index();
 539            deferred_draw.paint_range = paint_start..paint_end;
 540        }
 541        self.window.next_frame.deferred_draws = deferred_draws;
 542        self.window.element_id_stack.clear();
 543    }
 544
 545    pub(crate) fn prepaint_index(&self) -> PrepaintStateIndex {
 546        PrepaintStateIndex {
 547            hitboxes_index: self.window.next_frame.hitboxes.len(),
 548            tooltips_index: self.window.next_frame.tooltip_requests.len(),
 549            deferred_draws_index: self.window.next_frame.deferred_draws.len(),
 550            dispatch_tree_index: self.window.next_frame.dispatch_tree.len(),
 551            accessed_element_states_index: self.window.next_frame.accessed_element_states.len(),
 552            line_layout_index: self.window.text_system.layout_index(),
 553        }
 554    }
 555
 556    pub(crate) fn reuse_prepaint(&mut self, range: Range<PrepaintStateIndex>) {
 557        let window = &mut self.window;
 558        window.next_frame.hitboxes.extend(
 559            window.rendered_frame.hitboxes[range.start.hitboxes_index..range.end.hitboxes_index]
 560                .iter()
 561                .cloned(),
 562        );
 563        window.next_frame.tooltip_requests.extend(
 564            window.rendered_frame.tooltip_requests
 565                [range.start.tooltips_index..range.end.tooltips_index]
 566                .iter_mut()
 567                .map(|request| request.take()),
 568        );
 569        window.next_frame.accessed_element_states.extend(
 570            window.rendered_frame.accessed_element_states[range.start.accessed_element_states_index
 571                ..range.end.accessed_element_states_index]
 572                .iter()
 573                .cloned(),
 574        );
 575        window
 576            .text_system
 577            .reuse_layouts(range.start.line_layout_index..range.end.line_layout_index);
 578
 579        let reused_subtree = window.next_frame.dispatch_tree.reuse_subtree(
 580            range.start.dispatch_tree_index..range.end.dispatch_tree_index,
 581            &mut window.rendered_frame.dispatch_tree,
 582        );
 583        window.next_frame.deferred_draws.extend(
 584            window.rendered_frame.deferred_draws
 585                [range.start.deferred_draws_index..range.end.deferred_draws_index]
 586                .iter()
 587                .map(|deferred_draw| DeferredDraw {
 588                    parent_node: reused_subtree.refresh_node_id(deferred_draw.parent_node),
 589                    element_id_stack: deferred_draw.element_id_stack.clone(),
 590                    text_style_stack: deferred_draw.text_style_stack.clone(),
 591                    priority: deferred_draw.priority,
 592                    element: None,
 593                    absolute_offset: deferred_draw.absolute_offset,
 594                    prepaint_range: deferred_draw.prepaint_range.clone(),
 595                    paint_range: deferred_draw.paint_range.clone(),
 596                }),
 597        );
 598    }
 599
 600    pub(crate) fn paint_index(&self) -> PaintIndex {
 601        PaintIndex {
 602            scene_index: self.window.next_frame.scene.len(),
 603            mouse_listeners_index: self.window.next_frame.mouse_listeners.len(),
 604            input_handlers_index: self.window.next_frame.input_handlers.len(),
 605            cursor_styles_index: self.window.next_frame.cursor_styles.len(),
 606            accessed_element_states_index: self.window.next_frame.accessed_element_states.len(),
 607            line_layout_index: self.window.text_system.layout_index(),
 608        }
 609    }
 610
 611    pub(crate) fn reuse_paint(&mut self, range: Range<PaintIndex>) {
 612        let window = &mut self.cx.window;
 613
 614        window.next_frame.cursor_styles.extend(
 615            window.rendered_frame.cursor_styles
 616                [range.start.cursor_styles_index..range.end.cursor_styles_index]
 617                .iter()
 618                .cloned(),
 619        );
 620        window.next_frame.input_handlers.extend(
 621            window.rendered_frame.input_handlers
 622                [range.start.input_handlers_index..range.end.input_handlers_index]
 623                .iter_mut()
 624                .map(|handler| handler.take()),
 625        );
 626        window.next_frame.mouse_listeners.extend(
 627            window.rendered_frame.mouse_listeners
 628                [range.start.mouse_listeners_index..range.end.mouse_listeners_index]
 629                .iter_mut()
 630                .map(|listener| listener.take()),
 631        );
 632        window.next_frame.accessed_element_states.extend(
 633            window.rendered_frame.accessed_element_states[range.start.accessed_element_states_index
 634                ..range.end.accessed_element_states_index]
 635                .iter()
 636                .cloned(),
 637        );
 638        window
 639            .text_system
 640            .reuse_layouts(range.start.line_layout_index..range.end.line_layout_index);
 641        window.next_frame.scene.replay(
 642            range.start.scene_index..range.end.scene_index,
 643            &window.rendered_frame.scene,
 644        );
 645    }
 646
 647    /// Push a text style onto the stack, and call a function with that style active.
 648    /// Use [`AppContext::text_style`] to get the current, combined text style.
 649    pub fn with_text_style<F, R>(&mut self, style: Option<TextStyleRefinement>, f: F) -> R
 650    where
 651        F: FnOnce(&mut Self) -> R,
 652    {
 653        if let Some(style) = style {
 654            self.window.text_style_stack.push(style);
 655            let result = f(self);
 656            self.window.text_style_stack.pop();
 657            result
 658        } else {
 659            f(self)
 660        }
 661    }
 662
 663    /// Updates the cursor style at the platform level.
 664    pub fn set_cursor_style(&mut self, style: CursorStyle, hitbox: &Hitbox) {
 665        self.window
 666            .next_frame
 667            .cursor_styles
 668            .push(CursorStyleRequest {
 669                hitbox_id: hitbox.id,
 670                style,
 671            });
 672    }
 673
 674    /// Sets a tooltip to be rendered for the upcoming frame
 675    pub fn set_tooltip(&mut self, tooltip: AnyTooltip) -> TooltipId {
 676        let id = TooltipId(post_inc(&mut self.window.next_tooltip_id.0));
 677        self.window
 678            .next_frame
 679            .tooltip_requests
 680            .push(Some(TooltipRequest { id, tooltip }));
 681        id
 682    }
 683
 684    /// Pushes the given element id onto the global stack and invokes the given closure
 685    /// with a `GlobalElementId`, which disambiguates the given id in the context of its ancestor
 686    /// ids. Because elements are discarded and recreated on each frame, the `GlobalElementId` is
 687    /// used to associate state with identified elements across separate frames.
 688    pub fn with_element_id<R>(
 689        &mut self,
 690        id: Option<impl Into<ElementId>>,
 691        f: impl FnOnce(&mut Self) -> R,
 692    ) -> R {
 693        if let Some(id) = id.map(Into::into) {
 694            let window = self.window_mut();
 695            window.element_id_stack.push(id);
 696            let result = f(self);
 697            let window: &mut Window = self.borrow_mut();
 698            window.element_id_stack.pop();
 699            result
 700        } else {
 701            f(self)
 702        }
 703    }
 704
 705    /// Invoke the given function with the given content mask after intersecting it
 706    /// with the current mask.
 707    pub fn with_content_mask<R>(
 708        &mut self,
 709        mask: Option<ContentMask<Pixels>>,
 710        f: impl FnOnce(&mut Self) -> R,
 711    ) -> R {
 712        if let Some(mask) = mask {
 713            let mask = mask.intersect(&self.content_mask());
 714            self.window_mut().content_mask_stack.push(mask);
 715            let result = f(self);
 716            self.window_mut().content_mask_stack.pop();
 717            result
 718        } else {
 719            f(self)
 720        }
 721    }
 722
 723    /// Updates the global element offset relative to the current offset. This is used to implement
 724    /// scrolling.
 725    pub fn with_element_offset<R>(
 726        &mut self,
 727        offset: Point<Pixels>,
 728        f: impl FnOnce(&mut Self) -> R,
 729    ) -> R {
 730        if offset.is_zero() {
 731            return f(self);
 732        };
 733
 734        let abs_offset = self.element_offset() + offset;
 735        self.with_absolute_element_offset(abs_offset, f)
 736    }
 737
 738    /// Updates the global element offset based on the given offset. This is used to implement
 739    /// drag handles and other manual painting of elements.
 740    pub fn with_absolute_element_offset<R>(
 741        &mut self,
 742        offset: Point<Pixels>,
 743        f: impl FnOnce(&mut Self) -> R,
 744    ) -> R {
 745        self.window_mut().element_offset_stack.push(offset);
 746        let result = f(self);
 747        self.window_mut().element_offset_stack.pop();
 748        result
 749    }
 750
 751    /// Perform prepaint on child elements in a "retryable" manner, so that any side effects
 752    /// of prepaints can be discarded before prepainting again. This is used to support autoscroll
 753    /// where we need to prepaint children to detect the autoscroll bounds, then adjust the
 754    /// element offset and prepaint again. See [`List`] for an example.
 755    pub fn transact<T, U>(&mut self, f: impl FnOnce(&mut Self) -> Result<T, U>) -> Result<T, U> {
 756        let index = self.prepaint_index();
 757        let result = f(self);
 758        if result.is_err() {
 759            self.window
 760                .next_frame
 761                .hitboxes
 762                .truncate(index.hitboxes_index);
 763            self.window
 764                .next_frame
 765                .tooltip_requests
 766                .truncate(index.tooltips_index);
 767            self.window
 768                .next_frame
 769                .deferred_draws
 770                .truncate(index.deferred_draws_index);
 771            self.window
 772                .next_frame
 773                .dispatch_tree
 774                .truncate(index.dispatch_tree_index);
 775            self.window
 776                .next_frame
 777                .accessed_element_states
 778                .truncate(index.accessed_element_states_index);
 779            self.window
 780                .text_system
 781                .truncate_layouts(index.line_layout_index);
 782        }
 783        result
 784    }
 785
 786    /// When you call this method during [`prepaint`], containing elements will attempt to
 787    /// scroll to cause the specified bounds to become visible. When they decide to autoscroll, they will call
 788    /// [`prepaint`] again with a new set of bounds. See [`List`] for an example of an element
 789    /// that supports this method being called on the elements it contains.
 790    pub fn request_autoscroll(&mut self, bounds: Bounds<Pixels>) {
 791        self.window.requested_autoscroll = Some(bounds);
 792    }
 793
 794    /// This method can be called from a containing element such as [`List`] to support the autoscroll behavior
 795    /// described in [`request_autoscroll`].
 796    pub fn take_autoscroll(&mut self) -> Option<Bounds<Pixels>> {
 797        self.window.requested_autoscroll.take()
 798    }
 799
 800    /// Remove an asset from GPUI's cache
 801    pub fn remove_cached_asset<A: Asset + 'static>(
 802        &mut self,
 803        source: &A::Source,
 804    ) -> Option<A::Output> {
 805        self.asset_cache.remove::<A>(source)
 806    }
 807
 808    /// Asynchronously load an asset, if the asset hasn't finished loading this will return None.
 809    /// Your view will be re-drawn once the asset has finished loading.
 810    ///
 811    /// Note that the multiple calls to this method will only result in one `Asset::load` call.
 812    /// The results of that call will be cached, and returned on subsequent uses of this API.
 813    ///
 814    /// Use [Self::remove_cached_asset] to reload your asset.
 815    pub fn use_cached_asset<A: Asset + 'static>(
 816        &mut self,
 817        source: &A::Source,
 818    ) -> Option<A::Output> {
 819        self.asset_cache.get::<A>(source).or_else(|| {
 820            if let Some(asset) = self.use_asset::<A>(source) {
 821                self.asset_cache
 822                    .insert::<A>(source.to_owned(), asset.clone());
 823                Some(asset)
 824            } else {
 825                None
 826            }
 827        })
 828    }
 829
 830    /// Asynchronously load an asset, if the asset hasn't finished loading this will return None.
 831    /// Your view will be re-drawn once the asset has finished loading.
 832    ///
 833    /// Note that the multiple calls to this method will only result in one `Asset::load` call at a
 834    /// time.
 835    ///
 836    /// This asset will not be cached by default, see [Self::use_cached_asset]
 837    pub fn use_asset<A: Asset + 'static>(&mut self, source: &A::Source) -> Option<A::Output> {
 838        let asset_id = (TypeId::of::<A>(), hash(source));
 839        let mut is_first = false;
 840        let task = self
 841            .loading_assets
 842            .remove(&asset_id)
 843            .map(|boxed_task| *boxed_task.downcast::<Shared<Task<A::Output>>>().unwrap())
 844            .unwrap_or_else(|| {
 845                is_first = true;
 846                let future = A::load(source.clone(), self);
 847                let task = self.background_executor().spawn(future).shared();
 848                task
 849            });
 850
 851        task.clone().now_or_never().or_else(|| {
 852            if is_first {
 853                let parent_id = self.parent_view_id();
 854                self.spawn({
 855                    let task = task.clone();
 856                    |mut cx| async move {
 857                        task.await;
 858
 859                        cx.on_next_frame(move |cx| {
 860                            if let Some(parent_id) = parent_id {
 861                                cx.notify(parent_id)
 862                            } else {
 863                                cx.refresh()
 864                            }
 865                        });
 866                    }
 867                })
 868                .detach();
 869            }
 870
 871            self.loading_assets.insert(asset_id, Box::new(task));
 872
 873            None
 874        })
 875    }
 876
 877    /// Obtain the current element offset.
 878    pub fn element_offset(&self) -> Point<Pixels> {
 879        self.window()
 880            .element_offset_stack
 881            .last()
 882            .copied()
 883            .unwrap_or_default()
 884    }
 885
 886    /// Obtain the current content mask.
 887    pub fn content_mask(&self) -> ContentMask<Pixels> {
 888        self.window()
 889            .content_mask_stack
 890            .last()
 891            .cloned()
 892            .unwrap_or_else(|| ContentMask {
 893                bounds: Bounds {
 894                    origin: Point::default(),
 895                    size: self.window().viewport_size,
 896                },
 897            })
 898    }
 899
 900    /// The size of an em for the base font of the application. Adjusting this value allows the
 901    /// UI to scale, just like zooming a web page.
 902    pub fn rem_size(&self) -> Pixels {
 903        self.window().rem_size
 904    }
 905
 906    /// Updates or initializes state for an element with the given id that lives across multiple
 907    /// frames. If an element with this ID existed in the rendered frame, its state will be passed
 908    /// to the given closure. The state returned by the closure will be stored so it can be referenced
 909    /// when drawing the next frame.
 910    pub fn with_element_state<S, R>(
 911        &mut self,
 912        element_id: Option<ElementId>,
 913        f: impl FnOnce(Option<Option<S>>, &mut Self) -> (R, Option<S>),
 914    ) -> R
 915    where
 916        S: 'static,
 917    {
 918        let id_is_none = element_id.is_none();
 919        self.with_element_id(element_id, |cx| {
 920            if id_is_none {
 921                let (result, state) = f(None, cx);
 922                debug_assert!(state.is_none(), "you must not return an element state when passing None for the element id");
 923                result
 924            } else {
 925                let global_id = cx.window().element_id_stack.clone();
 926                let key = (global_id, TypeId::of::<S>());
 927                cx.window.next_frame.accessed_element_states.push(key.clone());
 928
 929                if let Some(any) = cx
 930                    .window_mut()
 931                    .next_frame
 932                    .element_states
 933                    .remove(&key)
 934                    .or_else(|| {
 935                        cx.window_mut()
 936                            .rendered_frame
 937                            .element_states
 938                            .remove(&key)
 939                    })
 940                {
 941                    let ElementStateBox {
 942                        inner,
 943                        #[cfg(debug_assertions)]
 944                        type_name
 945                    } = any;
 946                    // Using the extra inner option to avoid needing to reallocate a new box.
 947                    let mut state_box = inner
 948                        .downcast::<Option<S>>()
 949                        .map_err(|_| {
 950                            #[cfg(debug_assertions)]
 951                            {
 952                                anyhow::anyhow!(
 953                                    "invalid element state type for id, requested_type {:?}, actual type: {:?}",
 954                                    std::any::type_name::<S>(),
 955                                    type_name
 956                                )
 957                            }
 958
 959                            #[cfg(not(debug_assertions))]
 960                            {
 961                                anyhow::anyhow!(
 962                                    "invalid element state type for id, requested_type {:?}",
 963                                    std::any::type_name::<S>(),
 964                                )
 965                            }
 966                        })
 967                        .unwrap();
 968
 969                    // Actual: Option<AnyElement> <- View
 970                    // Requested: () <- AnyElement
 971                    let state = state_box
 972                        .take()
 973                        .expect("reentrant call to with_element_state for the same state type and element id");
 974                    let (result, state) = f(Some(Some(state)), cx);
 975                    state_box.replace(state.expect("you must return "));
 976                    cx.window_mut()
 977                        .next_frame
 978                        .element_states
 979                        .insert(key, ElementStateBox {
 980                            inner: state_box,
 981                            #[cfg(debug_assertions)]
 982                            type_name
 983                        });
 984                    result
 985                } else {
 986                    let (result, state) = f(Some(None), cx);
 987                    cx.window_mut()
 988                        .next_frame
 989                        .element_states
 990                        .insert(key,
 991                            ElementStateBox {
 992                                inner: Box::new(Some(state.expect("you must return Some<State> when you pass some element id"))),
 993                                #[cfg(debug_assertions)]
 994                                type_name: std::any::type_name::<S>()
 995                            }
 996
 997                        );
 998                    result
 999                }
1000            }
1001        })
1002    }
1003
1004    /// Defers the drawing of the given element, scheduling it to be painted on top of the currently-drawn tree
1005    /// at a later time. The `priority` parameter determines the drawing order relative to other deferred elements,
1006    /// with higher values being drawn on top.
1007    pub fn defer_draw(
1008        &mut self,
1009        element: AnyElement,
1010        absolute_offset: Point<Pixels>,
1011        priority: usize,
1012    ) {
1013        let window = &mut self.cx.window;
1014        assert_eq!(
1015            window.draw_phase,
1016            DrawPhase::Layout,
1017            "defer_draw can only be called during request_layout or prepaint"
1018        );
1019        let parent_node = window.next_frame.dispatch_tree.active_node_id().unwrap();
1020        window.next_frame.deferred_draws.push(DeferredDraw {
1021            parent_node,
1022            element_id_stack: window.element_id_stack.clone(),
1023            text_style_stack: window.text_style_stack.clone(),
1024            priority,
1025            element: Some(element),
1026            absolute_offset,
1027            prepaint_range: PrepaintStateIndex::default()..PrepaintStateIndex::default(),
1028            paint_range: PaintIndex::default()..PaintIndex::default(),
1029        });
1030    }
1031
1032    /// Creates a new painting layer for the specified bounds. A "layer" is a batch
1033    /// of geometry that are non-overlapping and have the same draw order. This is typically used
1034    /// for performance reasons.
1035    pub fn paint_layer<R>(&mut self, bounds: Bounds<Pixels>, f: impl FnOnce(&mut Self) -> R) -> R {
1036        let scale_factor = self.scale_factor();
1037        let content_mask = self.content_mask();
1038        let clipped_bounds = bounds.intersect(&content_mask.bounds);
1039        if !clipped_bounds.is_empty() {
1040            self.window
1041                .next_frame
1042                .scene
1043                .push_layer(clipped_bounds.scale(scale_factor));
1044        }
1045
1046        let result = f(self);
1047
1048        if !clipped_bounds.is_empty() {
1049            self.window.next_frame.scene.pop_layer();
1050        }
1051
1052        result
1053    }
1054
1055    /// Paint one or more drop shadows into the scene for the next frame at the current z-index.
1056    pub fn paint_shadows(
1057        &mut self,
1058        bounds: Bounds<Pixels>,
1059        corner_radii: Corners<Pixels>,
1060        shadows: &[BoxShadow],
1061    ) {
1062        let scale_factor = self.scale_factor();
1063        let content_mask = self.content_mask();
1064        for shadow in shadows {
1065            let mut shadow_bounds = bounds;
1066            shadow_bounds.origin += shadow.offset;
1067            shadow_bounds.dilate(shadow.spread_radius);
1068            self.window.next_frame.scene.insert_primitive(Shadow {
1069                order: 0,
1070                blur_radius: shadow.blur_radius.scale(scale_factor),
1071                bounds: shadow_bounds.scale(scale_factor),
1072                content_mask: content_mask.scale(scale_factor),
1073                corner_radii: corner_radii.scale(scale_factor),
1074                color: shadow.color,
1075            });
1076        }
1077    }
1078
1079    /// Paint one or more quads into the scene for the next frame at the current stacking context.
1080    /// Quads are colored rectangular regions with an optional background, border, and corner radius.
1081    /// see [`fill`](crate::fill), [`outline`](crate::outline), and [`quad`](crate::quad) to construct this type.
1082    pub fn paint_quad(&mut self, quad: PaintQuad) {
1083        let scale_factor = self.scale_factor();
1084        let content_mask = self.content_mask();
1085        self.window.next_frame.scene.insert_primitive(Quad {
1086            order: 0,
1087            pad: 0,
1088            bounds: quad.bounds.scale(scale_factor),
1089            content_mask: content_mask.scale(scale_factor),
1090            background: quad.background,
1091            border_color: quad.border_color,
1092            corner_radii: quad.corner_radii.scale(scale_factor),
1093            border_widths: quad.border_widths.scale(scale_factor),
1094        });
1095    }
1096
1097    /// Paint the given `Path` into the scene for the next frame at the current z-index.
1098    pub fn paint_path(&mut self, mut path: Path<Pixels>, color: impl Into<Hsla>) {
1099        let scale_factor = self.scale_factor();
1100        let content_mask = self.content_mask();
1101        path.content_mask = content_mask;
1102        path.color = color.into();
1103        self.window
1104            .next_frame
1105            .scene
1106            .insert_primitive(path.scale(scale_factor));
1107    }
1108
1109    /// Paint an underline into the scene for the next frame at the current z-index.
1110    pub fn paint_underline(
1111        &mut self,
1112        origin: Point<Pixels>,
1113        width: Pixels,
1114        style: &UnderlineStyle,
1115    ) {
1116        let scale_factor = self.scale_factor();
1117        let height = if style.wavy {
1118            style.thickness * 3.
1119        } else {
1120            style.thickness
1121        };
1122        let bounds = Bounds {
1123            origin,
1124            size: size(width, height),
1125        };
1126        let content_mask = self.content_mask();
1127
1128        self.window.next_frame.scene.insert_primitive(Underline {
1129            order: 0,
1130            pad: 0,
1131            bounds: bounds.scale(scale_factor),
1132            content_mask: content_mask.scale(scale_factor),
1133            color: style.color.unwrap_or_default(),
1134            thickness: style.thickness.scale(scale_factor),
1135            wavy: style.wavy,
1136        });
1137    }
1138
1139    /// Paint a strikethrough into the scene for the next frame at the current z-index.
1140    pub fn paint_strikethrough(
1141        &mut self,
1142        origin: Point<Pixels>,
1143        width: Pixels,
1144        style: &StrikethroughStyle,
1145    ) {
1146        let scale_factor = self.scale_factor();
1147        let height = style.thickness;
1148        let bounds = Bounds {
1149            origin,
1150            size: size(width, height),
1151        };
1152        let content_mask = self.content_mask();
1153
1154        self.window.next_frame.scene.insert_primitive(Underline {
1155            order: 0,
1156            pad: 0,
1157            bounds: bounds.scale(scale_factor),
1158            content_mask: content_mask.scale(scale_factor),
1159            thickness: style.thickness.scale(scale_factor),
1160            color: style.color.unwrap_or_default(),
1161            wavy: false,
1162        });
1163    }
1164
1165    /// Paints a monochrome (non-emoji) glyph into the scene for the next frame at the current z-index.
1166    ///
1167    /// The y component of the origin is the baseline of the glyph.
1168    /// You should generally prefer to use the [`ShapedLine::paint`](crate::ShapedLine::paint) or
1169    /// [`WrappedLine::paint`](crate::WrappedLine::paint) methods in the [`TextSystem`](crate::TextSystem).
1170    /// This method is only useful if you need to paint a single glyph that has already been shaped.
1171    pub fn paint_glyph(
1172        &mut self,
1173        origin: Point<Pixels>,
1174        font_id: FontId,
1175        glyph_id: GlyphId,
1176        font_size: Pixels,
1177        color: Hsla,
1178    ) -> Result<()> {
1179        let scale_factor = self.scale_factor();
1180        let glyph_origin = origin.scale(scale_factor);
1181        let subpixel_variant = Point {
1182            x: (glyph_origin.x.0.fract() * SUBPIXEL_VARIANTS as f32).floor() as u8,
1183            y: (glyph_origin.y.0.fract() * SUBPIXEL_VARIANTS as f32).floor() as u8,
1184        };
1185        let params = RenderGlyphParams {
1186            font_id,
1187            glyph_id,
1188            font_size,
1189            subpixel_variant,
1190            scale_factor,
1191            is_emoji: false,
1192        };
1193
1194        let raster_bounds = self.text_system().raster_bounds(&params)?;
1195        if !raster_bounds.is_zero() {
1196            let tile =
1197                self.window
1198                    .sprite_atlas
1199                    .get_or_insert_with(&params.clone().into(), &mut || {
1200                        let (size, bytes) = self.text_system().rasterize_glyph(&params)?;
1201                        Ok((size, Cow::Owned(bytes)))
1202                    })?;
1203            let bounds = Bounds {
1204                origin: glyph_origin.map(|px| px.floor()) + raster_bounds.origin.map(Into::into),
1205                size: tile.bounds.size.map(Into::into),
1206            };
1207            let content_mask = self.content_mask().scale(scale_factor);
1208            self.window
1209                .next_frame
1210                .scene
1211                .insert_primitive(MonochromeSprite {
1212                    order: 0,
1213                    pad: 0,
1214                    bounds,
1215                    content_mask,
1216                    color,
1217                    tile,
1218                    transformation: TransformationMatrix::unit(),
1219                });
1220        }
1221        Ok(())
1222    }
1223
1224    /// Paints an emoji glyph into the scene for the next frame at the current z-index.
1225    ///
1226    /// The y component of the origin is the baseline of the glyph.
1227    /// You should generally prefer to use the [`ShapedLine::paint`](crate::ShapedLine::paint) or
1228    /// [`WrappedLine::paint`](crate::WrappedLine::paint) methods in the [`TextSystem`](crate::TextSystem).
1229    /// This method is only useful if you need to paint a single emoji that has already been shaped.
1230    pub fn paint_emoji(
1231        &mut self,
1232        origin: Point<Pixels>,
1233        font_id: FontId,
1234        glyph_id: GlyphId,
1235        font_size: Pixels,
1236    ) -> Result<()> {
1237        let scale_factor = self.scale_factor();
1238        let glyph_origin = origin.scale(scale_factor);
1239        let params = RenderGlyphParams {
1240            font_id,
1241            glyph_id,
1242            font_size,
1243            // We don't render emojis with subpixel variants.
1244            subpixel_variant: Default::default(),
1245            scale_factor,
1246            is_emoji: true,
1247        };
1248
1249        let raster_bounds = self.text_system().raster_bounds(&params)?;
1250        if !raster_bounds.is_zero() {
1251            let tile =
1252                self.window
1253                    .sprite_atlas
1254                    .get_or_insert_with(&params.clone().into(), &mut || {
1255                        let (size, bytes) = self.text_system().rasterize_glyph(&params)?;
1256                        Ok((size, Cow::Owned(bytes)))
1257                    })?;
1258            let bounds = Bounds {
1259                origin: glyph_origin.map(|px| px.floor()) + raster_bounds.origin.map(Into::into),
1260                size: tile.bounds.size.map(Into::into),
1261            };
1262            let content_mask = self.content_mask().scale(scale_factor);
1263
1264            self.window
1265                .next_frame
1266                .scene
1267                .insert_primitive(PolychromeSprite {
1268                    order: 0,
1269                    grayscale: false,
1270                    bounds,
1271                    corner_radii: Default::default(),
1272                    content_mask,
1273                    tile,
1274                });
1275        }
1276        Ok(())
1277    }
1278
1279    /// Paint a monochrome SVG into the scene for the next frame at the current stacking context.
1280    pub fn paint_svg(
1281        &mut self,
1282        bounds: Bounds<Pixels>,
1283        path: SharedString,
1284        transformation: TransformationMatrix,
1285        color: Hsla,
1286    ) -> Result<()> {
1287        let scale_factor = self.scale_factor();
1288        let bounds = bounds.scale(scale_factor);
1289        // Render the SVG at twice the size to get a higher quality result.
1290        let params = RenderSvgParams {
1291            path,
1292            size: bounds
1293                .size
1294                .map(|pixels| DevicePixels::from((pixels.0 * 2.).ceil() as i32)),
1295        };
1296
1297        let tile =
1298            self.window
1299                .sprite_atlas
1300                .get_or_insert_with(&params.clone().into(), &mut || {
1301                    let bytes = self.svg_renderer.render(&params)?;
1302                    Ok((params.size, Cow::Owned(bytes)))
1303                })?;
1304        let content_mask = self.content_mask().scale(scale_factor);
1305
1306        self.window
1307            .next_frame
1308            .scene
1309            .insert_primitive(MonochromeSprite {
1310                order: 0,
1311                pad: 0,
1312                bounds,
1313                content_mask,
1314                color,
1315                tile,
1316                transformation,
1317            });
1318
1319        Ok(())
1320    }
1321
1322    /// Paint an image into the scene for the next frame at the current z-index.
1323    pub fn paint_image(
1324        &mut self,
1325        bounds: Bounds<Pixels>,
1326        corner_radii: Corners<Pixels>,
1327        data: Arc<ImageData>,
1328        grayscale: bool,
1329    ) -> Result<()> {
1330        let scale_factor = self.scale_factor();
1331        let bounds = bounds.scale(scale_factor);
1332        let params = RenderImageParams { image_id: data.id };
1333
1334        let tile = self
1335            .window
1336            .sprite_atlas
1337            .get_or_insert_with(&params.clone().into(), &mut || {
1338                Ok((data.size(), Cow::Borrowed(data.as_bytes())))
1339            })?;
1340        let content_mask = self.content_mask().scale(scale_factor);
1341        let corner_radii = corner_radii.scale(scale_factor);
1342
1343        self.window
1344            .next_frame
1345            .scene
1346            .insert_primitive(PolychromeSprite {
1347                order: 0,
1348                grayscale,
1349                bounds,
1350                content_mask,
1351                corner_radii,
1352                tile,
1353            });
1354        Ok(())
1355    }
1356
1357    /// Paint a surface into the scene for the next frame at the current z-index.
1358    #[cfg(target_os = "macos")]
1359    pub fn paint_surface(&mut self, bounds: Bounds<Pixels>, image_buffer: CVImageBuffer) {
1360        let scale_factor = self.scale_factor();
1361        let bounds = bounds.scale(scale_factor);
1362        let content_mask = self.content_mask().scale(scale_factor);
1363        self.window
1364            .next_frame
1365            .scene
1366            .insert_primitive(crate::Surface {
1367                order: 0,
1368                bounds,
1369                content_mask,
1370                image_buffer,
1371            });
1372    }
1373
1374    #[must_use]
1375    /// Add a node to the layout tree for the current frame. Takes the `Style` of the element for which
1376    /// layout is being requested, along with the layout ids of any children. This method is called during
1377    /// calls to the `Element::layout` trait method and enables any element to participate in layout.
1378    pub fn request_layout(
1379        &mut self,
1380        style: &Style,
1381        children: impl IntoIterator<Item = LayoutId>,
1382    ) -> LayoutId {
1383        self.app.layout_id_buffer.clear();
1384        self.app.layout_id_buffer.extend(children);
1385        let rem_size = self.rem_size();
1386
1387        self.cx
1388            .window
1389            .layout_engine
1390            .as_mut()
1391            .unwrap()
1392            .request_layout(style, rem_size, &self.cx.app.layout_id_buffer)
1393    }
1394
1395    /// Add a node to the layout tree for the current frame. Instead of taking a `Style` and children,
1396    /// this variant takes a function that is invoked during layout so you can use arbitrary logic to
1397    /// determine the element's size. One place this is used internally is when measuring text.
1398    ///
1399    /// The given closure is invoked at layout time with the known dimensions and available space and
1400    /// returns a `Size`.
1401    pub fn request_measured_layout<
1402        F: FnMut(Size<Option<Pixels>>, Size<AvailableSpace>, &mut WindowContext) -> Size<Pixels>
1403            + 'static,
1404    >(
1405        &mut self,
1406        style: Style,
1407        measure: F,
1408    ) -> LayoutId {
1409        let rem_size = self.rem_size();
1410        self.window
1411            .layout_engine
1412            .as_mut()
1413            .unwrap()
1414            .request_measured_layout(style, rem_size, measure)
1415    }
1416
1417    /// Compute the layout for the given id within the given available space.
1418    /// This method is called for its side effect, typically by the framework prior to painting.
1419    /// After calling it, you can request the bounds of the given layout node id or any descendant.
1420    pub fn compute_layout(&mut self, layout_id: LayoutId, available_space: Size<AvailableSpace>) {
1421        let mut layout_engine = self.window.layout_engine.take().unwrap();
1422        layout_engine.compute_layout(layout_id, available_space, self);
1423        self.window.layout_engine = Some(layout_engine);
1424    }
1425
1426    /// Obtain the bounds computed for the given LayoutId relative to the window. This method will usually be invoked by
1427    /// GPUI itself automatically in order to pass your element its `Bounds` automatically.
1428    pub fn layout_bounds(&mut self, layout_id: LayoutId) -> Bounds<Pixels> {
1429        let mut bounds = self
1430            .window
1431            .layout_engine
1432            .as_mut()
1433            .unwrap()
1434            .layout_bounds(layout_id)
1435            .map(Into::into);
1436        bounds.origin += self.element_offset();
1437        bounds
1438    }
1439
1440    /// This method should be called during `prepaint`. You can use
1441    /// the returned [Hitbox] during `paint` or in an event handler
1442    /// to determine whether the inserted hitbox was the topmost.
1443    pub fn insert_hitbox(&mut self, bounds: Bounds<Pixels>, opaque: bool) -> Hitbox {
1444        let content_mask = self.content_mask();
1445        let window = &mut self.window;
1446        let id = window.next_hitbox_id;
1447        window.next_hitbox_id.0 += 1;
1448        let hitbox = Hitbox {
1449            id,
1450            bounds,
1451            content_mask,
1452            opaque,
1453        };
1454        window.next_frame.hitboxes.push(hitbox.clone());
1455        hitbox
1456    }
1457
1458    /// Sets the key context for the current element. This context will be used to translate
1459    /// keybindings into actions.
1460    pub fn set_key_context(&mut self, context: KeyContext) {
1461        self.window
1462            .next_frame
1463            .dispatch_tree
1464            .set_key_context(context);
1465    }
1466
1467    /// Sets the focus handle for the current element. This handle will be used to manage focus state
1468    /// and keyboard event dispatch for the element.
1469    pub fn set_focus_handle(&mut self, focus_handle: &FocusHandle) {
1470        self.window
1471            .next_frame
1472            .dispatch_tree
1473            .set_focus_id(focus_handle.id);
1474    }
1475
1476    /// Sets the view id for the current element, which will be used to manage view caching.
1477    pub fn set_view_id(&mut self, view_id: EntityId) {
1478        self.window.next_frame.dispatch_tree.set_view_id(view_id);
1479    }
1480
1481    /// Get the last view id for the current element
1482    pub fn parent_view_id(&mut self) -> Option<EntityId> {
1483        self.window.next_frame.dispatch_tree.parent_view_id()
1484    }
1485
1486    /// Sets an input handler, such as [`ElementInputHandler`][element_input_handler], which interfaces with the
1487    /// platform to receive textual input with proper integration with concerns such
1488    /// as IME interactions. This handler will be active for the upcoming frame until the following frame is
1489    /// rendered.
1490    ///
1491    /// [element_input_handler]: crate::ElementInputHandler
1492    pub fn handle_input(&mut self, focus_handle: &FocusHandle, input_handler: impl InputHandler) {
1493        if focus_handle.is_focused(self) {
1494            let cx = self.to_async();
1495            self.window
1496                .next_frame
1497                .input_handlers
1498                .push(Some(PlatformInputHandler::new(cx, Box::new(input_handler))));
1499        }
1500    }
1501
1502    /// Register a mouse event listener on the window for the next frame. The type of event
1503    /// is determined by the first parameter of the given listener. When the next frame is rendered
1504    /// the listener will be cleared.
1505    pub fn on_mouse_event<Event: MouseEvent>(
1506        &mut self,
1507        mut handler: impl FnMut(&Event, DispatchPhase, &mut ElementContext) + 'static,
1508    ) {
1509        self.window.next_frame.mouse_listeners.push(Some(Box::new(
1510            move |event: &dyn Any, phase: DispatchPhase, cx: &mut ElementContext<'_>| {
1511                if let Some(event) = event.downcast_ref() {
1512                    handler(event, phase, cx)
1513                }
1514            },
1515        )));
1516    }
1517
1518    /// Register a key event listener on the window for the next frame. The type of event
1519    /// is determined by the first parameter of the given listener. When the next frame is rendered
1520    /// the listener will be cleared.
1521    ///
1522    /// This is a fairly low-level method, so prefer using event handlers on elements unless you have
1523    /// a specific need to register a global listener.
1524    pub fn on_key_event<Event: KeyEvent>(
1525        &mut self,
1526        listener: impl Fn(&Event, DispatchPhase, &mut ElementContext) + 'static,
1527    ) {
1528        self.window.next_frame.dispatch_tree.on_key_event(Rc::new(
1529            move |event: &dyn Any, phase, cx: &mut ElementContext<'_>| {
1530                if let Some(event) = event.downcast_ref::<Event>() {
1531                    listener(event, phase, cx)
1532                }
1533            },
1534        ));
1535    }
1536
1537    /// Register a modifiers changed event listener on the window for the next frame.
1538    ///
1539    /// This is a fairly low-level method, so prefer using event handlers on elements unless you have
1540    /// a specific need to register a global listener.
1541    pub fn on_modifiers_changed(
1542        &mut self,
1543        listener: impl Fn(&ModifiersChangedEvent, &mut ElementContext) + 'static,
1544    ) {
1545        self.window
1546            .next_frame
1547            .dispatch_tree
1548            .on_modifiers_changed(Rc::new(
1549                move |event: &ModifiersChangedEvent, cx: &mut ElementContext<'_>| {
1550                    listener(event, cx)
1551                },
1552            ));
1553    }
1554}