app.rs

   1pub mod action;
   2
   3use crate::{
   4    elements::ElementBox,
   5    executor::{self, Task},
   6    keymap::{self, Binding, Keystroke},
   7    platform::{self, CursorStyle, Platform, PromptLevel, WindowOptions},
   8    presenter::Presenter,
   9    util::post_inc,
  10    AssetCache, AssetSource, ClipboardItem, FontCache, PathPromptOptions, TextLayoutCache,
  11};
  12pub use action::*;
  13use anyhow::{anyhow, Context, Result};
  14use collections::btree_map;
  15use keymap::MatchResult;
  16use lazy_static::lazy_static;
  17use parking_lot::Mutex;
  18use platform::Event;
  19use postage::oneshot;
  20use smallvec::SmallVec;
  21use smol::prelude::*;
  22use std::{
  23    any::{type_name, Any, TypeId},
  24    cell::RefCell,
  25    collections::{hash_map::Entry, BTreeMap, HashMap, HashSet, VecDeque},
  26    fmt::{self, Debug},
  27    hash::{Hash, Hasher},
  28    marker::PhantomData,
  29    mem,
  30    ops::{Deref, DerefMut},
  31    path::{Path, PathBuf},
  32    pin::Pin,
  33    rc::{self, Rc},
  34    sync::{
  35        atomic::{AtomicUsize, Ordering::SeqCst},
  36        Arc, Weak,
  37    },
  38    time::Duration,
  39};
  40
  41pub trait Entity: 'static {
  42    type Event;
  43
  44    fn release(&mut self, _: &mut MutableAppContext) {}
  45    fn app_will_quit(
  46        &mut self,
  47        _: &mut MutableAppContext,
  48    ) -> Option<Pin<Box<dyn 'static + Future<Output = ()>>>> {
  49        None
  50    }
  51}
  52
  53pub trait View: Entity + Sized {
  54    fn ui_name() -> &'static str;
  55    fn render(&mut self, cx: &mut RenderContext<'_, Self>) -> ElementBox;
  56    fn on_focus(&mut self, _: &mut ViewContext<Self>) {}
  57    fn on_blur(&mut self, _: &mut ViewContext<Self>) {}
  58    fn keymap_context(&self, _: &AppContext) -> keymap::Context {
  59        Self::default_keymap_context()
  60    }
  61    fn default_keymap_context() -> keymap::Context {
  62        let mut cx = keymap::Context::default();
  63        cx.set.insert(Self::ui_name().into());
  64        cx
  65    }
  66    fn debug_json(&self, _: &AppContext) -> serde_json::Value {
  67        serde_json::Value::Null
  68    }
  69}
  70
  71pub trait ReadModel {
  72    fn read_model<T: Entity>(&self, handle: &ModelHandle<T>) -> &T;
  73}
  74
  75pub trait ReadModelWith {
  76    fn read_model_with<E: Entity, T>(
  77        &self,
  78        handle: &ModelHandle<E>,
  79        read: &mut dyn FnMut(&E, &AppContext) -> T,
  80    ) -> T;
  81}
  82
  83pub trait UpdateModel {
  84    fn update_model<T: Entity, O>(
  85        &mut self,
  86        handle: &ModelHandle<T>,
  87        update: &mut dyn FnMut(&mut T, &mut ModelContext<T>) -> O,
  88    ) -> O;
  89}
  90
  91pub trait UpgradeModelHandle {
  92    fn upgrade_model_handle<T: Entity>(
  93        &self,
  94        handle: &WeakModelHandle<T>,
  95    ) -> Option<ModelHandle<T>>;
  96
  97    fn model_handle_is_upgradable<T: Entity>(&self, handle: &WeakModelHandle<T>) -> bool;
  98
  99    fn upgrade_any_model_handle(&self, handle: &AnyWeakModelHandle) -> Option<AnyModelHandle>;
 100}
 101
 102pub trait UpgradeViewHandle {
 103    fn upgrade_view_handle<T: View>(&self, handle: &WeakViewHandle<T>) -> Option<ViewHandle<T>>;
 104
 105    fn upgrade_any_view_handle(&self, handle: &AnyWeakViewHandle) -> Option<AnyViewHandle>;
 106}
 107
 108pub trait ReadView {
 109    fn read_view<T: View>(&self, handle: &ViewHandle<T>) -> &T;
 110}
 111
 112pub trait ReadViewWith {
 113    fn read_view_with<V, T>(
 114        &self,
 115        handle: &ViewHandle<V>,
 116        read: &mut dyn FnMut(&V, &AppContext) -> T,
 117    ) -> T
 118    where
 119        V: View;
 120}
 121
 122pub trait UpdateView {
 123    fn update_view<T, S>(
 124        &mut self,
 125        handle: &ViewHandle<T>,
 126        update: &mut dyn FnMut(&mut T, &mut ViewContext<T>) -> S,
 127    ) -> S
 128    where
 129        T: View;
 130}
 131
 132pub trait ElementStateContext: DerefMut<Target = MutableAppContext> {
 133    fn current_view_id(&self) -> usize;
 134
 135    fn element_state<Tag: 'static, T: 'static + Default>(
 136        &mut self,
 137        element_id: usize,
 138    ) -> ElementStateHandle<T> {
 139        let id = ElementStateId {
 140            view_id: self.current_view_id(),
 141            element_id,
 142            tag: TypeId::of::<Tag>(),
 143        };
 144        self.cx
 145            .element_states
 146            .entry(id)
 147            .or_insert_with(|| Box::new(T::default()));
 148        ElementStateHandle::new(id, self.frame_count, &self.cx.ref_counts)
 149    }
 150}
 151
 152pub struct Menu<'a> {
 153    pub name: &'a str,
 154    pub items: Vec<MenuItem<'a>>,
 155}
 156
 157pub enum MenuItem<'a> {
 158    Action {
 159        name: &'a str,
 160        keystroke: Option<&'a str>,
 161        action: Box<dyn Action>,
 162    },
 163    Separator,
 164}
 165
 166#[derive(Clone)]
 167pub struct App(Rc<RefCell<MutableAppContext>>);
 168
 169#[derive(Clone)]
 170pub struct AsyncAppContext(Rc<RefCell<MutableAppContext>>);
 171
 172#[cfg(any(test, feature = "test-support"))]
 173pub struct TestAppContext {
 174    cx: Rc<RefCell<MutableAppContext>>,
 175    foreground_platform: Rc<platform::test::ForegroundPlatform>,
 176}
 177
 178impl App {
 179    pub fn new(asset_source: impl AssetSource) -> Result<Self> {
 180        let platform = platform::current::platform();
 181        let foreground_platform = platform::current::foreground_platform();
 182        let foreground = Rc::new(executor::Foreground::platform(platform.dispatcher())?);
 183        let app = Self(Rc::new(RefCell::new(MutableAppContext::new(
 184            foreground,
 185            Arc::new(executor::Background::new()),
 186            platform.clone(),
 187            foreground_platform.clone(),
 188            Arc::new(FontCache::new(platform.fonts())),
 189            Default::default(),
 190            asset_source,
 191        ))));
 192
 193        foreground_platform.on_quit(Box::new({
 194            let cx = app.0.clone();
 195            move || {
 196                cx.borrow_mut().quit();
 197            }
 198        }));
 199        foreground_platform.on_menu_command(Box::new({
 200            let cx = app.0.clone();
 201            move |action| {
 202                let mut cx = cx.borrow_mut();
 203                if let Some(key_window_id) = cx.cx.platform.key_window_id() {
 204                    if let Some((presenter, _)) =
 205                        cx.presenters_and_platform_windows.get(&key_window_id)
 206                    {
 207                        let presenter = presenter.clone();
 208                        let path = presenter.borrow().dispatch_path(cx.as_ref());
 209                        cx.dispatch_action_any(key_window_id, &path, action);
 210                    } else {
 211                        cx.dispatch_global_action_any(action);
 212                    }
 213                } else {
 214                    cx.dispatch_global_action_any(action);
 215                }
 216            }
 217        }));
 218
 219        app.0.borrow_mut().weak_self = Some(Rc::downgrade(&app.0));
 220        Ok(app)
 221    }
 222
 223    pub fn background(&self) -> Arc<executor::Background> {
 224        self.0.borrow().background().clone()
 225    }
 226
 227    pub fn on_become_active<F>(self, mut callback: F) -> Self
 228    where
 229        F: 'static + FnMut(&mut MutableAppContext),
 230    {
 231        let cx = self.0.clone();
 232        self.0
 233            .borrow_mut()
 234            .foreground_platform
 235            .on_become_active(Box::new(move || callback(&mut *cx.borrow_mut())));
 236        self
 237    }
 238
 239    pub fn on_resign_active<F>(self, mut callback: F) -> Self
 240    where
 241        F: 'static + FnMut(&mut MutableAppContext),
 242    {
 243        let cx = self.0.clone();
 244        self.0
 245            .borrow_mut()
 246            .foreground_platform
 247            .on_resign_active(Box::new(move || callback(&mut *cx.borrow_mut())));
 248        self
 249    }
 250
 251    pub fn on_quit<F>(&mut self, mut callback: F) -> &mut Self
 252    where
 253        F: 'static + FnMut(&mut MutableAppContext),
 254    {
 255        let cx = self.0.clone();
 256        self.0
 257            .borrow_mut()
 258            .foreground_platform
 259            .on_quit(Box::new(move || callback(&mut *cx.borrow_mut())));
 260        self
 261    }
 262
 263    pub fn on_event<F>(&mut self, mut callback: F) -> &mut Self
 264    where
 265        F: 'static + FnMut(Event, &mut MutableAppContext) -> bool,
 266    {
 267        let cx = self.0.clone();
 268        self.0
 269            .borrow_mut()
 270            .foreground_platform
 271            .on_event(Box::new(move |event| {
 272                callback(event, &mut *cx.borrow_mut())
 273            }));
 274        self
 275    }
 276
 277    pub fn on_open_urls<F>(&mut self, mut callback: F) -> &mut Self
 278    where
 279        F: 'static + FnMut(Vec<String>, &mut MutableAppContext),
 280    {
 281        let cx = self.0.clone();
 282        self.0
 283            .borrow_mut()
 284            .foreground_platform
 285            .on_open_urls(Box::new(move |paths| {
 286                callback(paths, &mut *cx.borrow_mut())
 287            }));
 288        self
 289    }
 290
 291    pub fn run<F>(self, on_finish_launching: F)
 292    where
 293        F: 'static + FnOnce(&mut MutableAppContext),
 294    {
 295        let platform = self.0.borrow().foreground_platform.clone();
 296        platform.run(Box::new(move || {
 297            let mut cx = self.0.borrow_mut();
 298            let cx = &mut *cx;
 299            crate::views::init(cx);
 300            on_finish_launching(cx);
 301        }))
 302    }
 303
 304    pub fn platform(&self) -> Arc<dyn Platform> {
 305        self.0.borrow().platform()
 306    }
 307
 308    pub fn font_cache(&self) -> Arc<FontCache> {
 309        self.0.borrow().cx.font_cache.clone()
 310    }
 311
 312    fn update<T, F: FnOnce(&mut MutableAppContext) -> T>(&mut self, callback: F) -> T {
 313        let mut state = self.0.borrow_mut();
 314        let result = state.update(callback);
 315        state.pending_notifications.clear();
 316        result
 317    }
 318}
 319
 320#[cfg(any(test, feature = "test-support"))]
 321impl TestAppContext {
 322    pub fn new(
 323        foreground_platform: Rc<platform::test::ForegroundPlatform>,
 324        platform: Arc<dyn Platform>,
 325        foreground: Rc<executor::Foreground>,
 326        background: Arc<executor::Background>,
 327        font_cache: Arc<FontCache>,
 328        leak_detector: Arc<Mutex<LeakDetector>>,
 329        first_entity_id: usize,
 330    ) -> Self {
 331        let mut cx = MutableAppContext::new(
 332            foreground.clone(),
 333            background,
 334            platform,
 335            foreground_platform.clone(),
 336            font_cache,
 337            RefCounts {
 338                #[cfg(any(test, feature = "test-support"))]
 339                leak_detector,
 340                ..Default::default()
 341            },
 342            (),
 343        );
 344        cx.next_entity_id = first_entity_id;
 345        let cx = TestAppContext {
 346            cx: Rc::new(RefCell::new(cx)),
 347            foreground_platform,
 348        };
 349        cx.cx.borrow_mut().weak_self = Some(Rc::downgrade(&cx.cx));
 350        cx
 351    }
 352
 353    pub fn dispatch_action<A: Action>(&self, window_id: usize, action: A) {
 354        let mut cx = self.cx.borrow_mut();
 355        let dispatch_path = cx
 356            .presenters_and_platform_windows
 357            .get(&window_id)
 358            .unwrap()
 359            .0
 360            .borrow()
 361            .dispatch_path(cx.as_ref());
 362
 363        cx.dispatch_action_any(window_id, &dispatch_path, &action);
 364    }
 365
 366    pub fn dispatch_global_action<A: Action>(&self, action: A) {
 367        self.cx.borrow_mut().dispatch_global_action(action);
 368    }
 369
 370    pub fn dispatch_keystroke(
 371        &mut self,
 372        window_id: usize,
 373        keystroke: Keystroke,
 374        input: Option<String>,
 375        is_held: bool,
 376    ) {
 377        self.cx.borrow_mut().update(|cx| {
 378            let presenter = cx
 379                .presenters_and_platform_windows
 380                .get(&window_id)
 381                .unwrap()
 382                .0
 383                .clone();
 384            let dispatch_path = presenter.borrow().dispatch_path(cx.as_ref());
 385
 386            if !cx.dispatch_keystroke(window_id, dispatch_path, &keystroke) {
 387                presenter.borrow_mut().dispatch_event(
 388                    Event::KeyDown {
 389                        keystroke,
 390                        input,
 391                        is_held,
 392                    },
 393                    cx,
 394                );
 395            }
 396        });
 397    }
 398
 399    pub fn add_model<T, F>(&mut self, build_model: F) -> ModelHandle<T>
 400    where
 401        T: Entity,
 402        F: FnOnce(&mut ModelContext<T>) -> T,
 403    {
 404        self.cx.borrow_mut().add_model(build_model)
 405    }
 406
 407    pub fn add_window<T, F>(&mut self, build_root_view: F) -> (usize, ViewHandle<T>)
 408    where
 409        T: View,
 410        F: FnOnce(&mut ViewContext<T>) -> T,
 411    {
 412        self.cx
 413            .borrow_mut()
 414            .add_window(Default::default(), build_root_view)
 415    }
 416
 417    pub fn window_ids(&self) -> Vec<usize> {
 418        self.cx.borrow().window_ids().collect()
 419    }
 420
 421    pub fn root_view<T: View>(&self, window_id: usize) -> Option<ViewHandle<T>> {
 422        self.cx.borrow().root_view(window_id)
 423    }
 424
 425    pub fn add_view<T, F>(&mut self, window_id: usize, build_view: F) -> ViewHandle<T>
 426    where
 427        T: View,
 428        F: FnOnce(&mut ViewContext<T>) -> T,
 429    {
 430        self.cx.borrow_mut().add_view(window_id, build_view)
 431    }
 432
 433    pub fn add_option_view<T, F>(
 434        &mut self,
 435        window_id: usize,
 436        build_view: F,
 437    ) -> Option<ViewHandle<T>>
 438    where
 439        T: View,
 440        F: FnOnce(&mut ViewContext<T>) -> Option<T>,
 441    {
 442        self.cx.borrow_mut().add_option_view(window_id, build_view)
 443    }
 444
 445    pub fn read<T, F: FnOnce(&AppContext) -> T>(&self, callback: F) -> T {
 446        callback(self.cx.borrow().as_ref())
 447    }
 448
 449    pub fn update<T, F: FnOnce(&mut MutableAppContext) -> T>(&mut self, callback: F) -> T {
 450        let mut state = self.cx.borrow_mut();
 451        // Don't increment pending flushes in order for effects to be flushed before the callback
 452        // completes, which is helpful in tests.
 453        let result = callback(&mut *state);
 454        // Flush effects after the callback just in case there are any. This can happen in edge
 455        // cases such as the closure dropping handles.
 456        state.flush_effects();
 457        result
 458    }
 459
 460    pub fn to_async(&self) -> AsyncAppContext {
 461        AsyncAppContext(self.cx.clone())
 462    }
 463
 464    pub fn font_cache(&self) -> Arc<FontCache> {
 465        self.cx.borrow().cx.font_cache.clone()
 466    }
 467
 468    pub fn foreground_platform(&self) -> Rc<platform::test::ForegroundPlatform> {
 469        self.foreground_platform.clone()
 470    }
 471
 472    pub fn platform(&self) -> Arc<dyn platform::Platform> {
 473        self.cx.borrow().cx.platform.clone()
 474    }
 475
 476    pub fn foreground(&self) -> Rc<executor::Foreground> {
 477        self.cx.borrow().foreground().clone()
 478    }
 479
 480    pub fn background(&self) -> Arc<executor::Background> {
 481        self.cx.borrow().background().clone()
 482    }
 483
 484    pub fn spawn<F, Fut, T>(&self, f: F) -> Task<T>
 485    where
 486        F: FnOnce(AsyncAppContext) -> Fut,
 487        Fut: 'static + Future<Output = T>,
 488        T: 'static,
 489    {
 490        self.cx.borrow_mut().spawn(f)
 491    }
 492
 493    pub fn simulate_new_path_selection(&self, result: impl FnOnce(PathBuf) -> Option<PathBuf>) {
 494        self.foreground_platform.simulate_new_path_selection(result);
 495    }
 496
 497    pub fn did_prompt_for_new_path(&self) -> bool {
 498        self.foreground_platform.as_ref().did_prompt_for_new_path()
 499    }
 500
 501    pub fn simulate_prompt_answer(&self, window_id: usize, answer: usize) {
 502        use postage::prelude::Sink as _;
 503
 504        let mut state = self.cx.borrow_mut();
 505        let (_, window) = state
 506            .presenters_and_platform_windows
 507            .get_mut(&window_id)
 508            .unwrap();
 509        let test_window = window
 510            .as_any_mut()
 511            .downcast_mut::<platform::test::Window>()
 512            .unwrap();
 513        let mut done_tx = test_window
 514            .last_prompt
 515            .take()
 516            .expect("prompt was not called");
 517        let _ = done_tx.try_send(answer);
 518    }
 519
 520    #[cfg(any(test, feature = "test-support"))]
 521    pub fn leak_detector(&self) -> Arc<Mutex<LeakDetector>> {
 522        self.cx.borrow().leak_detector()
 523    }
 524
 525    #[cfg(any(test, feature = "test-support"))]
 526    pub fn assert_dropped(&self, handle: impl WeakHandle) {
 527        self.cx
 528            .borrow()
 529            .leak_detector()
 530            .lock()
 531            .assert_dropped(handle.id())
 532    }
 533}
 534
 535impl AsyncAppContext {
 536    pub fn spawn<F, Fut, T>(&self, f: F) -> Task<T>
 537    where
 538        F: FnOnce(AsyncAppContext) -> Fut,
 539        Fut: 'static + Future<Output = T>,
 540        T: 'static,
 541    {
 542        self.0.borrow().foreground.spawn(f(self.clone()))
 543    }
 544
 545    pub fn read<T, F: FnOnce(&AppContext) -> T>(&mut self, callback: F) -> T {
 546        callback(self.0.borrow().as_ref())
 547    }
 548
 549    pub fn update<T, F: FnOnce(&mut MutableAppContext) -> T>(&mut self, callback: F) -> T {
 550        self.0.borrow_mut().update(callback)
 551    }
 552
 553    pub fn add_model<T, F>(&mut self, build_model: F) -> ModelHandle<T>
 554    where
 555        T: Entity,
 556        F: FnOnce(&mut ModelContext<T>) -> T,
 557    {
 558        self.update(|cx| cx.add_model(build_model))
 559    }
 560
 561    pub fn add_view<T, F>(&mut self, window_id: usize, build_view: F) -> ViewHandle<T>
 562    where
 563        T: View,
 564        F: FnOnce(&mut ViewContext<T>) -> T,
 565    {
 566        self.update(|cx| cx.add_view(window_id, build_view))
 567    }
 568
 569    pub fn add_window<T, F>(
 570        &mut self,
 571        window_options: WindowOptions,
 572        build_root_view: F,
 573    ) -> (usize, ViewHandle<T>)
 574    where
 575        T: View,
 576        F: FnOnce(&mut ViewContext<T>) -> T,
 577    {
 578        self.update(|cx| cx.add_window(window_options, build_root_view))
 579    }
 580
 581    pub fn platform(&self) -> Arc<dyn Platform> {
 582        self.0.borrow().platform()
 583    }
 584
 585    pub fn foreground(&self) -> Rc<executor::Foreground> {
 586        self.0.borrow().foreground.clone()
 587    }
 588
 589    pub fn background(&self) -> Arc<executor::Background> {
 590        self.0.borrow().cx.background.clone()
 591    }
 592}
 593
 594impl UpdateModel for AsyncAppContext {
 595    fn update_model<E: Entity, O>(
 596        &mut self,
 597        handle: &ModelHandle<E>,
 598        update: &mut dyn FnMut(&mut E, &mut ModelContext<E>) -> O,
 599    ) -> O {
 600        self.0.borrow_mut().update_model(handle, update)
 601    }
 602}
 603
 604impl UpgradeModelHandle for AsyncAppContext {
 605    fn upgrade_model_handle<T: Entity>(
 606        &self,
 607        handle: &WeakModelHandle<T>,
 608    ) -> Option<ModelHandle<T>> {
 609        self.0.borrow().upgrade_model_handle(handle)
 610    }
 611
 612    fn model_handle_is_upgradable<T: Entity>(&self, handle: &WeakModelHandle<T>) -> bool {
 613        self.0.borrow().model_handle_is_upgradable(handle)
 614    }
 615
 616    fn upgrade_any_model_handle(&self, handle: &AnyWeakModelHandle) -> Option<AnyModelHandle> {
 617        self.0.borrow().upgrade_any_model_handle(handle)
 618    }
 619}
 620
 621impl UpgradeViewHandle for AsyncAppContext {
 622    fn upgrade_view_handle<T: View>(&self, handle: &WeakViewHandle<T>) -> Option<ViewHandle<T>> {
 623        self.0.borrow_mut().upgrade_view_handle(handle)
 624    }
 625
 626    fn upgrade_any_view_handle(&self, handle: &AnyWeakViewHandle) -> Option<AnyViewHandle> {
 627        self.0.borrow_mut().upgrade_any_view_handle(handle)
 628    }
 629}
 630
 631impl ReadModelWith for AsyncAppContext {
 632    fn read_model_with<E: Entity, T>(
 633        &self,
 634        handle: &ModelHandle<E>,
 635        read: &mut dyn FnMut(&E, &AppContext) -> T,
 636    ) -> T {
 637        let cx = self.0.borrow();
 638        let cx = cx.as_ref();
 639        read(handle.read(cx), cx)
 640    }
 641}
 642
 643impl UpdateView for AsyncAppContext {
 644    fn update_view<T, S>(
 645        &mut self,
 646        handle: &ViewHandle<T>,
 647        update: &mut dyn FnMut(&mut T, &mut ViewContext<T>) -> S,
 648    ) -> S
 649    where
 650        T: View,
 651    {
 652        self.0.borrow_mut().update_view(handle, update)
 653    }
 654}
 655
 656impl ReadViewWith for AsyncAppContext {
 657    fn read_view_with<V, T>(
 658        &self,
 659        handle: &ViewHandle<V>,
 660        read: &mut dyn FnMut(&V, &AppContext) -> T,
 661    ) -> T
 662    where
 663        V: View,
 664    {
 665        let cx = self.0.borrow();
 666        let cx = cx.as_ref();
 667        read(handle.read(cx), cx)
 668    }
 669}
 670
 671#[cfg(any(test, feature = "test-support"))]
 672impl UpdateModel for TestAppContext {
 673    fn update_model<T: Entity, O>(
 674        &mut self,
 675        handle: &ModelHandle<T>,
 676        update: &mut dyn FnMut(&mut T, &mut ModelContext<T>) -> O,
 677    ) -> O {
 678        self.cx.borrow_mut().update_model(handle, update)
 679    }
 680}
 681
 682#[cfg(any(test, feature = "test-support"))]
 683impl ReadModelWith for TestAppContext {
 684    fn read_model_with<E: Entity, T>(
 685        &self,
 686        handle: &ModelHandle<E>,
 687        read: &mut dyn FnMut(&E, &AppContext) -> T,
 688    ) -> T {
 689        let cx = self.cx.borrow();
 690        let cx = cx.as_ref();
 691        read(handle.read(cx), cx)
 692    }
 693}
 694
 695#[cfg(any(test, feature = "test-support"))]
 696impl UpdateView for TestAppContext {
 697    fn update_view<T, S>(
 698        &mut self,
 699        handle: &ViewHandle<T>,
 700        update: &mut dyn FnMut(&mut T, &mut ViewContext<T>) -> S,
 701    ) -> S
 702    where
 703        T: View,
 704    {
 705        self.cx.borrow_mut().update_view(handle, update)
 706    }
 707}
 708
 709#[cfg(any(test, feature = "test-support"))]
 710impl ReadViewWith for TestAppContext {
 711    fn read_view_with<V, T>(
 712        &self,
 713        handle: &ViewHandle<V>,
 714        read: &mut dyn FnMut(&V, &AppContext) -> T,
 715    ) -> T
 716    where
 717        V: View,
 718    {
 719        let cx = self.cx.borrow();
 720        let cx = cx.as_ref();
 721        read(handle.read(cx), cx)
 722    }
 723}
 724
 725type ActionCallback =
 726    dyn FnMut(&mut dyn AnyView, &dyn Action, &mut MutableAppContext, usize, usize);
 727type GlobalActionCallback = dyn FnMut(&dyn Action, &mut MutableAppContext);
 728
 729type SubscriptionCallback = Box<dyn FnMut(&dyn Any, &mut MutableAppContext) -> bool>;
 730type GlobalSubscriptionCallback = Box<dyn FnMut(&dyn Any, &mut MutableAppContext)>;
 731type ObservationCallback = Box<dyn FnMut(&mut MutableAppContext) -> bool>;
 732type FocusObservationCallback = Box<dyn FnMut(&mut MutableAppContext) -> bool>;
 733type GlobalObservationCallback = Box<dyn FnMut(&dyn Any, &mut MutableAppContext)>;
 734type ReleaseObservationCallback = Box<dyn FnOnce(&dyn Any, &mut MutableAppContext)>;
 735type DeserializeActionCallback = fn(json: &str) -> anyhow::Result<Box<dyn Action>>;
 736
 737pub struct MutableAppContext {
 738    weak_self: Option<rc::Weak<RefCell<Self>>>,
 739    foreground_platform: Rc<dyn platform::ForegroundPlatform>,
 740    assets: Arc<AssetCache>,
 741    cx: AppContext,
 742    action_deserializers: HashMap<&'static str, (TypeId, DeserializeActionCallback)>,
 743    capture_actions: HashMap<TypeId, HashMap<TypeId, Vec<Box<ActionCallback>>>>,
 744    actions: HashMap<TypeId, HashMap<TypeId, Vec<Box<ActionCallback>>>>,
 745    global_actions: HashMap<TypeId, Box<GlobalActionCallback>>,
 746    keystroke_matcher: keymap::Matcher,
 747    next_entity_id: usize,
 748    next_window_id: usize,
 749    next_subscription_id: usize,
 750    frame_count: usize,
 751    subscriptions: Arc<Mutex<HashMap<usize, BTreeMap<usize, Option<SubscriptionCallback>>>>>,
 752    global_subscriptions:
 753        Arc<Mutex<HashMap<TypeId, BTreeMap<usize, Option<GlobalSubscriptionCallback>>>>>,
 754    observations: Arc<Mutex<HashMap<usize, BTreeMap<usize, Option<ObservationCallback>>>>>,
 755    focus_observations:
 756        Arc<Mutex<HashMap<usize, BTreeMap<usize, Option<FocusObservationCallback>>>>>,
 757    global_observations:
 758        Arc<Mutex<HashMap<TypeId, BTreeMap<usize, Option<GlobalObservationCallback>>>>>,
 759    release_observations: Arc<Mutex<HashMap<usize, BTreeMap<usize, ReleaseObservationCallback>>>>,
 760    presenters_and_platform_windows:
 761        HashMap<usize, (Rc<RefCell<Presenter>>, Box<dyn platform::Window>)>,
 762    foreground: Rc<executor::Foreground>,
 763    pending_effects: VecDeque<Effect>,
 764    pending_focus_index: Option<usize>,
 765    pending_notifications: HashSet<usize>,
 766    pending_global_notifications: HashSet<TypeId>,
 767    pending_flushes: usize,
 768    flushing_effects: bool,
 769    next_cursor_style_handle_id: Arc<AtomicUsize>,
 770    halt_action_dispatch: bool,
 771}
 772
 773impl MutableAppContext {
 774    fn new(
 775        foreground: Rc<executor::Foreground>,
 776        background: Arc<executor::Background>,
 777        platform: Arc<dyn platform::Platform>,
 778        foreground_platform: Rc<dyn platform::ForegroundPlatform>,
 779        font_cache: Arc<FontCache>,
 780        ref_counts: RefCounts,
 781        asset_source: impl AssetSource,
 782    ) -> Self {
 783        Self {
 784            weak_self: None,
 785            foreground_platform,
 786            assets: Arc::new(AssetCache::new(asset_source)),
 787            cx: AppContext {
 788                models: Default::default(),
 789                views: Default::default(),
 790                windows: Default::default(),
 791                globals: Default::default(),
 792                element_states: Default::default(),
 793                ref_counts: Arc::new(Mutex::new(ref_counts)),
 794                background,
 795                font_cache,
 796                platform,
 797            },
 798            action_deserializers: HashMap::new(),
 799            capture_actions: HashMap::new(),
 800            actions: HashMap::new(),
 801            global_actions: HashMap::new(),
 802            keystroke_matcher: keymap::Matcher::default(),
 803            next_entity_id: 0,
 804            next_window_id: 0,
 805            next_subscription_id: 0,
 806            frame_count: 0,
 807            subscriptions: Default::default(),
 808            global_subscriptions: Default::default(),
 809            observations: Default::default(),
 810            focus_observations: Default::default(),
 811            release_observations: Default::default(),
 812            global_observations: Default::default(),
 813            presenters_and_platform_windows: HashMap::new(),
 814            foreground,
 815            pending_effects: VecDeque::new(),
 816            pending_focus_index: None,
 817            pending_notifications: HashSet::new(),
 818            pending_global_notifications: HashSet::new(),
 819            pending_flushes: 0,
 820            flushing_effects: false,
 821            next_cursor_style_handle_id: Default::default(),
 822            halt_action_dispatch: false,
 823        }
 824    }
 825
 826    pub fn upgrade(&self) -> App {
 827        App(self.weak_self.as_ref().unwrap().upgrade().unwrap())
 828    }
 829
 830    pub fn quit(&mut self) {
 831        let mut futures = Vec::new();
 832        for model_id in self.cx.models.keys().copied().collect::<Vec<_>>() {
 833            let mut model = self.cx.models.remove(&model_id).unwrap();
 834            futures.extend(model.app_will_quit(self));
 835            self.cx.models.insert(model_id, model);
 836        }
 837
 838        for view_id in self.cx.views.keys().copied().collect::<Vec<_>>() {
 839            let mut view = self.cx.views.remove(&view_id).unwrap();
 840            futures.extend(view.app_will_quit(self));
 841            self.cx.views.insert(view_id, view);
 842        }
 843
 844        self.remove_all_windows();
 845
 846        let futures = futures::future::join_all(futures);
 847        if self
 848            .background
 849            .block_with_timeout(Duration::from_millis(100), futures)
 850            .is_err()
 851        {
 852            log::error!("timed out waiting on app_will_quit");
 853        }
 854    }
 855
 856    pub fn remove_all_windows(&mut self) {
 857        for (window_id, _) in self.cx.windows.drain() {
 858            self.presenters_and_platform_windows.remove(&window_id);
 859        }
 860        self.flush_effects();
 861    }
 862
 863    pub fn platform(&self) -> Arc<dyn platform::Platform> {
 864        self.cx.platform.clone()
 865    }
 866
 867    pub fn font_cache(&self) -> &Arc<FontCache> {
 868        &self.cx.font_cache
 869    }
 870
 871    pub fn foreground(&self) -> &Rc<executor::Foreground> {
 872        &self.foreground
 873    }
 874
 875    pub fn background(&self) -> &Arc<executor::Background> {
 876        &self.cx.background
 877    }
 878
 879    pub fn debug_elements(&self, window_id: usize) -> Option<crate::json::Value> {
 880        self.presenters_and_platform_windows
 881            .get(&window_id)
 882            .and_then(|(presenter, _)| presenter.borrow().debug_elements(self))
 883    }
 884
 885    pub fn deserialize_action(
 886        &self,
 887        name: &str,
 888        argument: Option<&str>,
 889    ) -> Result<Box<dyn Action>> {
 890        let callback = self
 891            .action_deserializers
 892            .get(name)
 893            .ok_or_else(|| anyhow!("unknown action {}", name))?
 894            .1;
 895        callback(argument.unwrap_or("{}"))
 896            .with_context(|| format!("invalid data for action {}", name))
 897    }
 898
 899    pub fn add_action<A, V, F>(&mut self, handler: F)
 900    where
 901        A: Action,
 902        V: View,
 903        F: 'static + FnMut(&mut V, &A, &mut ViewContext<V>),
 904    {
 905        self.add_action_internal(handler, false)
 906    }
 907
 908    pub fn capture_action<A, V, F>(&mut self, handler: F)
 909    where
 910        A: Action,
 911        V: View,
 912        F: 'static + FnMut(&mut V, &A, &mut ViewContext<V>),
 913    {
 914        self.add_action_internal(handler, true)
 915    }
 916
 917    fn add_action_internal<A, V, F>(&mut self, mut handler: F, capture: bool)
 918    where
 919        A: Action,
 920        V: View,
 921        F: 'static + FnMut(&mut V, &A, &mut ViewContext<V>),
 922    {
 923        let handler = Box::new(
 924            move |view: &mut dyn AnyView,
 925                  action: &dyn Action,
 926                  cx: &mut MutableAppContext,
 927                  window_id: usize,
 928                  view_id: usize| {
 929                let action = action.as_any().downcast_ref().unwrap();
 930                let mut cx = ViewContext::new(cx, window_id, view_id);
 931                handler(
 932                    view.as_any_mut()
 933                        .downcast_mut()
 934                        .expect("downcast is type safe"),
 935                    action,
 936                    &mut cx,
 937                );
 938            },
 939        );
 940
 941        self.action_deserializers
 942            .entry(A::qualified_name())
 943            .or_insert((TypeId::of::<A>(), A::from_json_str));
 944
 945        let actions = if capture {
 946            &mut self.capture_actions
 947        } else {
 948            &mut self.actions
 949        };
 950
 951        actions
 952            .entry(TypeId::of::<V>())
 953            .or_default()
 954            .entry(TypeId::of::<A>())
 955            .or_default()
 956            .push(handler);
 957    }
 958
 959    pub fn add_async_action<A, V, F>(&mut self, mut handler: F)
 960    where
 961        A: Action,
 962        V: View,
 963        F: 'static + FnMut(&mut V, &A, &mut ViewContext<V>) -> Option<Task<Result<()>>>,
 964    {
 965        self.add_action(move |view, action, cx| {
 966            handler(view, action, cx).map(|task| task.detach_and_log_err(cx));
 967        })
 968    }
 969
 970    pub fn add_global_action<A, F>(&mut self, mut handler: F)
 971    where
 972        A: Action,
 973        F: 'static + FnMut(&A, &mut MutableAppContext),
 974    {
 975        let handler = Box::new(move |action: &dyn Action, cx: &mut MutableAppContext| {
 976            let action = action.as_any().downcast_ref().unwrap();
 977            handler(action, cx);
 978        });
 979
 980        self.action_deserializers
 981            .entry(A::qualified_name())
 982            .or_insert((TypeId::of::<A>(), A::from_json_str));
 983
 984        if self
 985            .global_actions
 986            .insert(TypeId::of::<A>(), handler)
 987            .is_some()
 988        {
 989            panic!(
 990                "registered multiple global handlers for {}",
 991                type_name::<A>()
 992            );
 993        }
 994    }
 995
 996    pub fn window_ids(&self) -> impl Iterator<Item = usize> + '_ {
 997        self.cx.windows.keys().cloned()
 998    }
 999
1000    pub fn activate_window(&self, window_id: usize) {
1001        if let Some((_, window)) = self.presenters_and_platform_windows.get(&window_id) {
1002            window.activate()
1003        }
1004    }
1005
1006    pub fn root_view<T: View>(&self, window_id: usize) -> Option<ViewHandle<T>> {
1007        self.cx
1008            .windows
1009            .get(&window_id)
1010            .and_then(|window| window.root_view.clone().downcast::<T>())
1011    }
1012
1013    pub fn render_view(
1014        &mut self,
1015        window_id: usize,
1016        view_id: usize,
1017        titlebar_height: f32,
1018        refreshing: bool,
1019    ) -> Result<ElementBox> {
1020        let mut view = self
1021            .cx
1022            .views
1023            .remove(&(window_id, view_id))
1024            .ok_or(anyhow!("view not found"))?;
1025        let element = view.render(window_id, view_id, titlebar_height, refreshing, self);
1026        self.cx.views.insert((window_id, view_id), view);
1027        Ok(element)
1028    }
1029
1030    pub fn render_views(
1031        &mut self,
1032        window_id: usize,
1033        titlebar_height: f32,
1034    ) -> HashMap<usize, ElementBox> {
1035        self.start_frame();
1036        let view_ids = self
1037            .views
1038            .keys()
1039            .filter_map(|(win_id, view_id)| {
1040                if *win_id == window_id {
1041                    Some(*view_id)
1042                } else {
1043                    None
1044                }
1045            })
1046            .collect::<Vec<_>>();
1047        view_ids
1048            .into_iter()
1049            .map(|view_id| {
1050                (
1051                    view_id,
1052                    self.render_view(window_id, view_id, titlebar_height, false)
1053                        .unwrap(),
1054                )
1055            })
1056            .collect()
1057    }
1058
1059    pub(crate) fn start_frame(&mut self) {
1060        self.frame_count += 1;
1061    }
1062
1063    pub fn update<T, F: FnOnce(&mut Self) -> T>(&mut self, callback: F) -> T {
1064        self.pending_flushes += 1;
1065        let result = callback(self);
1066        self.flush_effects();
1067        result
1068    }
1069
1070    pub fn set_menus(&mut self, menus: Vec<Menu>) {
1071        self.foreground_platform.set_menus(menus);
1072    }
1073
1074    fn prompt(
1075        &self,
1076        window_id: usize,
1077        level: PromptLevel,
1078        msg: &str,
1079        answers: &[&str],
1080    ) -> oneshot::Receiver<usize> {
1081        let (_, window) = &self.presenters_and_platform_windows[&window_id];
1082        window.prompt(level, msg, answers)
1083    }
1084
1085    pub fn prompt_for_paths(
1086        &self,
1087        options: PathPromptOptions,
1088    ) -> oneshot::Receiver<Option<Vec<PathBuf>>> {
1089        self.foreground_platform.prompt_for_paths(options)
1090    }
1091
1092    pub fn prompt_for_new_path(&self, directory: &Path) -> oneshot::Receiver<Option<PathBuf>> {
1093        self.foreground_platform.prompt_for_new_path(directory)
1094    }
1095
1096    pub fn emit_global<E: Any>(&mut self, payload: E) {
1097        self.pending_effects.push_back(Effect::GlobalEvent {
1098            payload: Box::new(payload),
1099        });
1100    }
1101
1102    pub fn subscribe<E, H, F>(&mut self, handle: &H, mut callback: F) -> Subscription
1103    where
1104        E: Entity,
1105        E::Event: 'static,
1106        H: Handle<E>,
1107        F: 'static + FnMut(H, &E::Event, &mut Self),
1108    {
1109        self.subscribe_internal(handle, move |handle, event, cx| {
1110            callback(handle, event, cx);
1111            true
1112        })
1113    }
1114
1115    pub fn subscribe_global<E, F>(&mut self, mut callback: F) -> Subscription
1116    where
1117        E: Any,
1118        F: 'static + FnMut(&E, &mut Self),
1119    {
1120        let subscription_id = post_inc(&mut self.next_subscription_id);
1121        let type_id = TypeId::of::<E>();
1122        self.pending_effects.push_back(Effect::GlobalSubscription {
1123            type_id,
1124            subscription_id,
1125            callback: Box::new(move |payload, cx| {
1126                let payload = payload.downcast_ref().expect("downcast is type safe");
1127                callback(payload, cx)
1128            }),
1129        });
1130        Subscription::GlobalSubscription {
1131            id: subscription_id,
1132            type_id,
1133            subscriptions: Some(Arc::downgrade(&self.global_subscriptions)),
1134        }
1135    }
1136
1137    pub fn observe<E, H, F>(&mut self, handle: &H, mut callback: F) -> Subscription
1138    where
1139        E: Entity,
1140        E::Event: 'static,
1141        H: Handle<E>,
1142        F: 'static + FnMut(H, &mut Self),
1143    {
1144        self.observe_internal(handle, move |handle, cx| {
1145            callback(handle, cx);
1146            true
1147        })
1148    }
1149
1150    pub fn subscribe_internal<E, H, F>(&mut self, handle: &H, mut callback: F) -> Subscription
1151    where
1152        E: Entity,
1153        E::Event: 'static,
1154        H: Handle<E>,
1155        F: 'static + FnMut(H, &E::Event, &mut Self) -> bool,
1156    {
1157        let subscription_id = post_inc(&mut self.next_subscription_id);
1158        let emitter = handle.downgrade();
1159        self.pending_effects.push_back(Effect::Subscription {
1160            entity_id: handle.id(),
1161            subscription_id,
1162            callback: Box::new(move |payload, cx| {
1163                if let Some(emitter) = H::upgrade_from(&emitter, cx.as_ref()) {
1164                    let payload = payload.downcast_ref().expect("downcast is type safe");
1165                    callback(emitter, payload, cx)
1166                } else {
1167                    false
1168                }
1169            }),
1170        });
1171        Subscription::Subscription {
1172            id: subscription_id,
1173            entity_id: handle.id(),
1174            subscriptions: Some(Arc::downgrade(&self.subscriptions)),
1175        }
1176    }
1177
1178    fn observe_internal<E, H, F>(&mut self, handle: &H, mut callback: F) -> Subscription
1179    where
1180        E: Entity,
1181        E::Event: 'static,
1182        H: Handle<E>,
1183        F: 'static + FnMut(H, &mut Self) -> bool,
1184    {
1185        let subscription_id = post_inc(&mut self.next_subscription_id);
1186        let observed = handle.downgrade();
1187        let entity_id = handle.id();
1188        self.pending_effects.push_back(Effect::Observation {
1189            entity_id,
1190            subscription_id,
1191            callback: Box::new(move |cx| {
1192                if let Some(observed) = H::upgrade_from(&observed, cx) {
1193                    callback(observed, cx)
1194                } else {
1195                    false
1196                }
1197            }),
1198        });
1199        Subscription::Observation {
1200            id: subscription_id,
1201            entity_id,
1202            observations: Some(Arc::downgrade(&self.observations)),
1203        }
1204    }
1205
1206    fn observe_focus<F, V>(&mut self, handle: &ViewHandle<V>, mut callback: F) -> Subscription
1207    where
1208        F: 'static + FnMut(ViewHandle<V>, &mut MutableAppContext) -> bool,
1209        V: View,
1210    {
1211        let subscription_id = post_inc(&mut self.next_subscription_id);
1212        let observed = handle.downgrade();
1213        let view_id = handle.id();
1214        self.pending_effects.push_back(Effect::FocusObservation {
1215            view_id,
1216            subscription_id,
1217            callback: Box::new(move |cx| {
1218                if let Some(observed) = observed.upgrade(cx) {
1219                    callback(observed, cx)
1220                } else {
1221                    false
1222                }
1223            }),
1224        });
1225        Subscription::FocusObservation {
1226            id: subscription_id,
1227            view_id,
1228            observations: Some(Arc::downgrade(&self.focus_observations)),
1229        }
1230    }
1231
1232    pub fn observe_global<G, F>(&mut self, mut observe: F) -> Subscription
1233    where
1234        G: Any,
1235        F: 'static + FnMut(&G, &mut MutableAppContext),
1236    {
1237        let type_id = TypeId::of::<G>();
1238        let id = post_inc(&mut self.next_subscription_id);
1239
1240        self.global_observations
1241            .lock()
1242            .entry(type_id)
1243            .or_default()
1244            .insert(
1245                id,
1246                Some(
1247                    Box::new(move |global: &dyn Any, cx: &mut MutableAppContext| {
1248                        observe(global.downcast_ref().unwrap(), cx)
1249                    }) as GlobalObservationCallback,
1250                ),
1251            );
1252
1253        Subscription::GlobalObservation {
1254            id,
1255            type_id,
1256            observations: Some(Arc::downgrade(&self.global_observations)),
1257        }
1258    }
1259
1260    pub fn observe_release<E, H, F>(&mut self, handle: &H, callback: F) -> Subscription
1261    where
1262        E: Entity,
1263        E::Event: 'static,
1264        H: Handle<E>,
1265        F: 'static + FnOnce(&E, &mut Self),
1266    {
1267        let id = post_inc(&mut self.next_subscription_id);
1268        self.release_observations
1269            .lock()
1270            .entry(handle.id())
1271            .or_default()
1272            .insert(
1273                id,
1274                Box::new(move |released, cx| {
1275                    let released = released.downcast_ref().unwrap();
1276                    callback(released, cx)
1277                }),
1278            );
1279        Subscription::ReleaseObservation {
1280            id,
1281            entity_id: handle.id(),
1282            observations: Some(Arc::downgrade(&self.release_observations)),
1283        }
1284    }
1285
1286    pub fn defer(&mut self, callback: impl 'static + FnOnce(&mut MutableAppContext)) {
1287        self.pending_effects.push_back(Effect::Deferred {
1288            callback: Box::new(callback),
1289            after_window_update: false,
1290        })
1291    }
1292
1293    pub fn after_window_update(&mut self, callback: impl 'static + FnOnce(&mut MutableAppContext)) {
1294        self.pending_effects.push_back(Effect::Deferred {
1295            callback: Box::new(callback),
1296            after_window_update: true,
1297        })
1298    }
1299
1300    pub(crate) fn notify_model(&mut self, model_id: usize) {
1301        if self.pending_notifications.insert(model_id) {
1302            self.pending_effects
1303                .push_back(Effect::ModelNotification { model_id });
1304        }
1305    }
1306
1307    pub(crate) fn notify_view(&mut self, window_id: usize, view_id: usize) {
1308        if self.pending_notifications.insert(view_id) {
1309            self.pending_effects
1310                .push_back(Effect::ViewNotification { window_id, view_id });
1311        }
1312    }
1313
1314    pub(crate) fn notify_global(&mut self, type_id: TypeId) {
1315        if self.pending_global_notifications.insert(type_id) {
1316            self.pending_effects
1317                .push_back(Effect::GlobalNotification { type_id });
1318        }
1319    }
1320
1321    pub fn all_action_names<'a>(&'a self) -> impl Iterator<Item = &'static str> + 'a {
1322        self.action_deserializers.keys().copied()
1323    }
1324
1325    pub fn available_actions(
1326        &self,
1327        window_id: usize,
1328        view_id: usize,
1329    ) -> impl Iterator<Item = (&'static str, Box<dyn Action>, SmallVec<[&Binding; 1]>)> {
1330        let mut action_types: HashSet<_> = self.global_actions.keys().copied().collect();
1331
1332        let presenter = self
1333            .presenters_and_platform_windows
1334            .get(&window_id)
1335            .unwrap()
1336            .0
1337            .clone();
1338        let dispatch_path = presenter.borrow().dispatch_path_from(view_id);
1339        for view_id in dispatch_path {
1340            if let Some(view) = self.views.get(&(window_id, view_id)) {
1341                let view_type = view.as_any().type_id();
1342                if let Some(actions) = self.actions.get(&view_type) {
1343                    action_types.extend(actions.keys().copied());
1344                }
1345            }
1346        }
1347
1348        self.action_deserializers
1349            .iter()
1350            .filter_map(move |(name, (type_id, deserialize))| {
1351                if action_types.contains(type_id) {
1352                    Some((
1353                        *name,
1354                        deserialize("{}").ok()?,
1355                        self.keystroke_matcher
1356                            .bindings_for_action_type(*type_id)
1357                            .collect(),
1358                    ))
1359                } else {
1360                    None
1361                }
1362            })
1363    }
1364
1365    pub fn dispatch_action_at(&mut self, window_id: usize, view_id: usize, action: &dyn Action) {
1366        let presenter = self
1367            .presenters_and_platform_windows
1368            .get(&window_id)
1369            .unwrap()
1370            .0
1371            .clone();
1372        let dispatch_path = presenter.borrow().dispatch_path_from(view_id);
1373        self.dispatch_action_any(window_id, &dispatch_path, action);
1374    }
1375
1376    pub fn dispatch_action<A: Action>(
1377        &mut self,
1378        window_id: usize,
1379        dispatch_path: Vec<usize>,
1380        action: &A,
1381    ) {
1382        self.dispatch_action_any(window_id, &dispatch_path, action);
1383    }
1384
1385    pub(crate) fn dispatch_action_any(
1386        &mut self,
1387        window_id: usize,
1388        path: &[usize],
1389        action: &dyn Action,
1390    ) -> bool {
1391        self.update(|this| {
1392            this.halt_action_dispatch = false;
1393            for (capture_phase, view_id) in path
1394                .iter()
1395                .map(|view_id| (true, *view_id))
1396                .chain(path.iter().rev().map(|view_id| (false, *view_id)))
1397            {
1398                if let Some(mut view) = this.cx.views.remove(&(window_id, view_id)) {
1399                    let type_id = view.as_any().type_id();
1400
1401                    if let Some((name, mut handlers)) = this
1402                        .actions_mut(capture_phase)
1403                        .get_mut(&type_id)
1404                        .and_then(|h| h.remove_entry(&action.id()))
1405                    {
1406                        for handler in handlers.iter_mut().rev() {
1407                            this.halt_action_dispatch = true;
1408                            handler(view.as_mut(), action, this, window_id, view_id);
1409                            if this.halt_action_dispatch {
1410                                break;
1411                            }
1412                        }
1413                        this.actions_mut(capture_phase)
1414                            .get_mut(&type_id)
1415                            .unwrap()
1416                            .insert(name, handlers);
1417                    }
1418
1419                    this.cx.views.insert((window_id, view_id), view);
1420
1421                    if this.halt_action_dispatch {
1422                        break;
1423                    }
1424                }
1425            }
1426
1427            if !this.halt_action_dispatch {
1428                this.halt_action_dispatch = this.dispatch_global_action_any(action);
1429            }
1430            this.halt_action_dispatch
1431        })
1432    }
1433
1434    fn actions_mut(
1435        &mut self,
1436        capture_phase: bool,
1437    ) -> &mut HashMap<TypeId, HashMap<TypeId, Vec<Box<ActionCallback>>>> {
1438        if capture_phase {
1439            &mut self.capture_actions
1440        } else {
1441            &mut self.actions
1442        }
1443    }
1444
1445    pub fn dispatch_global_action<A: Action>(&mut self, action: A) {
1446        self.dispatch_global_action_any(&action);
1447    }
1448
1449    fn dispatch_global_action_any(&mut self, action: &dyn Action) -> bool {
1450        self.update(|this| {
1451            if let Some((name, mut handler)) = this.global_actions.remove_entry(&action.id()) {
1452                handler(action, this);
1453                this.global_actions.insert(name, handler);
1454                true
1455            } else {
1456                false
1457            }
1458        })
1459    }
1460
1461    pub fn add_bindings<T: IntoIterator<Item = keymap::Binding>>(&mut self, bindings: T) {
1462        self.keystroke_matcher.add_bindings(bindings);
1463    }
1464
1465    pub fn clear_bindings(&mut self) {
1466        self.keystroke_matcher.clear_bindings();
1467    }
1468
1469    pub fn dispatch_keystroke(
1470        &mut self,
1471        window_id: usize,
1472        dispatch_path: Vec<usize>,
1473        keystroke: &Keystroke,
1474    ) -> bool {
1475        let mut context_chain = Vec::new();
1476        for view_id in &dispatch_path {
1477            let view = self
1478                .cx
1479                .views
1480                .get(&(window_id, *view_id))
1481                .expect("view in responder chain does not exist");
1482            context_chain.push(view.keymap_context(self.as_ref()));
1483        }
1484
1485        let mut pending = false;
1486        for (i, cx) in context_chain.iter().enumerate().rev() {
1487            match self
1488                .keystroke_matcher
1489                .push_keystroke(keystroke.clone(), dispatch_path[i], cx)
1490            {
1491                MatchResult::None => {}
1492                MatchResult::Pending => pending = true,
1493                MatchResult::Action(action) => {
1494                    if self.dispatch_action_any(window_id, &dispatch_path[0..=i], action.as_ref()) {
1495                        self.keystroke_matcher.clear_pending();
1496                        return true;
1497                    }
1498                }
1499            }
1500        }
1501
1502        pending
1503    }
1504
1505    pub fn default_global<T: 'static + Default>(&mut self) -> &T {
1506        let type_id = TypeId::of::<T>();
1507        self.update(|this| {
1508            if !this.globals.contains_key(&type_id) {
1509                this.notify_global(type_id);
1510            }
1511
1512            this.cx
1513                .globals
1514                .entry(type_id)
1515                .or_insert_with(|| Box::new(T::default()));
1516        });
1517        self.globals.get(&type_id).unwrap().downcast_ref().unwrap()
1518    }
1519
1520    pub fn set_global<T: 'static>(&mut self, state: T) {
1521        self.update(|this| {
1522            let type_id = TypeId::of::<T>();
1523            this.cx.globals.insert(type_id, Box::new(state));
1524            this.notify_global(type_id);
1525        });
1526    }
1527
1528    pub fn update_default_global<T, F, U>(&mut self, update: F) -> U
1529    where
1530        T: 'static + Default,
1531        F: FnOnce(&mut T, &mut MutableAppContext) -> U,
1532    {
1533        self.update(|this| {
1534            let type_id = TypeId::of::<T>();
1535            let mut state = this
1536                .cx
1537                .globals
1538                .remove(&type_id)
1539                .unwrap_or_else(|| Box::new(T::default()));
1540            let result = update(state.downcast_mut().unwrap(), this);
1541            this.cx.globals.insert(type_id, state);
1542            this.notify_global(type_id);
1543            result
1544        })
1545    }
1546
1547    pub fn update_global<T, F, U>(&mut self, update: F) -> U
1548    where
1549        T: 'static,
1550        F: FnOnce(&mut T, &mut MutableAppContext) -> U,
1551    {
1552        self.update(|this| {
1553            let type_id = TypeId::of::<T>();
1554            let mut state = this
1555                .cx
1556                .globals
1557                .remove(&type_id)
1558                .expect("no global has been added for this type");
1559            let result = update(state.downcast_mut().unwrap(), this);
1560            this.cx.globals.insert(type_id, state);
1561            this.notify_global(type_id);
1562            result
1563        })
1564    }
1565
1566    pub fn add_model<T, F>(&mut self, build_model: F) -> ModelHandle<T>
1567    where
1568        T: Entity,
1569        F: FnOnce(&mut ModelContext<T>) -> T,
1570    {
1571        self.update(|this| {
1572            let model_id = post_inc(&mut this.next_entity_id);
1573            let handle = ModelHandle::new(model_id, &this.cx.ref_counts);
1574            let mut cx = ModelContext::new(this, model_id);
1575            let model = build_model(&mut cx);
1576            this.cx.models.insert(model_id, Box::new(model));
1577            handle
1578        })
1579    }
1580
1581    pub fn add_window<T, F>(
1582        &mut self,
1583        window_options: WindowOptions,
1584        build_root_view: F,
1585    ) -> (usize, ViewHandle<T>)
1586    where
1587        T: View,
1588        F: FnOnce(&mut ViewContext<T>) -> T,
1589    {
1590        self.update(|this| {
1591            let window_id = post_inc(&mut this.next_window_id);
1592            let root_view = this.add_view(window_id, build_root_view);
1593
1594            this.cx.windows.insert(
1595                window_id,
1596                Window {
1597                    root_view: root_view.clone().into(),
1598                    focused_view_id: Some(root_view.id()),
1599                    invalidation: None,
1600                },
1601            );
1602            root_view.update(this, |view, cx| {
1603                view.on_focus(cx);
1604            });
1605            this.open_platform_window(window_id, window_options);
1606
1607            (window_id, root_view)
1608        })
1609    }
1610
1611    pub fn remove_window(&mut self, window_id: usize) {
1612        self.cx.windows.remove(&window_id);
1613        self.presenters_and_platform_windows.remove(&window_id);
1614        self.flush_effects();
1615    }
1616
1617    fn open_platform_window(&mut self, window_id: usize, window_options: WindowOptions) {
1618        let mut window =
1619            self.cx
1620                .platform
1621                .open_window(window_id, window_options, self.foreground.clone());
1622        let presenter = Rc::new(RefCell::new(
1623            self.build_presenter(window_id, window.titlebar_height()),
1624        ));
1625
1626        {
1627            let mut app = self.upgrade();
1628            let presenter = presenter.clone();
1629            window.on_event(Box::new(move |event| {
1630                app.update(|cx| {
1631                    if let Event::KeyDown { keystroke, .. } = &event {
1632                        if cx.dispatch_keystroke(
1633                            window_id,
1634                            presenter.borrow().dispatch_path(cx.as_ref()),
1635                            keystroke,
1636                        ) {
1637                            return;
1638                        }
1639                    }
1640
1641                    presenter.borrow_mut().dispatch_event(event, cx);
1642                })
1643            }));
1644        }
1645
1646        {
1647            let mut app = self.upgrade();
1648            window.on_resize(Box::new(move || {
1649                app.update(|cx| cx.resize_window(window_id))
1650            }));
1651        }
1652
1653        {
1654            let mut app = self.upgrade();
1655            window.on_close(Box::new(move || {
1656                app.update(|cx| cx.remove_window(window_id));
1657            }));
1658        }
1659
1660        let scene =
1661            presenter
1662                .borrow_mut()
1663                .build_scene(window.size(), window.scale_factor(), false, self);
1664        window.present_scene(scene);
1665        self.presenters_and_platform_windows
1666            .insert(window_id, (presenter.clone(), window));
1667    }
1668
1669    pub fn build_presenter(&mut self, window_id: usize, titlebar_height: f32) -> Presenter {
1670        Presenter::new(
1671            window_id,
1672            titlebar_height,
1673            self.cx.font_cache.clone(),
1674            TextLayoutCache::new(self.cx.platform.fonts()),
1675            self.assets.clone(),
1676            self,
1677        )
1678    }
1679
1680    pub fn build_render_context<V: View>(
1681        &mut self,
1682        window_id: usize,
1683        view_id: usize,
1684        titlebar_height: f32,
1685        refreshing: bool,
1686    ) -> RenderContext<V> {
1687        RenderContext {
1688            app: self,
1689            titlebar_height,
1690            refreshing,
1691            window_id,
1692            view_id,
1693            view_type: PhantomData,
1694        }
1695    }
1696
1697    pub fn add_view<T, F>(&mut self, window_id: usize, build_view: F) -> ViewHandle<T>
1698    where
1699        T: View,
1700        F: FnOnce(&mut ViewContext<T>) -> T,
1701    {
1702        self.add_option_view(window_id, |cx| Some(build_view(cx)))
1703            .unwrap()
1704    }
1705
1706    pub fn add_option_view<T, F>(
1707        &mut self,
1708        window_id: usize,
1709        build_view: F,
1710    ) -> Option<ViewHandle<T>>
1711    where
1712        T: View,
1713        F: FnOnce(&mut ViewContext<T>) -> Option<T>,
1714    {
1715        self.update(|this| {
1716            let view_id = post_inc(&mut this.next_entity_id);
1717            let mut cx = ViewContext::new(this, window_id, view_id);
1718            let handle = if let Some(view) = build_view(&mut cx) {
1719                this.cx.views.insert((window_id, view_id), Box::new(view));
1720                if let Some(window) = this.cx.windows.get_mut(&window_id) {
1721                    window
1722                        .invalidation
1723                        .get_or_insert_with(Default::default)
1724                        .updated
1725                        .insert(view_id);
1726                }
1727                Some(ViewHandle::new(window_id, view_id, &this.cx.ref_counts))
1728            } else {
1729                None
1730            };
1731            handle
1732        })
1733    }
1734
1735    fn remove_dropped_entities(&mut self) {
1736        loop {
1737            let (dropped_models, dropped_views, dropped_element_states) =
1738                self.cx.ref_counts.lock().take_dropped();
1739            if dropped_models.is_empty()
1740                && dropped_views.is_empty()
1741                && dropped_element_states.is_empty()
1742            {
1743                break;
1744            }
1745
1746            for model_id in dropped_models {
1747                self.subscriptions.lock().remove(&model_id);
1748                self.observations.lock().remove(&model_id);
1749                let mut model = self.cx.models.remove(&model_id).unwrap();
1750                model.release(self);
1751                self.pending_effects
1752                    .push_back(Effect::ModelRelease { model_id, model });
1753            }
1754
1755            for (window_id, view_id) in dropped_views {
1756                self.subscriptions.lock().remove(&view_id);
1757                self.observations.lock().remove(&view_id);
1758                let mut view = self.cx.views.remove(&(window_id, view_id)).unwrap();
1759                view.release(self);
1760                let change_focus_to = self.cx.windows.get_mut(&window_id).and_then(|window| {
1761                    window
1762                        .invalidation
1763                        .get_or_insert_with(Default::default)
1764                        .removed
1765                        .push(view_id);
1766                    if window.focused_view_id == Some(view_id) {
1767                        Some(window.root_view.id())
1768                    } else {
1769                        None
1770                    }
1771                });
1772
1773                if let Some(view_id) = change_focus_to {
1774                    self.handle_focus_effect(window_id, Some(view_id));
1775                }
1776
1777                self.pending_effects
1778                    .push_back(Effect::ViewRelease { view_id, view });
1779            }
1780
1781            for key in dropped_element_states {
1782                self.cx.element_states.remove(&key);
1783            }
1784        }
1785    }
1786
1787    fn flush_effects(&mut self) {
1788        self.pending_flushes = self.pending_flushes.saturating_sub(1);
1789        let mut after_window_update_callbacks = Vec::new();
1790
1791        if !self.flushing_effects && self.pending_flushes == 0 {
1792            self.flushing_effects = true;
1793
1794            let mut refreshing = false;
1795            loop {
1796                if let Some(effect) = self.pending_effects.pop_front() {
1797                    if let Some(pending_focus_index) = self.pending_focus_index.as_mut() {
1798                        *pending_focus_index = pending_focus_index.saturating_sub(1);
1799                    }
1800                    match effect {
1801                        Effect::Subscription {
1802                            entity_id,
1803                            subscription_id,
1804                            callback,
1805                        } => self.handle_subscription_effect(entity_id, subscription_id, callback),
1806                        Effect::Event { entity_id, payload } => self.emit_event(entity_id, payload),
1807                        Effect::GlobalSubscription {
1808                            type_id,
1809                            subscription_id,
1810                            callback,
1811                        } => self.handle_global_subscription_effect(
1812                            type_id,
1813                            subscription_id,
1814                            callback,
1815                        ),
1816                        Effect::GlobalEvent { payload } => self.emit_global_event(payload),
1817                        Effect::Observation {
1818                            entity_id,
1819                            subscription_id,
1820                            callback,
1821                        } => self.handle_observation_effect(entity_id, subscription_id, callback),
1822                        Effect::ModelNotification { model_id } => {
1823                            self.handle_model_notification_effect(model_id)
1824                        }
1825                        Effect::ViewNotification { window_id, view_id } => {
1826                            self.handle_view_notification_effect(window_id, view_id)
1827                        }
1828                        Effect::GlobalNotification { type_id } => {
1829                            self.handle_global_notification_effect(type_id)
1830                        }
1831                        Effect::Deferred {
1832                            callback,
1833                            after_window_update,
1834                        } => {
1835                            if after_window_update {
1836                                after_window_update_callbacks.push(callback);
1837                            } else {
1838                                callback(self)
1839                            }
1840                        }
1841                        Effect::ModelRelease { model_id, model } => {
1842                            self.handle_entity_release_effect(model_id, model.as_any())
1843                        }
1844                        Effect::ViewRelease { view_id, view } => {
1845                            self.handle_entity_release_effect(view_id, view.as_any())
1846                        }
1847                        Effect::Focus { window_id, view_id } => {
1848                            self.handle_focus_effect(window_id, view_id);
1849                        }
1850                        Effect::FocusObservation {
1851                            view_id,
1852                            subscription_id,
1853                            callback,
1854                        } => {
1855                            self.handle_focus_observation_effect(view_id, subscription_id, callback)
1856                        }
1857                        Effect::ResizeWindow { window_id } => {
1858                            if let Some(window) = self.cx.windows.get_mut(&window_id) {
1859                                window
1860                                    .invalidation
1861                                    .get_or_insert(WindowInvalidation::default());
1862                            }
1863                        }
1864                        Effect::RefreshWindows => {
1865                            refreshing = true;
1866                        }
1867                    }
1868                    self.pending_notifications.clear();
1869                    self.remove_dropped_entities();
1870                } else {
1871                    self.remove_dropped_entities();
1872                    if refreshing {
1873                        self.perform_window_refresh();
1874                    } else {
1875                        self.update_windows();
1876                    }
1877
1878                    if self.pending_effects.is_empty() {
1879                        for callback in after_window_update_callbacks.drain(..) {
1880                            callback(self);
1881                        }
1882
1883                        if self.pending_effects.is_empty() {
1884                            self.flushing_effects = false;
1885                            self.pending_notifications.clear();
1886                            self.pending_global_notifications.clear();
1887                            break;
1888                        }
1889                    }
1890
1891                    refreshing = false;
1892                }
1893            }
1894        }
1895    }
1896
1897    fn update_windows(&mut self) {
1898        let mut invalidations = HashMap::new();
1899        for (window_id, window) in &mut self.cx.windows {
1900            if let Some(invalidation) = window.invalidation.take() {
1901                invalidations.insert(*window_id, invalidation);
1902            }
1903        }
1904
1905        for (window_id, mut invalidation) in invalidations {
1906            if let Some((presenter, mut window)) =
1907                self.presenters_and_platform_windows.remove(&window_id)
1908            {
1909                {
1910                    let mut presenter = presenter.borrow_mut();
1911                    presenter.invalidate(&mut invalidation, self);
1912                    let scene =
1913                        presenter.build_scene(window.size(), window.scale_factor(), false, self);
1914                    window.present_scene(scene);
1915                }
1916                self.presenters_and_platform_windows
1917                    .insert(window_id, (presenter, window));
1918            }
1919        }
1920    }
1921
1922    fn resize_window(&mut self, window_id: usize) {
1923        self.pending_effects
1924            .push_back(Effect::ResizeWindow { window_id });
1925    }
1926
1927    pub fn refresh_windows(&mut self) {
1928        self.pending_effects.push_back(Effect::RefreshWindows);
1929    }
1930
1931    fn perform_window_refresh(&mut self) {
1932        let mut presenters = mem::take(&mut self.presenters_and_platform_windows);
1933        for (window_id, (presenter, window)) in &mut presenters {
1934            let mut invalidation = self
1935                .cx
1936                .windows
1937                .get_mut(&window_id)
1938                .unwrap()
1939                .invalidation
1940                .take();
1941            let mut presenter = presenter.borrow_mut();
1942            presenter.refresh(
1943                invalidation.as_mut().unwrap_or(&mut Default::default()),
1944                self,
1945            );
1946            let scene = presenter.build_scene(window.size(), window.scale_factor(), true, self);
1947            window.present_scene(scene);
1948        }
1949        self.presenters_and_platform_windows = presenters;
1950    }
1951
1952    pub fn set_cursor_style(&mut self, style: CursorStyle) -> CursorStyleHandle {
1953        self.platform.set_cursor_style(style);
1954        let id = self.next_cursor_style_handle_id.fetch_add(1, SeqCst);
1955        CursorStyleHandle {
1956            id,
1957            next_cursor_style_handle_id: self.next_cursor_style_handle_id.clone(),
1958            platform: self.platform(),
1959        }
1960    }
1961
1962    fn handle_subscription_effect(
1963        &mut self,
1964        entity_id: usize,
1965        subscription_id: usize,
1966        callback: SubscriptionCallback,
1967    ) {
1968        match self
1969            .subscriptions
1970            .lock()
1971            .entry(entity_id)
1972            .or_default()
1973            .entry(subscription_id)
1974        {
1975            btree_map::Entry::Vacant(entry) => {
1976                entry.insert(Some(callback));
1977            }
1978            // Subscription was dropped before effect was processed
1979            btree_map::Entry::Occupied(entry) => {
1980                debug_assert!(entry.get().is_none());
1981                entry.remove();
1982            }
1983        }
1984    }
1985
1986    fn emit_event(&mut self, entity_id: usize, payload: Box<dyn Any>) {
1987        let callbacks = self.subscriptions.lock().remove(&entity_id);
1988        if let Some(callbacks) = callbacks {
1989            for (id, callback) in callbacks {
1990                if let Some(mut callback) = callback {
1991                    let alive = callback(payload.as_ref(), self);
1992                    if alive {
1993                        match self
1994                            .subscriptions
1995                            .lock()
1996                            .entry(entity_id)
1997                            .or_default()
1998                            .entry(id)
1999                        {
2000                            btree_map::Entry::Vacant(entry) => {
2001                                entry.insert(Some(callback));
2002                            }
2003                            btree_map::Entry::Occupied(entry) => {
2004                                entry.remove();
2005                            }
2006                        }
2007                    }
2008                }
2009            }
2010        }
2011    }
2012
2013    fn handle_global_subscription_effect(
2014        &mut self,
2015        type_id: TypeId,
2016        subscription_id: usize,
2017        callback: GlobalSubscriptionCallback,
2018    ) {
2019        match self
2020            .global_subscriptions
2021            .lock()
2022            .entry(type_id)
2023            .or_default()
2024            .entry(subscription_id)
2025        {
2026            btree_map::Entry::Vacant(entry) => {
2027                entry.insert(Some(callback));
2028            }
2029            // Subscription was dropped before effect was processed
2030            btree_map::Entry::Occupied(entry) => {
2031                debug_assert!(entry.get().is_none());
2032                entry.remove();
2033            }
2034        }
2035    }
2036
2037    fn emit_global_event(&mut self, payload: Box<dyn Any>) {
2038        let type_id = (&*payload).type_id();
2039        let callbacks = self.global_subscriptions.lock().remove(&type_id);
2040        if let Some(callbacks) = callbacks {
2041            for (id, callback) in callbacks {
2042                if let Some(mut callback) = callback {
2043                    callback(payload.as_ref(), self);
2044                    match self
2045                        .global_subscriptions
2046                        .lock()
2047                        .entry(type_id)
2048                        .or_default()
2049                        .entry(id)
2050                    {
2051                        btree_map::Entry::Vacant(entry) => {
2052                            entry.insert(Some(callback));
2053                        }
2054                        btree_map::Entry::Occupied(entry) => {
2055                            entry.remove();
2056                        }
2057                    }
2058                }
2059            }
2060        }
2061    }
2062
2063    fn handle_observation_effect(
2064        &mut self,
2065        entity_id: usize,
2066        subscription_id: usize,
2067        callback: ObservationCallback,
2068    ) {
2069        match self
2070            .observations
2071            .lock()
2072            .entry(entity_id)
2073            .or_default()
2074            .entry(subscription_id)
2075        {
2076            btree_map::Entry::Vacant(entry) => {
2077                entry.insert(Some(callback));
2078            }
2079            // Observation was dropped before effect was processed
2080            btree_map::Entry::Occupied(entry) => {
2081                debug_assert!(entry.get().is_none());
2082                entry.remove();
2083            }
2084        }
2085    }
2086
2087    fn handle_focus_observation_effect(
2088        &mut self,
2089        view_id: usize,
2090        subscription_id: usize,
2091        callback: FocusObservationCallback,
2092    ) {
2093        match self
2094            .focus_observations
2095            .lock()
2096            .entry(view_id)
2097            .or_default()
2098            .entry(subscription_id)
2099        {
2100            btree_map::Entry::Vacant(entry) => {
2101                entry.insert(Some(callback));
2102            }
2103            // Observation was dropped before effect was processed
2104            btree_map::Entry::Occupied(entry) => {
2105                debug_assert!(entry.get().is_none());
2106                entry.remove();
2107            }
2108        }
2109    }
2110
2111    fn handle_model_notification_effect(&mut self, observed_id: usize) {
2112        let callbacks = self.observations.lock().remove(&observed_id);
2113        if let Some(callbacks) = callbacks {
2114            if self.cx.models.contains_key(&observed_id) {
2115                for (id, callback) in callbacks {
2116                    if let Some(mut callback) = callback {
2117                        let alive = callback(self);
2118                        if alive {
2119                            match self
2120                                .observations
2121                                .lock()
2122                                .entry(observed_id)
2123                                .or_default()
2124                                .entry(id)
2125                            {
2126                                btree_map::Entry::Vacant(entry) => {
2127                                    entry.insert(Some(callback));
2128                                }
2129                                btree_map::Entry::Occupied(entry) => {
2130                                    entry.remove();
2131                                }
2132                            }
2133                        }
2134                    }
2135                }
2136            }
2137        }
2138    }
2139
2140    fn handle_view_notification_effect(
2141        &mut self,
2142        observed_window_id: usize,
2143        observed_view_id: usize,
2144    ) {
2145        if let Some(window) = self.cx.windows.get_mut(&observed_window_id) {
2146            window
2147                .invalidation
2148                .get_or_insert_with(Default::default)
2149                .updated
2150                .insert(observed_view_id);
2151        }
2152
2153        let callbacks = self.observations.lock().remove(&observed_view_id);
2154        if let Some(callbacks) = callbacks {
2155            if self
2156                .cx
2157                .views
2158                .contains_key(&(observed_window_id, observed_view_id))
2159            {
2160                for (id, callback) in callbacks {
2161                    if let Some(mut callback) = callback {
2162                        let alive = callback(self);
2163                        if alive {
2164                            match self
2165                                .observations
2166                                .lock()
2167                                .entry(observed_view_id)
2168                                .or_default()
2169                                .entry(id)
2170                            {
2171                                btree_map::Entry::Vacant(entry) => {
2172                                    entry.insert(Some(callback));
2173                                }
2174                                btree_map::Entry::Occupied(entry) => {
2175                                    entry.remove();
2176                                }
2177                            }
2178                        }
2179                    }
2180                }
2181            }
2182        }
2183    }
2184
2185    fn handle_global_notification_effect(&mut self, observed_type_id: TypeId) {
2186        let callbacks = self.global_observations.lock().remove(&observed_type_id);
2187        if let Some(callbacks) = callbacks {
2188            if let Some(global) = self.cx.globals.remove(&observed_type_id) {
2189                for (id, callback) in callbacks {
2190                    if let Some(mut callback) = callback {
2191                        callback(global.as_ref(), self);
2192                        match self
2193                            .global_observations
2194                            .lock()
2195                            .entry(observed_type_id)
2196                            .or_default()
2197                            .entry(id)
2198                        {
2199                            collections::btree_map::Entry::Vacant(entry) => {
2200                                entry.insert(Some(callback));
2201                            }
2202                            collections::btree_map::Entry::Occupied(entry) => {
2203                                entry.remove();
2204                            }
2205                        }
2206                    }
2207                }
2208                self.cx.globals.insert(observed_type_id, global);
2209            }
2210        }
2211    }
2212
2213    fn handle_entity_release_effect(&mut self, entity_id: usize, entity: &dyn Any) {
2214        let callbacks = self.release_observations.lock().remove(&entity_id);
2215        if let Some(callbacks) = callbacks {
2216            for (_, callback) in callbacks {
2217                callback(entity, self);
2218            }
2219        }
2220    }
2221
2222    fn handle_focus_effect(&mut self, window_id: usize, focused_id: Option<usize>) {
2223        self.pending_focus_index.take();
2224
2225        if self
2226            .cx
2227            .windows
2228            .get(&window_id)
2229            .map(|w| w.focused_view_id)
2230            .map_or(false, |cur_focused| cur_focused == focused_id)
2231        {
2232            return;
2233        }
2234
2235        self.update(|this| {
2236            let blurred_id = this.cx.windows.get_mut(&window_id).and_then(|window| {
2237                let blurred_id = window.focused_view_id;
2238                window.focused_view_id = focused_id;
2239                blurred_id
2240            });
2241
2242            if let Some(blurred_id) = blurred_id {
2243                if let Some(mut blurred_view) = this.cx.views.remove(&(window_id, blurred_id)) {
2244                    blurred_view.on_blur(this, window_id, blurred_id);
2245                    this.cx.views.insert((window_id, blurred_id), blurred_view);
2246                }
2247            }
2248
2249            if let Some(focused_id) = focused_id {
2250                if let Some(mut focused_view) = this.cx.views.remove(&(window_id, focused_id)) {
2251                    focused_view.on_focus(this, window_id, focused_id);
2252                    this.cx.views.insert((window_id, focused_id), focused_view);
2253
2254                    let callbacks = this.focus_observations.lock().remove(&focused_id);
2255                    if let Some(callbacks) = callbacks {
2256                        for (id, callback) in callbacks {
2257                            if let Some(mut callback) = callback {
2258                                let alive = callback(this);
2259                                if alive {
2260                                    match this
2261                                        .focus_observations
2262                                        .lock()
2263                                        .entry(focused_id)
2264                                        .or_default()
2265                                        .entry(id)
2266                                    {
2267                                        btree_map::Entry::Vacant(entry) => {
2268                                            entry.insert(Some(callback));
2269                                        }
2270                                        btree_map::Entry::Occupied(entry) => {
2271                                            entry.remove();
2272                                        }
2273                                    }
2274                                }
2275                            }
2276                        }
2277                    }
2278                }
2279            }
2280        })
2281    }
2282
2283    fn focus(&mut self, window_id: usize, view_id: Option<usize>) {
2284        if let Some(pending_focus_index) = self.pending_focus_index {
2285            self.pending_effects.remove(pending_focus_index);
2286        }
2287        self.pending_focus_index = Some(self.pending_effects.len());
2288        self.pending_effects
2289            .push_back(Effect::Focus { window_id, view_id });
2290    }
2291
2292    pub fn spawn<F, Fut, T>(&self, f: F) -> Task<T>
2293    where
2294        F: FnOnce(AsyncAppContext) -> Fut,
2295        Fut: 'static + Future<Output = T>,
2296        T: 'static,
2297    {
2298        let future = f(self.to_async());
2299        let cx = self.to_async();
2300        self.foreground.spawn(async move {
2301            let result = future.await;
2302            cx.0.borrow_mut().flush_effects();
2303            result
2304        })
2305    }
2306
2307    pub fn to_async(&self) -> AsyncAppContext {
2308        AsyncAppContext(self.weak_self.as_ref().unwrap().upgrade().unwrap())
2309    }
2310
2311    pub fn write_to_clipboard(&self, item: ClipboardItem) {
2312        self.cx.platform.write_to_clipboard(item);
2313    }
2314
2315    pub fn read_from_clipboard(&self) -> Option<ClipboardItem> {
2316        self.cx.platform.read_from_clipboard()
2317    }
2318
2319    #[cfg(any(test, feature = "test-support"))]
2320    pub fn leak_detector(&self) -> Arc<Mutex<LeakDetector>> {
2321        self.cx.ref_counts.lock().leak_detector.clone()
2322    }
2323}
2324
2325impl ReadModel for MutableAppContext {
2326    fn read_model<T: Entity>(&self, handle: &ModelHandle<T>) -> &T {
2327        if let Some(model) = self.cx.models.get(&handle.model_id) {
2328            model
2329                .as_any()
2330                .downcast_ref()
2331                .expect("downcast is type safe")
2332        } else {
2333            panic!("circular model reference");
2334        }
2335    }
2336}
2337
2338impl UpdateModel for MutableAppContext {
2339    fn update_model<T: Entity, V>(
2340        &mut self,
2341        handle: &ModelHandle<T>,
2342        update: &mut dyn FnMut(&mut T, &mut ModelContext<T>) -> V,
2343    ) -> V {
2344        if let Some(mut model) = self.cx.models.remove(&handle.model_id) {
2345            self.update(|this| {
2346                let mut cx = ModelContext::new(this, handle.model_id);
2347                let result = update(
2348                    model
2349                        .as_any_mut()
2350                        .downcast_mut()
2351                        .expect("downcast is type safe"),
2352                    &mut cx,
2353                );
2354                this.cx.models.insert(handle.model_id, model);
2355                result
2356            })
2357        } else {
2358            panic!("circular model update");
2359        }
2360    }
2361}
2362
2363impl UpgradeModelHandle for MutableAppContext {
2364    fn upgrade_model_handle<T: Entity>(
2365        &self,
2366        handle: &WeakModelHandle<T>,
2367    ) -> Option<ModelHandle<T>> {
2368        self.cx.upgrade_model_handle(handle)
2369    }
2370
2371    fn model_handle_is_upgradable<T: Entity>(&self, handle: &WeakModelHandle<T>) -> bool {
2372        self.cx.model_handle_is_upgradable(handle)
2373    }
2374
2375    fn upgrade_any_model_handle(&self, handle: &AnyWeakModelHandle) -> Option<AnyModelHandle> {
2376        self.cx.upgrade_any_model_handle(handle)
2377    }
2378}
2379
2380impl UpgradeViewHandle for MutableAppContext {
2381    fn upgrade_view_handle<T: View>(&self, handle: &WeakViewHandle<T>) -> Option<ViewHandle<T>> {
2382        self.cx.upgrade_view_handle(handle)
2383    }
2384
2385    fn upgrade_any_view_handle(&self, handle: &AnyWeakViewHandle) -> Option<AnyViewHandle> {
2386        self.cx.upgrade_any_view_handle(handle)
2387    }
2388}
2389
2390impl ReadView for MutableAppContext {
2391    fn read_view<T: View>(&self, handle: &ViewHandle<T>) -> &T {
2392        if let Some(view) = self.cx.views.get(&(handle.window_id, handle.view_id)) {
2393            view.as_any().downcast_ref().expect("downcast is type safe")
2394        } else {
2395            panic!("circular view reference");
2396        }
2397    }
2398}
2399
2400impl UpdateView for MutableAppContext {
2401    fn update_view<T, S>(
2402        &mut self,
2403        handle: &ViewHandle<T>,
2404        update: &mut dyn FnMut(&mut T, &mut ViewContext<T>) -> S,
2405    ) -> S
2406    where
2407        T: View,
2408    {
2409        self.update(|this| {
2410            let mut view = this
2411                .cx
2412                .views
2413                .remove(&(handle.window_id, handle.view_id))
2414                .expect("circular view update");
2415
2416            let mut cx = ViewContext::new(this, handle.window_id, handle.view_id);
2417            let result = update(
2418                view.as_any_mut()
2419                    .downcast_mut()
2420                    .expect("downcast is type safe"),
2421                &mut cx,
2422            );
2423            this.cx
2424                .views
2425                .insert((handle.window_id, handle.view_id), view);
2426            result
2427        })
2428    }
2429}
2430
2431impl AsRef<AppContext> for MutableAppContext {
2432    fn as_ref(&self) -> &AppContext {
2433        &self.cx
2434    }
2435}
2436
2437impl Deref for MutableAppContext {
2438    type Target = AppContext;
2439
2440    fn deref(&self) -> &Self::Target {
2441        &self.cx
2442    }
2443}
2444
2445pub struct AppContext {
2446    models: HashMap<usize, Box<dyn AnyModel>>,
2447    views: HashMap<(usize, usize), Box<dyn AnyView>>,
2448    windows: HashMap<usize, Window>,
2449    globals: HashMap<TypeId, Box<dyn Any>>,
2450    element_states: HashMap<ElementStateId, Box<dyn Any>>,
2451    background: Arc<executor::Background>,
2452    ref_counts: Arc<Mutex<RefCounts>>,
2453    font_cache: Arc<FontCache>,
2454    platform: Arc<dyn Platform>,
2455}
2456
2457impl AppContext {
2458    pub(crate) fn root_view(&self, window_id: usize) -> Option<AnyViewHandle> {
2459        self.windows
2460            .get(&window_id)
2461            .map(|window| window.root_view.clone())
2462    }
2463
2464    pub fn root_view_id(&self, window_id: usize) -> Option<usize> {
2465        self.windows
2466            .get(&window_id)
2467            .map(|window| window.root_view.id())
2468    }
2469
2470    pub fn focused_view_id(&self, window_id: usize) -> Option<usize> {
2471        self.windows
2472            .get(&window_id)
2473            .and_then(|window| window.focused_view_id)
2474    }
2475
2476    pub fn background(&self) -> &Arc<executor::Background> {
2477        &self.background
2478    }
2479
2480    pub fn font_cache(&self) -> &Arc<FontCache> {
2481        &self.font_cache
2482    }
2483
2484    pub fn platform(&self) -> &Arc<dyn Platform> {
2485        &self.platform
2486    }
2487
2488    pub fn has_global<T: 'static>(&self) -> bool {
2489        self.globals.contains_key(&TypeId::of::<T>())
2490    }
2491
2492    pub fn global<T: 'static>(&self) -> &T {
2493        if let Some(global) = self.globals.get(&TypeId::of::<T>()) {
2494            global.downcast_ref().unwrap()
2495        } else {
2496            panic!("no global has been added for {}", type_name::<T>());
2497        }
2498    }
2499}
2500
2501impl ReadModel for AppContext {
2502    fn read_model<T: Entity>(&self, handle: &ModelHandle<T>) -> &T {
2503        if let Some(model) = self.models.get(&handle.model_id) {
2504            model
2505                .as_any()
2506                .downcast_ref()
2507                .expect("downcast should be type safe")
2508        } else {
2509            panic!("circular model reference");
2510        }
2511    }
2512}
2513
2514impl UpgradeModelHandle for AppContext {
2515    fn upgrade_model_handle<T: Entity>(
2516        &self,
2517        handle: &WeakModelHandle<T>,
2518    ) -> Option<ModelHandle<T>> {
2519        if self.models.contains_key(&handle.model_id) {
2520            Some(ModelHandle::new(handle.model_id, &self.ref_counts))
2521        } else {
2522            None
2523        }
2524    }
2525
2526    fn model_handle_is_upgradable<T: Entity>(&self, handle: &WeakModelHandle<T>) -> bool {
2527        self.models.contains_key(&handle.model_id)
2528    }
2529
2530    fn upgrade_any_model_handle(&self, handle: &AnyWeakModelHandle) -> Option<AnyModelHandle> {
2531        if self.models.contains_key(&handle.model_id) {
2532            Some(AnyModelHandle::new(
2533                handle.model_id,
2534                handle.model_type,
2535                self.ref_counts.clone(),
2536            ))
2537        } else {
2538            None
2539        }
2540    }
2541}
2542
2543impl UpgradeViewHandle for AppContext {
2544    fn upgrade_view_handle<T: View>(&self, handle: &WeakViewHandle<T>) -> Option<ViewHandle<T>> {
2545        if self.ref_counts.lock().is_entity_alive(handle.view_id) {
2546            Some(ViewHandle::new(
2547                handle.window_id,
2548                handle.view_id,
2549                &self.ref_counts,
2550            ))
2551        } else {
2552            None
2553        }
2554    }
2555
2556    fn upgrade_any_view_handle(&self, handle: &AnyWeakViewHandle) -> Option<AnyViewHandle> {
2557        if self.ref_counts.lock().is_entity_alive(handle.view_id) {
2558            Some(AnyViewHandle::new(
2559                handle.window_id,
2560                handle.view_id,
2561                handle.view_type,
2562                self.ref_counts.clone(),
2563            ))
2564        } else {
2565            None
2566        }
2567    }
2568}
2569
2570impl ReadView for AppContext {
2571    fn read_view<T: View>(&self, handle: &ViewHandle<T>) -> &T {
2572        if let Some(view) = self.views.get(&(handle.window_id, handle.view_id)) {
2573            view.as_any()
2574                .downcast_ref()
2575                .expect("downcast should be type safe")
2576        } else {
2577            panic!("circular view reference");
2578        }
2579    }
2580}
2581
2582struct Window {
2583    root_view: AnyViewHandle,
2584    focused_view_id: Option<usize>,
2585    invalidation: Option<WindowInvalidation>,
2586}
2587
2588#[derive(Default, Clone)]
2589pub struct WindowInvalidation {
2590    pub updated: HashSet<usize>,
2591    pub removed: Vec<usize>,
2592}
2593
2594pub enum Effect {
2595    Subscription {
2596        entity_id: usize,
2597        subscription_id: usize,
2598        callback: SubscriptionCallback,
2599    },
2600    Event {
2601        entity_id: usize,
2602        payload: Box<dyn Any>,
2603    },
2604    GlobalSubscription {
2605        type_id: TypeId,
2606        subscription_id: usize,
2607        callback: GlobalSubscriptionCallback,
2608    },
2609    GlobalEvent {
2610        payload: Box<dyn Any>,
2611    },
2612    Observation {
2613        entity_id: usize,
2614        subscription_id: usize,
2615        callback: ObservationCallback,
2616    },
2617    ModelNotification {
2618        model_id: usize,
2619    },
2620    ViewNotification {
2621        window_id: usize,
2622        view_id: usize,
2623    },
2624    Deferred {
2625        callback: Box<dyn FnOnce(&mut MutableAppContext)>,
2626        after_window_update: bool,
2627    },
2628    GlobalNotification {
2629        type_id: TypeId,
2630    },
2631    ModelRelease {
2632        model_id: usize,
2633        model: Box<dyn AnyModel>,
2634    },
2635    ViewRelease {
2636        view_id: usize,
2637        view: Box<dyn AnyView>,
2638    },
2639    Focus {
2640        window_id: usize,
2641        view_id: Option<usize>,
2642    },
2643    FocusObservation {
2644        view_id: usize,
2645        subscription_id: usize,
2646        callback: FocusObservationCallback,
2647    },
2648    ResizeWindow {
2649        window_id: usize,
2650    },
2651    RefreshWindows,
2652}
2653
2654impl Debug for Effect {
2655    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
2656        match self {
2657            Effect::Subscription {
2658                entity_id,
2659                subscription_id,
2660                ..
2661            } => f
2662                .debug_struct("Effect::Subscribe")
2663                .field("entity_id", entity_id)
2664                .field("subscription_id", subscription_id)
2665                .finish(),
2666            Effect::Event { entity_id, .. } => f
2667                .debug_struct("Effect::Event")
2668                .field("entity_id", entity_id)
2669                .finish(),
2670            Effect::GlobalSubscription {
2671                type_id,
2672                subscription_id,
2673                ..
2674            } => f
2675                .debug_struct("Effect::Subscribe")
2676                .field("type_id", type_id)
2677                .field("subscription_id", subscription_id)
2678                .finish(),
2679            Effect::GlobalEvent { payload, .. } => f
2680                .debug_struct("Effect::GlobalEvent")
2681                .field("type_id", &(&*payload).type_id())
2682                .finish(),
2683            Effect::Observation {
2684                entity_id,
2685                subscription_id,
2686                ..
2687            } => f
2688                .debug_struct("Effect::Observation")
2689                .field("entity_id", entity_id)
2690                .field("subscription_id", subscription_id)
2691                .finish(),
2692            Effect::ModelNotification { model_id } => f
2693                .debug_struct("Effect::ModelNotification")
2694                .field("model_id", model_id)
2695                .finish(),
2696            Effect::ViewNotification { window_id, view_id } => f
2697                .debug_struct("Effect::ViewNotification")
2698                .field("window_id", window_id)
2699                .field("view_id", view_id)
2700                .finish(),
2701            Effect::GlobalNotification { type_id } => f
2702                .debug_struct("Effect::GlobalNotification")
2703                .field("type_id", type_id)
2704                .finish(),
2705            Effect::Deferred { .. } => f.debug_struct("Effect::Deferred").finish(),
2706            Effect::ModelRelease { model_id, .. } => f
2707                .debug_struct("Effect::ModelRelease")
2708                .field("model_id", model_id)
2709                .finish(),
2710            Effect::ViewRelease { view_id, .. } => f
2711                .debug_struct("Effect::ViewRelease")
2712                .field("view_id", view_id)
2713                .finish(),
2714            Effect::Focus { window_id, view_id } => f
2715                .debug_struct("Effect::Focus")
2716                .field("window_id", window_id)
2717                .field("view_id", view_id)
2718                .finish(),
2719            Effect::FocusObservation {
2720                view_id,
2721                subscription_id,
2722                ..
2723            } => f
2724                .debug_struct("Effect::FocusObservation")
2725                .field("view_id", view_id)
2726                .field("subscription_id", subscription_id)
2727                .finish(),
2728            Effect::ResizeWindow { window_id } => f
2729                .debug_struct("Effect::RefreshWindow")
2730                .field("window_id", window_id)
2731                .finish(),
2732            Effect::RefreshWindows => f.debug_struct("Effect::FullViewRefresh").finish(),
2733        }
2734    }
2735}
2736
2737pub trait AnyModel {
2738    fn as_any(&self) -> &dyn Any;
2739    fn as_any_mut(&mut self) -> &mut dyn Any;
2740    fn release(&mut self, cx: &mut MutableAppContext);
2741    fn app_will_quit(
2742        &mut self,
2743        cx: &mut MutableAppContext,
2744    ) -> Option<Pin<Box<dyn 'static + Future<Output = ()>>>>;
2745}
2746
2747impl<T> AnyModel for T
2748where
2749    T: Entity,
2750{
2751    fn as_any(&self) -> &dyn Any {
2752        self
2753    }
2754
2755    fn as_any_mut(&mut self) -> &mut dyn Any {
2756        self
2757    }
2758
2759    fn release(&mut self, cx: &mut MutableAppContext) {
2760        self.release(cx);
2761    }
2762
2763    fn app_will_quit(
2764        &mut self,
2765        cx: &mut MutableAppContext,
2766    ) -> Option<Pin<Box<dyn 'static + Future<Output = ()>>>> {
2767        self.app_will_quit(cx)
2768    }
2769}
2770
2771pub trait AnyView {
2772    fn as_any(&self) -> &dyn Any;
2773    fn as_any_mut(&mut self) -> &mut dyn Any;
2774    fn release(&mut self, cx: &mut MutableAppContext);
2775    fn app_will_quit(
2776        &mut self,
2777        cx: &mut MutableAppContext,
2778    ) -> Option<Pin<Box<dyn 'static + Future<Output = ()>>>>;
2779    fn ui_name(&self) -> &'static str;
2780    fn render<'a>(
2781        &mut self,
2782        window_id: usize,
2783        view_id: usize,
2784        titlebar_height: f32,
2785        refreshing: bool,
2786        cx: &mut MutableAppContext,
2787    ) -> ElementBox;
2788    fn on_focus(&mut self, cx: &mut MutableAppContext, window_id: usize, view_id: usize);
2789    fn on_blur(&mut self, cx: &mut MutableAppContext, window_id: usize, view_id: usize);
2790    fn keymap_context(&self, cx: &AppContext) -> keymap::Context;
2791    fn debug_json(&self, cx: &AppContext) -> serde_json::Value;
2792}
2793
2794impl<T> AnyView for T
2795where
2796    T: View,
2797{
2798    fn as_any(&self) -> &dyn Any {
2799        self
2800    }
2801
2802    fn as_any_mut(&mut self) -> &mut dyn Any {
2803        self
2804    }
2805
2806    fn release(&mut self, cx: &mut MutableAppContext) {
2807        self.release(cx);
2808    }
2809
2810    fn app_will_quit(
2811        &mut self,
2812        cx: &mut MutableAppContext,
2813    ) -> Option<Pin<Box<dyn 'static + Future<Output = ()>>>> {
2814        self.app_will_quit(cx)
2815    }
2816
2817    fn ui_name(&self) -> &'static str {
2818        T::ui_name()
2819    }
2820
2821    fn render<'a>(
2822        &mut self,
2823        window_id: usize,
2824        view_id: usize,
2825        titlebar_height: f32,
2826        refreshing: bool,
2827        cx: &mut MutableAppContext,
2828    ) -> ElementBox {
2829        View::render(
2830            self,
2831            &mut RenderContext {
2832                window_id,
2833                view_id,
2834                app: cx,
2835                view_type: PhantomData::<T>,
2836                titlebar_height,
2837                refreshing,
2838            },
2839        )
2840    }
2841
2842    fn on_focus(&mut self, cx: &mut MutableAppContext, window_id: usize, view_id: usize) {
2843        let mut cx = ViewContext::new(cx, window_id, view_id);
2844        View::on_focus(self, &mut cx);
2845    }
2846
2847    fn on_blur(&mut self, cx: &mut MutableAppContext, window_id: usize, view_id: usize) {
2848        let mut cx = ViewContext::new(cx, window_id, view_id);
2849        View::on_blur(self, &mut cx);
2850    }
2851
2852    fn keymap_context(&self, cx: &AppContext) -> keymap::Context {
2853        View::keymap_context(self, cx)
2854    }
2855
2856    fn debug_json(&self, cx: &AppContext) -> serde_json::Value {
2857        View::debug_json(self, cx)
2858    }
2859}
2860
2861pub struct ModelContext<'a, T: ?Sized> {
2862    app: &'a mut MutableAppContext,
2863    model_id: usize,
2864    model_type: PhantomData<T>,
2865    halt_stream: bool,
2866}
2867
2868impl<'a, T: Entity> ModelContext<'a, T> {
2869    fn new(app: &'a mut MutableAppContext, model_id: usize) -> Self {
2870        Self {
2871            app,
2872            model_id,
2873            model_type: PhantomData,
2874            halt_stream: false,
2875        }
2876    }
2877
2878    pub fn background(&self) -> &Arc<executor::Background> {
2879        &self.app.cx.background
2880    }
2881
2882    pub fn halt_stream(&mut self) {
2883        self.halt_stream = true;
2884    }
2885
2886    pub fn model_id(&self) -> usize {
2887        self.model_id
2888    }
2889
2890    pub fn add_model<S, F>(&mut self, build_model: F) -> ModelHandle<S>
2891    where
2892        S: Entity,
2893        F: FnOnce(&mut ModelContext<S>) -> S,
2894    {
2895        self.app.add_model(build_model)
2896    }
2897
2898    pub fn defer(&mut self, callback: impl 'static + FnOnce(&mut T, &mut ModelContext<T>)) {
2899        let handle = self.handle();
2900        self.app.defer(move |cx| {
2901            handle.update(cx, |model, cx| {
2902                callback(model, cx);
2903            })
2904        })
2905    }
2906
2907    pub fn emit(&mut self, payload: T::Event) {
2908        self.app.pending_effects.push_back(Effect::Event {
2909            entity_id: self.model_id,
2910            payload: Box::new(payload),
2911        });
2912    }
2913
2914    pub fn notify(&mut self) {
2915        self.app.notify_model(self.model_id);
2916    }
2917
2918    pub fn subscribe<S: Entity, F>(
2919        &mut self,
2920        handle: &ModelHandle<S>,
2921        mut callback: F,
2922    ) -> Subscription
2923    where
2924        S::Event: 'static,
2925        F: 'static + FnMut(&mut T, ModelHandle<S>, &S::Event, &mut ModelContext<T>),
2926    {
2927        let subscriber = self.weak_handle();
2928        self.app
2929            .subscribe_internal(handle, move |emitter, event, cx| {
2930                if let Some(subscriber) = subscriber.upgrade(cx) {
2931                    subscriber.update(cx, |subscriber, cx| {
2932                        callback(subscriber, emitter, event, cx);
2933                    });
2934                    true
2935                } else {
2936                    false
2937                }
2938            })
2939    }
2940
2941    pub fn observe<S, F>(&mut self, handle: &ModelHandle<S>, mut callback: F) -> Subscription
2942    where
2943        S: Entity,
2944        F: 'static + FnMut(&mut T, ModelHandle<S>, &mut ModelContext<T>),
2945    {
2946        let observer = self.weak_handle();
2947        self.app.observe_internal(handle, move |observed, cx| {
2948            if let Some(observer) = observer.upgrade(cx) {
2949                observer.update(cx, |observer, cx| {
2950                    callback(observer, observed, cx);
2951                });
2952                true
2953            } else {
2954                false
2955            }
2956        })
2957    }
2958
2959    pub fn observe_release<S, F>(
2960        &mut self,
2961        handle: &ModelHandle<S>,
2962        mut callback: F,
2963    ) -> Subscription
2964    where
2965        S: Entity,
2966        F: 'static + FnMut(&mut T, &S, &mut ModelContext<T>),
2967    {
2968        let observer = self.weak_handle();
2969        self.app.observe_release(handle, move |released, cx| {
2970            if let Some(observer) = observer.upgrade(cx) {
2971                observer.update(cx, |observer, cx| {
2972                    callback(observer, released, cx);
2973                });
2974            }
2975        })
2976    }
2977
2978    pub fn handle(&self) -> ModelHandle<T> {
2979        ModelHandle::new(self.model_id, &self.app.cx.ref_counts)
2980    }
2981
2982    pub fn weak_handle(&self) -> WeakModelHandle<T> {
2983        WeakModelHandle::new(self.model_id)
2984    }
2985
2986    pub fn spawn<F, Fut, S>(&self, f: F) -> Task<S>
2987    where
2988        F: FnOnce(ModelHandle<T>, AsyncAppContext) -> Fut,
2989        Fut: 'static + Future<Output = S>,
2990        S: 'static,
2991    {
2992        let handle = self.handle();
2993        self.app.spawn(|cx| f(handle, cx))
2994    }
2995
2996    pub fn spawn_weak<F, Fut, S>(&self, f: F) -> Task<S>
2997    where
2998        F: FnOnce(WeakModelHandle<T>, AsyncAppContext) -> Fut,
2999        Fut: 'static + Future<Output = S>,
3000        S: 'static,
3001    {
3002        let handle = self.weak_handle();
3003        self.app.spawn(|cx| f(handle, cx))
3004    }
3005}
3006
3007impl<M> AsRef<AppContext> for ModelContext<'_, M> {
3008    fn as_ref(&self) -> &AppContext {
3009        &self.app.cx
3010    }
3011}
3012
3013impl<M> AsMut<MutableAppContext> for ModelContext<'_, M> {
3014    fn as_mut(&mut self) -> &mut MutableAppContext {
3015        self.app
3016    }
3017}
3018
3019impl<M> ReadModel for ModelContext<'_, M> {
3020    fn read_model<T: Entity>(&self, handle: &ModelHandle<T>) -> &T {
3021        self.app.read_model(handle)
3022    }
3023}
3024
3025impl<M> UpdateModel for ModelContext<'_, M> {
3026    fn update_model<T: Entity, V>(
3027        &mut self,
3028        handle: &ModelHandle<T>,
3029        update: &mut dyn FnMut(&mut T, &mut ModelContext<T>) -> V,
3030    ) -> V {
3031        self.app.update_model(handle, update)
3032    }
3033}
3034
3035impl<M> UpgradeModelHandle for ModelContext<'_, M> {
3036    fn upgrade_model_handle<T: Entity>(
3037        &self,
3038        handle: &WeakModelHandle<T>,
3039    ) -> Option<ModelHandle<T>> {
3040        self.cx.upgrade_model_handle(handle)
3041    }
3042
3043    fn model_handle_is_upgradable<T: Entity>(&self, handle: &WeakModelHandle<T>) -> bool {
3044        self.cx.model_handle_is_upgradable(handle)
3045    }
3046
3047    fn upgrade_any_model_handle(&self, handle: &AnyWeakModelHandle) -> Option<AnyModelHandle> {
3048        self.cx.upgrade_any_model_handle(handle)
3049    }
3050}
3051
3052impl<M> Deref for ModelContext<'_, M> {
3053    type Target = MutableAppContext;
3054
3055    fn deref(&self) -> &Self::Target {
3056        &self.app
3057    }
3058}
3059
3060impl<M> DerefMut for ModelContext<'_, M> {
3061    fn deref_mut(&mut self) -> &mut Self::Target {
3062        &mut self.app
3063    }
3064}
3065
3066pub struct ViewContext<'a, T: ?Sized> {
3067    app: &'a mut MutableAppContext,
3068    window_id: usize,
3069    view_id: usize,
3070    view_type: PhantomData<T>,
3071}
3072
3073impl<'a, T: View> ViewContext<'a, T> {
3074    fn new(app: &'a mut MutableAppContext, window_id: usize, view_id: usize) -> Self {
3075        Self {
3076            app,
3077            window_id,
3078            view_id,
3079            view_type: PhantomData,
3080        }
3081    }
3082
3083    pub fn handle(&self) -> ViewHandle<T> {
3084        ViewHandle::new(self.window_id, self.view_id, &self.app.cx.ref_counts)
3085    }
3086
3087    pub fn weak_handle(&self) -> WeakViewHandle<T> {
3088        WeakViewHandle::new(self.window_id, self.view_id)
3089    }
3090
3091    pub fn window_id(&self) -> usize {
3092        self.window_id
3093    }
3094
3095    pub fn view_id(&self) -> usize {
3096        self.view_id
3097    }
3098
3099    pub fn foreground(&self) -> &Rc<executor::Foreground> {
3100        self.app.foreground()
3101    }
3102
3103    pub fn background_executor(&self) -> &Arc<executor::Background> {
3104        &self.app.cx.background
3105    }
3106
3107    pub fn platform(&self) -> Arc<dyn Platform> {
3108        self.app.platform()
3109    }
3110
3111    pub fn prompt(
3112        &self,
3113        level: PromptLevel,
3114        msg: &str,
3115        answers: &[&str],
3116    ) -> oneshot::Receiver<usize> {
3117        self.app.prompt(self.window_id, level, msg, answers)
3118    }
3119
3120    pub fn prompt_for_paths(
3121        &self,
3122        options: PathPromptOptions,
3123    ) -> oneshot::Receiver<Option<Vec<PathBuf>>> {
3124        self.app.prompt_for_paths(options)
3125    }
3126
3127    pub fn prompt_for_new_path(&self, directory: &Path) -> oneshot::Receiver<Option<PathBuf>> {
3128        self.app.prompt_for_new_path(directory)
3129    }
3130
3131    pub fn debug_elements(&self) -> crate::json::Value {
3132        self.app.debug_elements(self.window_id).unwrap()
3133    }
3134
3135    pub fn focus<S>(&mut self, handle: S)
3136    where
3137        S: Into<AnyViewHandle>,
3138    {
3139        let handle = handle.into();
3140        self.app.focus(handle.window_id, Some(handle.view_id));
3141    }
3142
3143    pub fn focus_self(&mut self) {
3144        self.app.focus(self.window_id, Some(self.view_id));
3145    }
3146
3147    pub fn blur(&mut self) {
3148        self.app.focus(self.window_id, None);
3149    }
3150
3151    pub fn add_model<S, F>(&mut self, build_model: F) -> ModelHandle<S>
3152    where
3153        S: Entity,
3154        F: FnOnce(&mut ModelContext<S>) -> S,
3155    {
3156        self.app.add_model(build_model)
3157    }
3158
3159    pub fn add_view<S, F>(&mut self, build_view: F) -> ViewHandle<S>
3160    where
3161        S: View,
3162        F: FnOnce(&mut ViewContext<S>) -> S,
3163    {
3164        self.app.add_view(self.window_id, build_view)
3165    }
3166
3167    pub fn add_option_view<S, F>(&mut self, build_view: F) -> Option<ViewHandle<S>>
3168    where
3169        S: View,
3170        F: FnOnce(&mut ViewContext<S>) -> Option<S>,
3171    {
3172        self.app.add_option_view(self.window_id, build_view)
3173    }
3174
3175    pub fn subscribe<E, H, F>(&mut self, handle: &H, mut callback: F) -> Subscription
3176    where
3177        E: Entity,
3178        E::Event: 'static,
3179        H: Handle<E>,
3180        F: 'static + FnMut(&mut T, H, &E::Event, &mut ViewContext<T>),
3181    {
3182        let subscriber = self.weak_handle();
3183        self.app
3184            .subscribe_internal(handle, move |emitter, event, cx| {
3185                if let Some(subscriber) = subscriber.upgrade(cx) {
3186                    subscriber.update(cx, |subscriber, cx| {
3187                        callback(subscriber, emitter, event, cx);
3188                    });
3189                    true
3190                } else {
3191                    false
3192                }
3193            })
3194    }
3195
3196    pub fn observe<E, F, H>(&mut self, handle: &H, mut callback: F) -> Subscription
3197    where
3198        E: Entity,
3199        H: Handle<E>,
3200        F: 'static + FnMut(&mut T, H, &mut ViewContext<T>),
3201    {
3202        let observer = self.weak_handle();
3203        self.app.observe_internal(handle, move |observed, cx| {
3204            if let Some(observer) = observer.upgrade(cx) {
3205                observer.update(cx, |observer, cx| {
3206                    callback(observer, observed, cx);
3207                });
3208                true
3209            } else {
3210                false
3211            }
3212        })
3213    }
3214
3215    pub fn observe_focus<F, V>(&mut self, handle: &ViewHandle<V>, mut callback: F) -> Subscription
3216    where
3217        F: 'static + FnMut(&mut T, ViewHandle<V>, &mut ViewContext<T>),
3218        V: View,
3219    {
3220        let observer = self.weak_handle();
3221        self.app.observe_focus(handle, move |observed, cx| {
3222            if let Some(observer) = observer.upgrade(cx) {
3223                observer.update(cx, |observer, cx| {
3224                    callback(observer, observed, cx);
3225                });
3226                true
3227            } else {
3228                false
3229            }
3230        })
3231    }
3232
3233    pub fn observe_release<E, F, H>(&mut self, handle: &H, mut callback: F) -> Subscription
3234    where
3235        E: Entity,
3236        H: Handle<E>,
3237        F: 'static + FnMut(&mut T, &E, &mut ViewContext<T>),
3238    {
3239        let observer = self.weak_handle();
3240        self.app.observe_release(handle, move |released, cx| {
3241            if let Some(observer) = observer.upgrade(cx) {
3242                observer.update(cx, |observer, cx| {
3243                    callback(observer, released, cx);
3244                });
3245            }
3246        })
3247    }
3248
3249    pub fn emit(&mut self, payload: T::Event) {
3250        self.app.pending_effects.push_back(Effect::Event {
3251            entity_id: self.view_id,
3252            payload: Box::new(payload),
3253        });
3254    }
3255
3256    pub fn notify(&mut self) {
3257        self.app.notify_view(self.window_id, self.view_id);
3258    }
3259
3260    pub fn defer(&mut self, callback: impl 'static + FnOnce(&mut T, &mut ViewContext<T>)) {
3261        let handle = self.handle();
3262        self.app.defer(move |cx| {
3263            handle.update(cx, |view, cx| {
3264                callback(view, cx);
3265            })
3266        })
3267    }
3268
3269    pub fn after_window_update(
3270        &mut self,
3271        callback: impl 'static + FnOnce(&mut T, &mut ViewContext<T>),
3272    ) {
3273        let handle = self.handle();
3274        self.app.after_window_update(move |cx| {
3275            handle.update(cx, |view, cx| {
3276                callback(view, cx);
3277            })
3278        })
3279    }
3280
3281    pub fn propagate_action(&mut self) {
3282        self.app.halt_action_dispatch = false;
3283    }
3284
3285    pub fn spawn<F, Fut, S>(&self, f: F) -> Task<S>
3286    where
3287        F: FnOnce(ViewHandle<T>, AsyncAppContext) -> Fut,
3288        Fut: 'static + Future<Output = S>,
3289        S: 'static,
3290    {
3291        let handle = self.handle();
3292        self.app.spawn(|cx| f(handle, cx))
3293    }
3294
3295    pub fn spawn_weak<F, Fut, S>(&self, f: F) -> Task<S>
3296    where
3297        F: FnOnce(WeakViewHandle<T>, AsyncAppContext) -> Fut,
3298        Fut: 'static + Future<Output = S>,
3299        S: 'static,
3300    {
3301        let handle = self.weak_handle();
3302        self.app.spawn(|cx| f(handle, cx))
3303    }
3304}
3305
3306pub struct RenderContext<'a, T: View> {
3307    pub app: &'a mut MutableAppContext,
3308    pub titlebar_height: f32,
3309    pub refreshing: bool,
3310    window_id: usize,
3311    view_id: usize,
3312    view_type: PhantomData<T>,
3313}
3314
3315impl<'a, T: View> RenderContext<'a, T> {
3316    pub fn handle(&self) -> WeakViewHandle<T> {
3317        WeakViewHandle::new(self.window_id, self.view_id)
3318    }
3319
3320    pub fn view_id(&self) -> usize {
3321        self.view_id
3322    }
3323}
3324
3325impl AsRef<AppContext> for &AppContext {
3326    fn as_ref(&self) -> &AppContext {
3327        self
3328    }
3329}
3330
3331impl<V: View> Deref for RenderContext<'_, V> {
3332    type Target = MutableAppContext;
3333
3334    fn deref(&self) -> &Self::Target {
3335        self.app
3336    }
3337}
3338
3339impl<V: View> DerefMut for RenderContext<'_, V> {
3340    fn deref_mut(&mut self) -> &mut Self::Target {
3341        self.app
3342    }
3343}
3344
3345impl<V: View> ReadModel for RenderContext<'_, V> {
3346    fn read_model<T: Entity>(&self, handle: &ModelHandle<T>) -> &T {
3347        self.app.read_model(handle)
3348    }
3349}
3350
3351impl<V: View> UpdateModel for RenderContext<'_, V> {
3352    fn update_model<T: Entity, O>(
3353        &mut self,
3354        handle: &ModelHandle<T>,
3355        update: &mut dyn FnMut(&mut T, &mut ModelContext<T>) -> O,
3356    ) -> O {
3357        self.app.update_model(handle, update)
3358    }
3359}
3360
3361impl<V: View> ReadView for RenderContext<'_, V> {
3362    fn read_view<T: View>(&self, handle: &ViewHandle<T>) -> &T {
3363        self.app.read_view(handle)
3364    }
3365}
3366
3367impl<V: View> ElementStateContext for RenderContext<'_, V> {
3368    fn current_view_id(&self) -> usize {
3369        self.view_id
3370    }
3371}
3372
3373impl<M> AsRef<AppContext> for ViewContext<'_, M> {
3374    fn as_ref(&self) -> &AppContext {
3375        &self.app.cx
3376    }
3377}
3378
3379impl<M> Deref for ViewContext<'_, M> {
3380    type Target = MutableAppContext;
3381
3382    fn deref(&self) -> &Self::Target {
3383        &self.app
3384    }
3385}
3386
3387impl<M> DerefMut for ViewContext<'_, M> {
3388    fn deref_mut(&mut self) -> &mut Self::Target {
3389        &mut self.app
3390    }
3391}
3392
3393impl<M> AsMut<MutableAppContext> for ViewContext<'_, M> {
3394    fn as_mut(&mut self) -> &mut MutableAppContext {
3395        self.app
3396    }
3397}
3398
3399impl<V> ReadModel for ViewContext<'_, V> {
3400    fn read_model<T: Entity>(&self, handle: &ModelHandle<T>) -> &T {
3401        self.app.read_model(handle)
3402    }
3403}
3404
3405impl<V> UpgradeModelHandle for ViewContext<'_, V> {
3406    fn upgrade_model_handle<T: Entity>(
3407        &self,
3408        handle: &WeakModelHandle<T>,
3409    ) -> Option<ModelHandle<T>> {
3410        self.cx.upgrade_model_handle(handle)
3411    }
3412
3413    fn model_handle_is_upgradable<T: Entity>(&self, handle: &WeakModelHandle<T>) -> bool {
3414        self.cx.model_handle_is_upgradable(handle)
3415    }
3416
3417    fn upgrade_any_model_handle(&self, handle: &AnyWeakModelHandle) -> Option<AnyModelHandle> {
3418        self.cx.upgrade_any_model_handle(handle)
3419    }
3420}
3421
3422impl<V> UpgradeViewHandle for ViewContext<'_, V> {
3423    fn upgrade_view_handle<T: View>(&self, handle: &WeakViewHandle<T>) -> Option<ViewHandle<T>> {
3424        self.cx.upgrade_view_handle(handle)
3425    }
3426
3427    fn upgrade_any_view_handle(&self, handle: &AnyWeakViewHandle) -> Option<AnyViewHandle> {
3428        self.cx.upgrade_any_view_handle(handle)
3429    }
3430}
3431
3432impl<V: View> UpdateModel for ViewContext<'_, V> {
3433    fn update_model<T: Entity, O>(
3434        &mut self,
3435        handle: &ModelHandle<T>,
3436        update: &mut dyn FnMut(&mut T, &mut ModelContext<T>) -> O,
3437    ) -> O {
3438        self.app.update_model(handle, update)
3439    }
3440}
3441
3442impl<V: View> ReadView for ViewContext<'_, V> {
3443    fn read_view<T: View>(&self, handle: &ViewHandle<T>) -> &T {
3444        self.app.read_view(handle)
3445    }
3446}
3447
3448impl<V: View> UpdateView for ViewContext<'_, V> {
3449    fn update_view<T, S>(
3450        &mut self,
3451        handle: &ViewHandle<T>,
3452        update: &mut dyn FnMut(&mut T, &mut ViewContext<T>) -> S,
3453    ) -> S
3454    where
3455        T: View,
3456    {
3457        self.app.update_view(handle, update)
3458    }
3459}
3460
3461impl<V: View> ElementStateContext for ViewContext<'_, V> {
3462    fn current_view_id(&self) -> usize {
3463        self.view_id
3464    }
3465}
3466
3467pub trait Handle<T> {
3468    type Weak: 'static;
3469    fn id(&self) -> usize;
3470    fn location(&self) -> EntityLocation;
3471    fn downgrade(&self) -> Self::Weak;
3472    fn upgrade_from(weak: &Self::Weak, cx: &AppContext) -> Option<Self>
3473    where
3474        Self: Sized;
3475}
3476
3477pub trait WeakHandle {
3478    fn id(&self) -> usize;
3479}
3480
3481#[derive(Clone, Copy, Debug, Eq, PartialEq, Hash)]
3482pub enum EntityLocation {
3483    Model(usize),
3484    View(usize, usize),
3485}
3486
3487pub struct ModelHandle<T: Entity> {
3488    model_id: usize,
3489    model_type: PhantomData<T>,
3490    ref_counts: Arc<Mutex<RefCounts>>,
3491
3492    #[cfg(any(test, feature = "test-support"))]
3493    handle_id: usize,
3494}
3495
3496impl<T: Entity> ModelHandle<T> {
3497    fn new(model_id: usize, ref_counts: &Arc<Mutex<RefCounts>>) -> Self {
3498        ref_counts.lock().inc_model(model_id);
3499
3500        #[cfg(any(test, feature = "test-support"))]
3501        let handle_id = ref_counts
3502            .lock()
3503            .leak_detector
3504            .lock()
3505            .handle_created(Some(type_name::<T>()), model_id);
3506
3507        Self {
3508            model_id,
3509            model_type: PhantomData,
3510            ref_counts: ref_counts.clone(),
3511
3512            #[cfg(any(test, feature = "test-support"))]
3513            handle_id,
3514        }
3515    }
3516
3517    pub fn downgrade(&self) -> WeakModelHandle<T> {
3518        WeakModelHandle::new(self.model_id)
3519    }
3520
3521    pub fn id(&self) -> usize {
3522        self.model_id
3523    }
3524
3525    pub fn read<'a, C: ReadModel>(&self, cx: &'a C) -> &'a T {
3526        cx.read_model(self)
3527    }
3528
3529    pub fn read_with<'a, C, F, S>(&self, cx: &C, read: F) -> S
3530    where
3531        C: ReadModelWith,
3532        F: FnOnce(&T, &AppContext) -> S,
3533    {
3534        let mut read = Some(read);
3535        cx.read_model_with(self, &mut |model, cx| {
3536            let read = read.take().unwrap();
3537            read(model, cx)
3538        })
3539    }
3540
3541    pub fn update<C, F, S>(&self, cx: &mut C, update: F) -> S
3542    where
3543        C: UpdateModel,
3544        F: FnOnce(&mut T, &mut ModelContext<T>) -> S,
3545    {
3546        let mut update = Some(update);
3547        cx.update_model(self, &mut |model, cx| {
3548            let update = update.take().unwrap();
3549            update(model, cx)
3550        })
3551    }
3552
3553    #[cfg(any(test, feature = "test-support"))]
3554    pub fn next_notification(&self, cx: &TestAppContext) -> impl Future<Output = ()> {
3555        let (tx, mut rx) = futures::channel::mpsc::unbounded();
3556        let mut cx = cx.cx.borrow_mut();
3557        let subscription = cx.observe(self, move |_, _| {
3558            tx.unbounded_send(()).ok();
3559        });
3560
3561        let duration = if std::env::var("CI").is_ok() {
3562            Duration::from_secs(5)
3563        } else {
3564            Duration::from_secs(1)
3565        };
3566
3567        async move {
3568            let notification = crate::util::timeout(duration, rx.next())
3569                .await
3570                .expect("next notification timed out");
3571            drop(subscription);
3572            notification.expect("model dropped while test was waiting for its next notification")
3573        }
3574    }
3575
3576    #[cfg(any(test, feature = "test-support"))]
3577    pub fn next_event(&self, cx: &TestAppContext) -> impl Future<Output = T::Event>
3578    where
3579        T::Event: Clone,
3580    {
3581        let (tx, mut rx) = futures::channel::mpsc::unbounded();
3582        let mut cx = cx.cx.borrow_mut();
3583        let subscription = cx.subscribe(self, move |_, event, _| {
3584            tx.unbounded_send(event.clone()).ok();
3585        });
3586
3587        let duration = if std::env::var("CI").is_ok() {
3588            Duration::from_secs(5)
3589        } else {
3590            Duration::from_secs(1)
3591        };
3592
3593        cx.foreground.start_waiting();
3594        async move {
3595            let event = crate::util::timeout(duration, rx.next())
3596                .await
3597                .expect("next event timed out");
3598            drop(subscription);
3599            event.expect("model dropped while test was waiting for its next event")
3600        }
3601    }
3602
3603    #[cfg(any(test, feature = "test-support"))]
3604    pub fn condition(
3605        &self,
3606        cx: &TestAppContext,
3607        mut predicate: impl FnMut(&T, &AppContext) -> bool,
3608    ) -> impl Future<Output = ()> {
3609        let (tx, mut rx) = futures::channel::mpsc::unbounded();
3610
3611        let mut cx = cx.cx.borrow_mut();
3612        let subscriptions = (
3613            cx.observe(self, {
3614                let tx = tx.clone();
3615                move |_, _| {
3616                    tx.unbounded_send(()).ok();
3617                }
3618            }),
3619            cx.subscribe(self, {
3620                let tx = tx.clone();
3621                move |_, _, _| {
3622                    tx.unbounded_send(()).ok();
3623                }
3624            }),
3625        );
3626
3627        let cx = cx.weak_self.as_ref().unwrap().upgrade().unwrap();
3628        let handle = self.downgrade();
3629        let duration = if std::env::var("CI").is_ok() {
3630            Duration::from_secs(5)
3631        } else {
3632            Duration::from_secs(1)
3633        };
3634
3635        async move {
3636            crate::util::timeout(duration, async move {
3637                loop {
3638                    {
3639                        let cx = cx.borrow();
3640                        let cx = cx.as_ref();
3641                        if predicate(
3642                            handle
3643                                .upgrade(cx)
3644                                .expect("model dropped with pending condition")
3645                                .read(cx),
3646                            cx,
3647                        ) {
3648                            break;
3649                        }
3650                    }
3651
3652                    cx.borrow().foreground().start_waiting();
3653                    rx.next()
3654                        .await
3655                        .expect("model dropped with pending condition");
3656                    cx.borrow().foreground().finish_waiting();
3657                }
3658            })
3659            .await
3660            .expect("condition timed out");
3661            drop(subscriptions);
3662        }
3663    }
3664}
3665
3666impl<T: Entity> Clone for ModelHandle<T> {
3667    fn clone(&self) -> Self {
3668        Self::new(self.model_id, &self.ref_counts)
3669    }
3670}
3671
3672impl<T: Entity> PartialEq for ModelHandle<T> {
3673    fn eq(&self, other: &Self) -> bool {
3674        self.model_id == other.model_id
3675    }
3676}
3677
3678impl<T: Entity> Eq for ModelHandle<T> {}
3679
3680impl<T: Entity> PartialEq<WeakModelHandle<T>> for ModelHandle<T> {
3681    fn eq(&self, other: &WeakModelHandle<T>) -> bool {
3682        self.model_id == other.model_id
3683    }
3684}
3685
3686impl<T: Entity> Hash for ModelHandle<T> {
3687    fn hash<H: Hasher>(&self, state: &mut H) {
3688        self.model_id.hash(state);
3689    }
3690}
3691
3692impl<T: Entity> std::borrow::Borrow<usize> for ModelHandle<T> {
3693    fn borrow(&self) -> &usize {
3694        &self.model_id
3695    }
3696}
3697
3698impl<T: Entity> Debug for ModelHandle<T> {
3699    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
3700        f.debug_tuple(&format!("ModelHandle<{}>", type_name::<T>()))
3701            .field(&self.model_id)
3702            .finish()
3703    }
3704}
3705
3706unsafe impl<T: Entity> Send for ModelHandle<T> {}
3707unsafe impl<T: Entity> Sync for ModelHandle<T> {}
3708
3709impl<T: Entity> Drop for ModelHandle<T> {
3710    fn drop(&mut self) {
3711        let mut ref_counts = self.ref_counts.lock();
3712        ref_counts.dec_model(self.model_id);
3713
3714        #[cfg(any(test, feature = "test-support"))]
3715        ref_counts
3716            .leak_detector
3717            .lock()
3718            .handle_dropped(self.model_id, self.handle_id);
3719    }
3720}
3721
3722impl<T: Entity> Handle<T> for ModelHandle<T> {
3723    type Weak = WeakModelHandle<T>;
3724
3725    fn id(&self) -> usize {
3726        self.model_id
3727    }
3728
3729    fn location(&self) -> EntityLocation {
3730        EntityLocation::Model(self.model_id)
3731    }
3732
3733    fn downgrade(&self) -> Self::Weak {
3734        self.downgrade()
3735    }
3736
3737    fn upgrade_from(weak: &Self::Weak, cx: &AppContext) -> Option<Self>
3738    where
3739        Self: Sized,
3740    {
3741        weak.upgrade(cx)
3742    }
3743}
3744
3745pub struct WeakModelHandle<T> {
3746    model_id: usize,
3747    model_type: PhantomData<T>,
3748}
3749
3750impl<T> WeakHandle for WeakModelHandle<T> {
3751    fn id(&self) -> usize {
3752        self.model_id
3753    }
3754}
3755
3756unsafe impl<T> Send for WeakModelHandle<T> {}
3757unsafe impl<T> Sync for WeakModelHandle<T> {}
3758
3759impl<T: Entity> WeakModelHandle<T> {
3760    fn new(model_id: usize) -> Self {
3761        Self {
3762            model_id,
3763            model_type: PhantomData,
3764        }
3765    }
3766
3767    pub fn id(&self) -> usize {
3768        self.model_id
3769    }
3770
3771    pub fn is_upgradable(&self, cx: &impl UpgradeModelHandle) -> bool {
3772        cx.model_handle_is_upgradable(self)
3773    }
3774
3775    pub fn upgrade(&self, cx: &impl UpgradeModelHandle) -> Option<ModelHandle<T>> {
3776        cx.upgrade_model_handle(self)
3777    }
3778}
3779
3780impl<T> Hash for WeakModelHandle<T> {
3781    fn hash<H: Hasher>(&self, state: &mut H) {
3782        self.model_id.hash(state)
3783    }
3784}
3785
3786impl<T> PartialEq for WeakModelHandle<T> {
3787    fn eq(&self, other: &Self) -> bool {
3788        self.model_id == other.model_id
3789    }
3790}
3791
3792impl<T> Eq for WeakModelHandle<T> {}
3793
3794impl<T> Clone for WeakModelHandle<T> {
3795    fn clone(&self) -> Self {
3796        Self {
3797            model_id: self.model_id,
3798            model_type: PhantomData,
3799        }
3800    }
3801}
3802
3803impl<T> Copy for WeakModelHandle<T> {}
3804
3805pub struct ViewHandle<T> {
3806    window_id: usize,
3807    view_id: usize,
3808    view_type: PhantomData<T>,
3809    ref_counts: Arc<Mutex<RefCounts>>,
3810    #[cfg(any(test, feature = "test-support"))]
3811    handle_id: usize,
3812}
3813
3814impl<T: View> ViewHandle<T> {
3815    fn new(window_id: usize, view_id: usize, ref_counts: &Arc<Mutex<RefCounts>>) -> Self {
3816        ref_counts.lock().inc_view(window_id, view_id);
3817        #[cfg(any(test, feature = "test-support"))]
3818        let handle_id = ref_counts
3819            .lock()
3820            .leak_detector
3821            .lock()
3822            .handle_created(Some(type_name::<T>()), view_id);
3823
3824        Self {
3825            window_id,
3826            view_id,
3827            view_type: PhantomData,
3828            ref_counts: ref_counts.clone(),
3829
3830            #[cfg(any(test, feature = "test-support"))]
3831            handle_id,
3832        }
3833    }
3834
3835    pub fn downgrade(&self) -> WeakViewHandle<T> {
3836        WeakViewHandle::new(self.window_id, self.view_id)
3837    }
3838
3839    pub fn window_id(&self) -> usize {
3840        self.window_id
3841    }
3842
3843    pub fn id(&self) -> usize {
3844        self.view_id
3845    }
3846
3847    pub fn read<'a, C: ReadView>(&self, cx: &'a C) -> &'a T {
3848        cx.read_view(self)
3849    }
3850
3851    pub fn read_with<C, F, S>(&self, cx: &C, read: F) -> S
3852    where
3853        C: ReadViewWith,
3854        F: FnOnce(&T, &AppContext) -> S,
3855    {
3856        let mut read = Some(read);
3857        cx.read_view_with(self, &mut |view, cx| {
3858            let read = read.take().unwrap();
3859            read(view, cx)
3860        })
3861    }
3862
3863    pub fn update<C, F, S>(&self, cx: &mut C, update: F) -> S
3864    where
3865        C: UpdateView,
3866        F: FnOnce(&mut T, &mut ViewContext<T>) -> S,
3867    {
3868        let mut update = Some(update);
3869        cx.update_view(self, &mut |view, cx| {
3870            let update = update.take().unwrap();
3871            update(view, cx)
3872        })
3873    }
3874
3875    pub fn defer<C, F>(&self, cx: &mut C, update: F)
3876    where
3877        C: AsMut<MutableAppContext>,
3878        F: 'static + FnOnce(&mut T, &mut ViewContext<T>),
3879    {
3880        let this = self.clone();
3881        cx.as_mut().defer(move |cx| {
3882            this.update(cx, |view, cx| update(view, cx));
3883        });
3884    }
3885
3886    pub fn is_focused(&self, cx: &AppContext) -> bool {
3887        cx.focused_view_id(self.window_id)
3888            .map_or(false, |focused_id| focused_id == self.view_id)
3889    }
3890
3891    #[cfg(any(test, feature = "test-support"))]
3892    pub fn next_notification(&self, cx: &TestAppContext) -> impl Future<Output = ()> {
3893        use postage::prelude::{Sink as _, Stream as _};
3894
3895        let (mut tx, mut rx) = postage::mpsc::channel(1);
3896        let mut cx = cx.cx.borrow_mut();
3897        let subscription = cx.observe(self, move |_, _| {
3898            tx.try_send(()).ok();
3899        });
3900
3901        let duration = if std::env::var("CI").is_ok() {
3902            Duration::from_secs(5)
3903        } else {
3904            Duration::from_secs(1)
3905        };
3906
3907        async move {
3908            let notification = crate::util::timeout(duration, rx.recv())
3909                .await
3910                .expect("next notification timed out");
3911            drop(subscription);
3912            notification.expect("model dropped while test was waiting for its next notification")
3913        }
3914    }
3915
3916    #[cfg(any(test, feature = "test-support"))]
3917    pub fn condition(
3918        &self,
3919        cx: &TestAppContext,
3920        mut predicate: impl FnMut(&T, &AppContext) -> bool,
3921    ) -> impl Future<Output = ()> {
3922        use postage::prelude::{Sink as _, Stream as _};
3923
3924        let (tx, mut rx) = postage::mpsc::channel(1024);
3925
3926        let mut cx = cx.cx.borrow_mut();
3927        let subscriptions = self.update(&mut *cx, |_, cx| {
3928            (
3929                cx.observe(self, {
3930                    let mut tx = tx.clone();
3931                    move |_, _, _| {
3932                        tx.blocking_send(()).ok();
3933                    }
3934                }),
3935                cx.subscribe(self, {
3936                    let mut tx = tx.clone();
3937                    move |_, _, _, _| {
3938                        tx.blocking_send(()).ok();
3939                    }
3940                }),
3941            )
3942        });
3943
3944        let cx = cx.weak_self.as_ref().unwrap().upgrade().unwrap();
3945        let handle = self.downgrade();
3946        let duration = if std::env::var("CI").is_ok() {
3947            Duration::from_secs(2)
3948        } else {
3949            Duration::from_millis(500)
3950        };
3951
3952        async move {
3953            crate::util::timeout(duration, async move {
3954                loop {
3955                    {
3956                        let cx = cx.borrow();
3957                        let cx = cx.as_ref();
3958                        if predicate(
3959                            handle
3960                                .upgrade(cx)
3961                                .expect("view dropped with pending condition")
3962                                .read(cx),
3963                            cx,
3964                        ) {
3965                            break;
3966                        }
3967                    }
3968
3969                    cx.borrow().foreground().start_waiting();
3970                    rx.recv()
3971                        .await
3972                        .expect("view dropped with pending condition");
3973                    cx.borrow().foreground().finish_waiting();
3974                }
3975            })
3976            .await
3977            .expect("condition timed out");
3978            drop(subscriptions);
3979        }
3980    }
3981}
3982
3983impl<T: View> Clone for ViewHandle<T> {
3984    fn clone(&self) -> Self {
3985        ViewHandle::new(self.window_id, self.view_id, &self.ref_counts)
3986    }
3987}
3988
3989impl<T> PartialEq for ViewHandle<T> {
3990    fn eq(&self, other: &Self) -> bool {
3991        self.window_id == other.window_id && self.view_id == other.view_id
3992    }
3993}
3994
3995impl<T> PartialEq<WeakViewHandle<T>> for ViewHandle<T> {
3996    fn eq(&self, other: &WeakViewHandle<T>) -> bool {
3997        self.window_id == other.window_id && self.view_id == other.view_id
3998    }
3999}
4000
4001impl<T> PartialEq<ViewHandle<T>> for WeakViewHandle<T> {
4002    fn eq(&self, other: &ViewHandle<T>) -> bool {
4003        self.window_id == other.window_id && self.view_id == other.view_id
4004    }
4005}
4006
4007impl<T> Eq for ViewHandle<T> {}
4008
4009impl<T> Hash for ViewHandle<T> {
4010    fn hash<H: Hasher>(&self, state: &mut H) {
4011        self.window_id.hash(state);
4012        self.view_id.hash(state);
4013    }
4014}
4015
4016impl<T> Debug for ViewHandle<T> {
4017    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
4018        f.debug_struct(&format!("ViewHandle<{}>", type_name::<T>()))
4019            .field("window_id", &self.window_id)
4020            .field("view_id", &self.view_id)
4021            .finish()
4022    }
4023}
4024
4025impl<T> Drop for ViewHandle<T> {
4026    fn drop(&mut self) {
4027        self.ref_counts
4028            .lock()
4029            .dec_view(self.window_id, self.view_id);
4030        #[cfg(any(test, feature = "test-support"))]
4031        self.ref_counts
4032            .lock()
4033            .leak_detector
4034            .lock()
4035            .handle_dropped(self.view_id, self.handle_id);
4036    }
4037}
4038
4039impl<T: View> Handle<T> for ViewHandle<T> {
4040    type Weak = WeakViewHandle<T>;
4041
4042    fn id(&self) -> usize {
4043        self.view_id
4044    }
4045
4046    fn location(&self) -> EntityLocation {
4047        EntityLocation::View(self.window_id, self.view_id)
4048    }
4049
4050    fn downgrade(&self) -> Self::Weak {
4051        self.downgrade()
4052    }
4053
4054    fn upgrade_from(weak: &Self::Weak, cx: &AppContext) -> Option<Self>
4055    where
4056        Self: Sized,
4057    {
4058        weak.upgrade(cx)
4059    }
4060}
4061
4062pub struct AnyViewHandle {
4063    window_id: usize,
4064    view_id: usize,
4065    view_type: TypeId,
4066    ref_counts: Arc<Mutex<RefCounts>>,
4067
4068    #[cfg(any(test, feature = "test-support"))]
4069    handle_id: usize,
4070}
4071
4072impl AnyViewHandle {
4073    fn new(
4074        window_id: usize,
4075        view_id: usize,
4076        view_type: TypeId,
4077        ref_counts: Arc<Mutex<RefCounts>>,
4078    ) -> Self {
4079        ref_counts.lock().inc_view(window_id, view_id);
4080
4081        #[cfg(any(test, feature = "test-support"))]
4082        let handle_id = ref_counts
4083            .lock()
4084            .leak_detector
4085            .lock()
4086            .handle_created(None, view_id);
4087
4088        Self {
4089            window_id,
4090            view_id,
4091            view_type,
4092            ref_counts,
4093            #[cfg(any(test, feature = "test-support"))]
4094            handle_id,
4095        }
4096    }
4097
4098    pub fn id(&self) -> usize {
4099        self.view_id
4100    }
4101
4102    pub fn is<T: 'static>(&self) -> bool {
4103        TypeId::of::<T>() == self.view_type
4104    }
4105
4106    pub fn is_focused(&self, cx: &AppContext) -> bool {
4107        cx.focused_view_id(self.window_id)
4108            .map_or(false, |focused_id| focused_id == self.view_id)
4109    }
4110
4111    pub fn downcast<T: View>(self) -> Option<ViewHandle<T>> {
4112        if self.is::<T>() {
4113            let result = Some(ViewHandle {
4114                window_id: self.window_id,
4115                view_id: self.view_id,
4116                ref_counts: self.ref_counts.clone(),
4117                view_type: PhantomData,
4118                #[cfg(any(test, feature = "test-support"))]
4119                handle_id: self.handle_id,
4120            });
4121            unsafe {
4122                Arc::decrement_strong_count(&self.ref_counts);
4123            }
4124            std::mem::forget(self);
4125            result
4126        } else {
4127            None
4128        }
4129    }
4130
4131    pub fn downgrade(&self) -> AnyWeakViewHandle {
4132        AnyWeakViewHandle {
4133            window_id: self.window_id,
4134            view_id: self.view_id,
4135            view_type: self.view_type,
4136        }
4137    }
4138
4139    pub fn view_type(&self) -> TypeId {
4140        self.view_type
4141    }
4142
4143    pub fn debug_json(&self, cx: &AppContext) -> serde_json::Value {
4144        cx.views
4145            .get(&(self.window_id, self.view_id))
4146            .map_or_else(|| serde_json::Value::Null, |view| view.debug_json(cx))
4147    }
4148}
4149
4150impl Clone for AnyViewHandle {
4151    fn clone(&self) -> Self {
4152        Self::new(
4153            self.window_id,
4154            self.view_id,
4155            self.view_type,
4156            self.ref_counts.clone(),
4157        )
4158    }
4159}
4160
4161impl From<&AnyViewHandle> for AnyViewHandle {
4162    fn from(handle: &AnyViewHandle) -> Self {
4163        handle.clone()
4164    }
4165}
4166
4167impl<T: View> From<&ViewHandle<T>> for AnyViewHandle {
4168    fn from(handle: &ViewHandle<T>) -> Self {
4169        Self::new(
4170            handle.window_id,
4171            handle.view_id,
4172            TypeId::of::<T>(),
4173            handle.ref_counts.clone(),
4174        )
4175    }
4176}
4177
4178impl<T: View> From<ViewHandle<T>> for AnyViewHandle {
4179    fn from(handle: ViewHandle<T>) -> Self {
4180        let any_handle = AnyViewHandle {
4181            window_id: handle.window_id,
4182            view_id: handle.view_id,
4183            view_type: TypeId::of::<T>(),
4184            ref_counts: handle.ref_counts.clone(),
4185            #[cfg(any(test, feature = "test-support"))]
4186            handle_id: handle.handle_id,
4187        };
4188        unsafe {
4189            Arc::decrement_strong_count(&handle.ref_counts);
4190        }
4191        std::mem::forget(handle);
4192        any_handle
4193    }
4194}
4195
4196impl Drop for AnyViewHandle {
4197    fn drop(&mut self) {
4198        self.ref_counts
4199            .lock()
4200            .dec_view(self.window_id, self.view_id);
4201        #[cfg(any(test, feature = "test-support"))]
4202        self.ref_counts
4203            .lock()
4204            .leak_detector
4205            .lock()
4206            .handle_dropped(self.view_id, self.handle_id);
4207    }
4208}
4209
4210pub struct AnyModelHandle {
4211    model_id: usize,
4212    model_type: TypeId,
4213    ref_counts: Arc<Mutex<RefCounts>>,
4214
4215    #[cfg(any(test, feature = "test-support"))]
4216    handle_id: usize,
4217}
4218
4219impl AnyModelHandle {
4220    fn new(model_id: usize, model_type: TypeId, ref_counts: Arc<Mutex<RefCounts>>) -> Self {
4221        ref_counts.lock().inc_model(model_id);
4222
4223        #[cfg(any(test, feature = "test-support"))]
4224        let handle_id = ref_counts
4225            .lock()
4226            .leak_detector
4227            .lock()
4228            .handle_created(None, model_id);
4229
4230        Self {
4231            model_id,
4232            model_type,
4233            ref_counts,
4234
4235            #[cfg(any(test, feature = "test-support"))]
4236            handle_id,
4237        }
4238    }
4239
4240    pub fn downcast<T: Entity>(self) -> Option<ModelHandle<T>> {
4241        if self.is::<T>() {
4242            let result = Some(ModelHandle {
4243                model_id: self.model_id,
4244                model_type: PhantomData,
4245                ref_counts: self.ref_counts.clone(),
4246
4247                #[cfg(any(test, feature = "test-support"))]
4248                handle_id: self.handle_id,
4249            });
4250            unsafe {
4251                Arc::decrement_strong_count(&self.ref_counts);
4252            }
4253            std::mem::forget(self);
4254            result
4255        } else {
4256            None
4257        }
4258    }
4259
4260    pub fn downgrade(&self) -> AnyWeakModelHandle {
4261        AnyWeakModelHandle {
4262            model_id: self.model_id,
4263            model_type: self.model_type,
4264        }
4265    }
4266
4267    pub fn is<T: Entity>(&self) -> bool {
4268        self.model_type == TypeId::of::<T>()
4269    }
4270
4271    pub fn model_type(&self) -> TypeId {
4272        self.model_type
4273    }
4274}
4275
4276impl<T: Entity> From<ModelHandle<T>> for AnyModelHandle {
4277    fn from(handle: ModelHandle<T>) -> Self {
4278        Self::new(
4279            handle.model_id,
4280            TypeId::of::<T>(),
4281            handle.ref_counts.clone(),
4282        )
4283    }
4284}
4285
4286impl Clone for AnyModelHandle {
4287    fn clone(&self) -> Self {
4288        Self::new(self.model_id, self.model_type, self.ref_counts.clone())
4289    }
4290}
4291
4292impl Drop for AnyModelHandle {
4293    fn drop(&mut self) {
4294        let mut ref_counts = self.ref_counts.lock();
4295        ref_counts.dec_model(self.model_id);
4296
4297        #[cfg(any(test, feature = "test-support"))]
4298        ref_counts
4299            .leak_detector
4300            .lock()
4301            .handle_dropped(self.model_id, self.handle_id);
4302    }
4303}
4304
4305pub struct AnyWeakModelHandle {
4306    model_id: usize,
4307    model_type: TypeId,
4308}
4309
4310impl AnyWeakModelHandle {
4311    pub fn upgrade(&self, cx: &impl UpgradeModelHandle) -> Option<AnyModelHandle> {
4312        cx.upgrade_any_model_handle(self)
4313    }
4314}
4315
4316impl<T: Entity> From<WeakModelHandle<T>> for AnyWeakModelHandle {
4317    fn from(handle: WeakModelHandle<T>) -> Self {
4318        AnyWeakModelHandle {
4319            model_id: handle.model_id,
4320            model_type: TypeId::of::<T>(),
4321        }
4322    }
4323}
4324
4325pub struct WeakViewHandle<T> {
4326    window_id: usize,
4327    view_id: usize,
4328    view_type: PhantomData<T>,
4329}
4330
4331impl<T> WeakHandle for WeakViewHandle<T> {
4332    fn id(&self) -> usize {
4333        self.view_id
4334    }
4335}
4336
4337impl<T: View> WeakViewHandle<T> {
4338    fn new(window_id: usize, view_id: usize) -> Self {
4339        Self {
4340            window_id,
4341            view_id,
4342            view_type: PhantomData,
4343        }
4344    }
4345
4346    pub fn id(&self) -> usize {
4347        self.view_id
4348    }
4349
4350    pub fn upgrade(&self, cx: &impl UpgradeViewHandle) -> Option<ViewHandle<T>> {
4351        cx.upgrade_view_handle(self)
4352    }
4353}
4354
4355impl<T> Clone for WeakViewHandle<T> {
4356    fn clone(&self) -> Self {
4357        Self {
4358            window_id: self.window_id,
4359            view_id: self.view_id,
4360            view_type: PhantomData,
4361        }
4362    }
4363}
4364
4365impl<T> PartialEq for WeakViewHandle<T> {
4366    fn eq(&self, other: &Self) -> bool {
4367        self.window_id == other.window_id && self.view_id == other.view_id
4368    }
4369}
4370
4371impl<T> Eq for WeakViewHandle<T> {}
4372
4373impl<T> Hash for WeakViewHandle<T> {
4374    fn hash<H: Hasher>(&self, state: &mut H) {
4375        self.window_id.hash(state);
4376        self.view_id.hash(state);
4377    }
4378}
4379
4380pub struct AnyWeakViewHandle {
4381    window_id: usize,
4382    view_id: usize,
4383    view_type: TypeId,
4384}
4385
4386impl AnyWeakViewHandle {
4387    pub fn upgrade(&self, cx: &impl UpgradeViewHandle) -> Option<AnyViewHandle> {
4388        cx.upgrade_any_view_handle(self)
4389    }
4390}
4391
4392impl<T: View> From<WeakViewHandle<T>> for AnyWeakViewHandle {
4393    fn from(handle: WeakViewHandle<T>) -> Self {
4394        AnyWeakViewHandle {
4395            window_id: handle.window_id,
4396            view_id: handle.view_id,
4397            view_type: TypeId::of::<T>(),
4398        }
4399    }
4400}
4401
4402#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
4403pub struct ElementStateId {
4404    view_id: usize,
4405    element_id: usize,
4406    tag: TypeId,
4407}
4408
4409pub struct ElementStateHandle<T> {
4410    value_type: PhantomData<T>,
4411    id: ElementStateId,
4412    ref_counts: Weak<Mutex<RefCounts>>,
4413}
4414
4415impl<T: 'static> ElementStateHandle<T> {
4416    fn new(id: ElementStateId, frame_id: usize, ref_counts: &Arc<Mutex<RefCounts>>) -> Self {
4417        ref_counts.lock().inc_element_state(id, frame_id);
4418        Self {
4419            value_type: PhantomData,
4420            id,
4421            ref_counts: Arc::downgrade(ref_counts),
4422        }
4423    }
4424
4425    pub fn read<'a>(&self, cx: &'a AppContext) -> &'a T {
4426        cx.element_states
4427            .get(&self.id)
4428            .unwrap()
4429            .downcast_ref()
4430            .unwrap()
4431    }
4432
4433    pub fn update<C, R>(&self, cx: &mut C, f: impl FnOnce(&mut T, &mut C) -> R) -> R
4434    where
4435        C: DerefMut<Target = MutableAppContext>,
4436    {
4437        let mut element_state = cx.deref_mut().cx.element_states.remove(&self.id).unwrap();
4438        let result = f(element_state.downcast_mut().unwrap(), cx);
4439        cx.deref_mut()
4440            .cx
4441            .element_states
4442            .insert(self.id, element_state);
4443        result
4444    }
4445}
4446
4447impl<T> Drop for ElementStateHandle<T> {
4448    fn drop(&mut self) {
4449        if let Some(ref_counts) = self.ref_counts.upgrade() {
4450            ref_counts.lock().dec_element_state(self.id);
4451        }
4452    }
4453}
4454
4455pub struct CursorStyleHandle {
4456    id: usize,
4457    next_cursor_style_handle_id: Arc<AtomicUsize>,
4458    platform: Arc<dyn Platform>,
4459}
4460
4461impl Drop for CursorStyleHandle {
4462    fn drop(&mut self) {
4463        if self.id + 1 == self.next_cursor_style_handle_id.load(SeqCst) {
4464            self.platform.set_cursor_style(CursorStyle::Arrow);
4465        }
4466    }
4467}
4468
4469#[must_use]
4470pub enum Subscription {
4471    Subscription {
4472        id: usize,
4473        entity_id: usize,
4474        subscriptions:
4475            Option<Weak<Mutex<HashMap<usize, BTreeMap<usize, Option<SubscriptionCallback>>>>>>,
4476    },
4477    GlobalSubscription {
4478        id: usize,
4479        type_id: TypeId,
4480        subscriptions: Option<
4481            Weak<Mutex<HashMap<TypeId, BTreeMap<usize, Option<GlobalSubscriptionCallback>>>>>,
4482        >,
4483    },
4484    Observation {
4485        id: usize,
4486        entity_id: usize,
4487        observations:
4488            Option<Weak<Mutex<HashMap<usize, BTreeMap<usize, Option<ObservationCallback>>>>>>,
4489    },
4490    GlobalObservation {
4491        id: usize,
4492        type_id: TypeId,
4493        observations: Option<
4494            Weak<Mutex<HashMap<TypeId, BTreeMap<usize, Option<GlobalObservationCallback>>>>>,
4495        >,
4496    },
4497    FocusObservation {
4498        id: usize,
4499        view_id: usize,
4500        observations:
4501            Option<Weak<Mutex<HashMap<usize, BTreeMap<usize, Option<FocusObservationCallback>>>>>>,
4502    },
4503    ReleaseObservation {
4504        id: usize,
4505        entity_id: usize,
4506        observations:
4507            Option<Weak<Mutex<HashMap<usize, BTreeMap<usize, ReleaseObservationCallback>>>>>,
4508    },
4509}
4510
4511impl Subscription {
4512    pub fn detach(&mut self) {
4513        match self {
4514            Subscription::Subscription { subscriptions, .. } => {
4515                subscriptions.take();
4516            }
4517            Subscription::GlobalSubscription { subscriptions, .. } => {
4518                subscriptions.take();
4519            }
4520            Subscription::Observation { observations, .. } => {
4521                observations.take();
4522            }
4523            Subscription::GlobalObservation { observations, .. } => {
4524                observations.take();
4525            }
4526            Subscription::ReleaseObservation { observations, .. } => {
4527                observations.take();
4528            }
4529            Subscription::FocusObservation { observations, .. } => {
4530                observations.take();
4531            }
4532        }
4533    }
4534}
4535
4536impl Drop for Subscription {
4537    fn drop(&mut self) {
4538        match self {
4539            Subscription::Subscription {
4540                id,
4541                entity_id,
4542                subscriptions,
4543            } => {
4544                if let Some(subscriptions) = subscriptions.as_ref().and_then(Weak::upgrade) {
4545                    match subscriptions
4546                        .lock()
4547                        .entry(*entity_id)
4548                        .or_default()
4549                        .entry(*id)
4550                    {
4551                        btree_map::Entry::Vacant(entry) => {
4552                            entry.insert(None);
4553                        }
4554                        btree_map::Entry::Occupied(entry) => {
4555                            entry.remove();
4556                        }
4557                    }
4558                }
4559            }
4560            Subscription::GlobalSubscription {
4561                id,
4562                type_id,
4563                subscriptions,
4564            } => {
4565                if let Some(subscriptions) = subscriptions.as_ref().and_then(Weak::upgrade) {
4566                    match subscriptions.lock().entry(*type_id).or_default().entry(*id) {
4567                        btree_map::Entry::Vacant(entry) => {
4568                            entry.insert(None);
4569                        }
4570                        btree_map::Entry::Occupied(entry) => {
4571                            entry.remove();
4572                        }
4573                    }
4574                }
4575            }
4576            Subscription::Observation {
4577                id,
4578                entity_id,
4579                observations,
4580            } => {
4581                if let Some(observations) = observations.as_ref().and_then(Weak::upgrade) {
4582                    match observations
4583                        .lock()
4584                        .entry(*entity_id)
4585                        .or_default()
4586                        .entry(*id)
4587                    {
4588                        btree_map::Entry::Vacant(entry) => {
4589                            entry.insert(None);
4590                        }
4591                        btree_map::Entry::Occupied(entry) => {
4592                            entry.remove();
4593                        }
4594                    }
4595                }
4596            }
4597            Subscription::GlobalObservation {
4598                id,
4599                type_id,
4600                observations,
4601            } => {
4602                if let Some(observations) = observations.as_ref().and_then(Weak::upgrade) {
4603                    match observations.lock().entry(*type_id).or_default().entry(*id) {
4604                        collections::btree_map::Entry::Vacant(entry) => {
4605                            entry.insert(None);
4606                        }
4607                        collections::btree_map::Entry::Occupied(entry) => {
4608                            entry.remove();
4609                        }
4610                    }
4611                }
4612            }
4613            Subscription::ReleaseObservation {
4614                id,
4615                entity_id,
4616                observations,
4617            } => {
4618                if let Some(observations) = observations.as_ref().and_then(Weak::upgrade) {
4619                    if let Some(observations) = observations.lock().get_mut(entity_id) {
4620                        observations.remove(id);
4621                    }
4622                }
4623            }
4624            Subscription::FocusObservation {
4625                id,
4626                view_id,
4627                observations,
4628            } => {
4629                if let Some(observations) = observations.as_ref().and_then(Weak::upgrade) {
4630                    match observations.lock().entry(*view_id).or_default().entry(*id) {
4631                        btree_map::Entry::Vacant(entry) => {
4632                            entry.insert(None);
4633                        }
4634                        btree_map::Entry::Occupied(entry) => {
4635                            entry.remove();
4636                        }
4637                    }
4638                }
4639            }
4640        }
4641    }
4642}
4643
4644lazy_static! {
4645    static ref LEAK_BACKTRACE: bool =
4646        std::env::var("LEAK_BACKTRACE").map_or(false, |b| !b.is_empty());
4647}
4648
4649#[cfg(any(test, feature = "test-support"))]
4650#[derive(Default)]
4651pub struct LeakDetector {
4652    next_handle_id: usize,
4653    handle_backtraces: HashMap<
4654        usize,
4655        (
4656            Option<&'static str>,
4657            HashMap<usize, Option<backtrace::Backtrace>>,
4658        ),
4659    >,
4660}
4661
4662#[cfg(any(test, feature = "test-support"))]
4663impl LeakDetector {
4664    fn handle_created(&mut self, type_name: Option<&'static str>, entity_id: usize) -> usize {
4665        let handle_id = post_inc(&mut self.next_handle_id);
4666        let entry = self.handle_backtraces.entry(entity_id).or_default();
4667        let backtrace = if *LEAK_BACKTRACE {
4668            Some(backtrace::Backtrace::new_unresolved())
4669        } else {
4670            None
4671        };
4672        if let Some(type_name) = type_name {
4673            entry.0.get_or_insert(type_name);
4674        }
4675        entry.1.insert(handle_id, backtrace);
4676        handle_id
4677    }
4678
4679    fn handle_dropped(&mut self, entity_id: usize, handle_id: usize) {
4680        if let Some((_, backtraces)) = self.handle_backtraces.get_mut(&entity_id) {
4681            assert!(backtraces.remove(&handle_id).is_some());
4682            if backtraces.is_empty() {
4683                self.handle_backtraces.remove(&entity_id);
4684            }
4685        }
4686    }
4687
4688    pub fn assert_dropped(&mut self, entity_id: usize) {
4689        if let Some((type_name, backtraces)) = self.handle_backtraces.get_mut(&entity_id) {
4690            for trace in backtraces.values_mut() {
4691                if let Some(trace) = trace {
4692                    trace.resolve();
4693                    eprintln!("{:?}", crate::util::CwdBacktrace(trace));
4694                }
4695            }
4696
4697            let hint = if *LEAK_BACKTRACE {
4698                ""
4699            } else {
4700                " – set LEAK_BACKTRACE=1 for more information"
4701            };
4702
4703            panic!(
4704                "{} handles to {} {} still exist{}",
4705                backtraces.len(),
4706                type_name.unwrap_or("entity"),
4707                entity_id,
4708                hint
4709            );
4710        }
4711    }
4712
4713    pub fn detect(&mut self) {
4714        let mut found_leaks = false;
4715        for (id, (type_name, backtraces)) in self.handle_backtraces.iter_mut() {
4716            eprintln!(
4717                "leaked {} handles to {} {}",
4718                backtraces.len(),
4719                type_name.unwrap_or("entity"),
4720                id
4721            );
4722            for trace in backtraces.values_mut() {
4723                if let Some(trace) = trace {
4724                    trace.resolve();
4725                    eprintln!("{:?}", crate::util::CwdBacktrace(trace));
4726                }
4727            }
4728            found_leaks = true;
4729        }
4730
4731        let hint = if *LEAK_BACKTRACE {
4732            ""
4733        } else {
4734            " – set LEAK_BACKTRACE=1 for more information"
4735        };
4736        assert!(!found_leaks, "detected leaked handles{}", hint);
4737    }
4738}
4739
4740#[derive(Default)]
4741struct RefCounts {
4742    entity_counts: HashMap<usize, usize>,
4743    element_state_counts: HashMap<ElementStateId, ElementStateRefCount>,
4744    dropped_models: HashSet<usize>,
4745    dropped_views: HashSet<(usize, usize)>,
4746    dropped_element_states: HashSet<ElementStateId>,
4747
4748    #[cfg(any(test, feature = "test-support"))]
4749    leak_detector: Arc<Mutex<LeakDetector>>,
4750}
4751
4752struct ElementStateRefCount {
4753    ref_count: usize,
4754    frame_id: usize,
4755}
4756
4757impl RefCounts {
4758    fn inc_model(&mut self, model_id: usize) {
4759        match self.entity_counts.entry(model_id) {
4760            Entry::Occupied(mut entry) => {
4761                *entry.get_mut() += 1;
4762            }
4763            Entry::Vacant(entry) => {
4764                entry.insert(1);
4765                self.dropped_models.remove(&model_id);
4766            }
4767        }
4768    }
4769
4770    fn inc_view(&mut self, window_id: usize, view_id: usize) {
4771        match self.entity_counts.entry(view_id) {
4772            Entry::Occupied(mut entry) => *entry.get_mut() += 1,
4773            Entry::Vacant(entry) => {
4774                entry.insert(1);
4775                self.dropped_views.remove(&(window_id, view_id));
4776            }
4777        }
4778    }
4779
4780    fn inc_element_state(&mut self, id: ElementStateId, frame_id: usize) {
4781        match self.element_state_counts.entry(id) {
4782            Entry::Occupied(mut entry) => {
4783                let entry = entry.get_mut();
4784                if entry.frame_id == frame_id || entry.ref_count >= 2 {
4785                    panic!("used the same element state more than once in the same frame");
4786                }
4787                entry.ref_count += 1;
4788                entry.frame_id = frame_id;
4789            }
4790            Entry::Vacant(entry) => {
4791                entry.insert(ElementStateRefCount {
4792                    ref_count: 1,
4793                    frame_id,
4794                });
4795                self.dropped_element_states.remove(&id);
4796            }
4797        }
4798    }
4799
4800    fn dec_model(&mut self, model_id: usize) {
4801        let count = self.entity_counts.get_mut(&model_id).unwrap();
4802        *count -= 1;
4803        if *count == 0 {
4804            self.entity_counts.remove(&model_id);
4805            self.dropped_models.insert(model_id);
4806        }
4807    }
4808
4809    fn dec_view(&mut self, window_id: usize, view_id: usize) {
4810        let count = self.entity_counts.get_mut(&view_id).unwrap();
4811        *count -= 1;
4812        if *count == 0 {
4813            self.entity_counts.remove(&view_id);
4814            self.dropped_views.insert((window_id, view_id));
4815        }
4816    }
4817
4818    fn dec_element_state(&mut self, id: ElementStateId) {
4819        let entry = self.element_state_counts.get_mut(&id).unwrap();
4820        entry.ref_count -= 1;
4821        if entry.ref_count == 0 {
4822            self.element_state_counts.remove(&id);
4823            self.dropped_element_states.insert(id);
4824        }
4825    }
4826
4827    fn is_entity_alive(&self, entity_id: usize) -> bool {
4828        self.entity_counts.contains_key(&entity_id)
4829    }
4830
4831    fn take_dropped(
4832        &mut self,
4833    ) -> (
4834        HashSet<usize>,
4835        HashSet<(usize, usize)>,
4836        HashSet<ElementStateId>,
4837    ) {
4838        (
4839            std::mem::take(&mut self.dropped_models),
4840            std::mem::take(&mut self.dropped_views),
4841            std::mem::take(&mut self.dropped_element_states),
4842        )
4843    }
4844}
4845
4846#[cfg(test)]
4847mod tests {
4848    use super::*;
4849    use crate::{actions, elements::*, impl_actions};
4850    use serde::Deserialize;
4851    use smol::future::poll_once;
4852    use std::{
4853        cell::Cell,
4854        sync::atomic::{AtomicBool, AtomicUsize, Ordering::SeqCst},
4855    };
4856
4857    #[crate::test(self)]
4858    fn test_model_handles(cx: &mut MutableAppContext) {
4859        struct Model {
4860            other: Option<ModelHandle<Model>>,
4861            events: Vec<String>,
4862        }
4863
4864        impl Entity for Model {
4865            type Event = usize;
4866        }
4867
4868        impl Model {
4869            fn new(other: Option<ModelHandle<Self>>, cx: &mut ModelContext<Self>) -> Self {
4870                if let Some(other) = other.as_ref() {
4871                    cx.observe(other, |me, _, _| {
4872                        me.events.push("notified".into());
4873                    })
4874                    .detach();
4875                    cx.subscribe(other, |me, _, event, _| {
4876                        me.events.push(format!("observed event {}", event));
4877                    })
4878                    .detach();
4879                }
4880
4881                Self {
4882                    other,
4883                    events: Vec::new(),
4884                }
4885            }
4886        }
4887
4888        let handle_1 = cx.add_model(|cx| Model::new(None, cx));
4889        let handle_2 = cx.add_model(|cx| Model::new(Some(handle_1.clone()), cx));
4890        assert_eq!(cx.cx.models.len(), 2);
4891
4892        handle_1.update(cx, |model, cx| {
4893            model.events.push("updated".into());
4894            cx.emit(1);
4895            cx.notify();
4896            cx.emit(2);
4897        });
4898        assert_eq!(handle_1.read(cx).events, vec!["updated".to_string()]);
4899        assert_eq!(
4900            handle_2.read(cx).events,
4901            vec![
4902                "observed event 1".to_string(),
4903                "notified".to_string(),
4904                "observed event 2".to_string(),
4905            ]
4906        );
4907
4908        handle_2.update(cx, |model, _| {
4909            drop(handle_1);
4910            model.other.take();
4911        });
4912
4913        assert_eq!(cx.cx.models.len(), 1);
4914        assert!(cx.subscriptions.lock().is_empty());
4915        assert!(cx.observations.lock().is_empty());
4916    }
4917
4918    #[crate::test(self)]
4919    fn test_model_events(cx: &mut MutableAppContext) {
4920        #[derive(Default)]
4921        struct Model {
4922            events: Vec<usize>,
4923        }
4924
4925        impl Entity for Model {
4926            type Event = usize;
4927        }
4928
4929        let handle_1 = cx.add_model(|_| Model::default());
4930        let handle_2 = cx.add_model(|_| Model::default());
4931
4932        handle_1.update(cx, |_, cx| {
4933            cx.subscribe(&handle_2, move |model: &mut Model, emitter, event, cx| {
4934                model.events.push(*event);
4935
4936                cx.subscribe(&emitter, |model, _, event, _| {
4937                    model.events.push(*event * 2);
4938                })
4939                .detach();
4940            })
4941            .detach();
4942        });
4943
4944        handle_2.update(cx, |_, c| c.emit(7));
4945        assert_eq!(handle_1.read(cx).events, vec![7]);
4946
4947        handle_2.update(cx, |_, c| c.emit(5));
4948        assert_eq!(handle_1.read(cx).events, vec![7, 5, 10]);
4949    }
4950
4951    #[crate::test(self)]
4952    fn test_model_emit_before_subscribe_in_same_update_cycle(cx: &mut MutableAppContext) {
4953        #[derive(Default)]
4954        struct Model;
4955
4956        impl Entity for Model {
4957            type Event = ();
4958        }
4959
4960        let events = Rc::new(RefCell::new(Vec::new()));
4961        cx.add_model(|cx| {
4962            drop(cx.subscribe(&cx.handle(), {
4963                let events = events.clone();
4964                move |_, _, _, _| events.borrow_mut().push("dropped before flush")
4965            }));
4966            cx.subscribe(&cx.handle(), {
4967                let events = events.clone();
4968                move |_, _, _, _| events.borrow_mut().push("before emit")
4969            })
4970            .detach();
4971            cx.emit(());
4972            cx.subscribe(&cx.handle(), {
4973                let events = events.clone();
4974                move |_, _, _, _| events.borrow_mut().push("after emit")
4975            })
4976            .detach();
4977            Model
4978        });
4979        assert_eq!(*events.borrow(), ["before emit"]);
4980    }
4981
4982    #[crate::test(self)]
4983    fn test_observe_and_notify_from_model(cx: &mut MutableAppContext) {
4984        #[derive(Default)]
4985        struct Model {
4986            count: usize,
4987            events: Vec<usize>,
4988        }
4989
4990        impl Entity for Model {
4991            type Event = ();
4992        }
4993
4994        let handle_1 = cx.add_model(|_| Model::default());
4995        let handle_2 = cx.add_model(|_| Model::default());
4996
4997        handle_1.update(cx, |_, c| {
4998            c.observe(&handle_2, move |model, observed, c| {
4999                model.events.push(observed.read(c).count);
5000                c.observe(&observed, |model, observed, c| {
5001                    model.events.push(observed.read(c).count * 2);
5002                })
5003                .detach();
5004            })
5005            .detach();
5006        });
5007
5008        handle_2.update(cx, |model, c| {
5009            model.count = 7;
5010            c.notify()
5011        });
5012        assert_eq!(handle_1.read(cx).events, vec![7]);
5013
5014        handle_2.update(cx, |model, c| {
5015            model.count = 5;
5016            c.notify()
5017        });
5018        assert_eq!(handle_1.read(cx).events, vec![7, 5, 10])
5019    }
5020
5021    #[crate::test(self)]
5022    fn test_model_notify_before_observe_in_same_update_cycle(cx: &mut MutableAppContext) {
5023        #[derive(Default)]
5024        struct Model;
5025
5026        impl Entity for Model {
5027            type Event = ();
5028        }
5029
5030        let events = Rc::new(RefCell::new(Vec::new()));
5031        cx.add_model(|cx| {
5032            drop(cx.observe(&cx.handle(), {
5033                let events = events.clone();
5034                move |_, _, _| events.borrow_mut().push("dropped before flush")
5035            }));
5036            cx.observe(&cx.handle(), {
5037                let events = events.clone();
5038                move |_, _, _| events.borrow_mut().push("before notify")
5039            })
5040            .detach();
5041            cx.notify();
5042            cx.observe(&cx.handle(), {
5043                let events = events.clone();
5044                move |_, _, _| events.borrow_mut().push("after notify")
5045            })
5046            .detach();
5047            Model
5048        });
5049        assert_eq!(*events.borrow(), ["before notify"]);
5050    }
5051
5052    #[crate::test(self)]
5053    fn test_defer_and_after_window_update(cx: &mut MutableAppContext) {
5054        struct View {
5055            render_count: usize,
5056        }
5057
5058        impl Entity for View {
5059            type Event = usize;
5060        }
5061
5062        impl super::View for View {
5063            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5064                post_inc(&mut self.render_count);
5065                Empty::new().boxed()
5066            }
5067
5068            fn ui_name() -> &'static str {
5069                "View"
5070            }
5071        }
5072
5073        let (_, view) = cx.add_window(Default::default(), |_| View { render_count: 0 });
5074        let called_defer = Rc::new(AtomicBool::new(false));
5075        let called_after_window_update = Rc::new(AtomicBool::new(false));
5076
5077        view.update(cx, |this, cx| {
5078            assert_eq!(this.render_count, 1);
5079            cx.defer({
5080                let called_defer = called_defer.clone();
5081                move |this, _| {
5082                    assert_eq!(this.render_count, 1);
5083                    called_defer.store(true, SeqCst);
5084                }
5085            });
5086            cx.after_window_update({
5087                let called_after_window_update = called_after_window_update.clone();
5088                move |this, cx| {
5089                    assert_eq!(this.render_count, 2);
5090                    called_after_window_update.store(true, SeqCst);
5091                    cx.notify();
5092                }
5093            });
5094            assert!(!called_defer.load(SeqCst));
5095            assert!(!called_after_window_update.load(SeqCst));
5096            cx.notify();
5097        });
5098
5099        assert!(called_defer.load(SeqCst));
5100        assert!(called_after_window_update.load(SeqCst));
5101        assert_eq!(view.read(cx).render_count, 3);
5102    }
5103
5104    #[crate::test(self)]
5105    fn test_view_handles(cx: &mut MutableAppContext) {
5106        struct View {
5107            other: Option<ViewHandle<View>>,
5108            events: Vec<String>,
5109        }
5110
5111        impl Entity for View {
5112            type Event = usize;
5113        }
5114
5115        impl super::View for View {
5116            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5117                Empty::new().boxed()
5118            }
5119
5120            fn ui_name() -> &'static str {
5121                "View"
5122            }
5123        }
5124
5125        impl View {
5126            fn new(other: Option<ViewHandle<View>>, cx: &mut ViewContext<Self>) -> Self {
5127                if let Some(other) = other.as_ref() {
5128                    cx.subscribe(other, |me, _, event, _| {
5129                        me.events.push(format!("observed event {}", event));
5130                    })
5131                    .detach();
5132                }
5133                Self {
5134                    other,
5135                    events: Vec::new(),
5136                }
5137            }
5138        }
5139
5140        let (window_id, _) = cx.add_window(Default::default(), |cx| View::new(None, cx));
5141        let handle_1 = cx.add_view(window_id, |cx| View::new(None, cx));
5142        let handle_2 = cx.add_view(window_id, |cx| View::new(Some(handle_1.clone()), cx));
5143        assert_eq!(cx.cx.views.len(), 3);
5144
5145        handle_1.update(cx, |view, cx| {
5146            view.events.push("updated".into());
5147            cx.emit(1);
5148            cx.emit(2);
5149        });
5150        assert_eq!(handle_1.read(cx).events, vec!["updated".to_string()]);
5151        assert_eq!(
5152            handle_2.read(cx).events,
5153            vec![
5154                "observed event 1".to_string(),
5155                "observed event 2".to_string(),
5156            ]
5157        );
5158
5159        handle_2.update(cx, |view, _| {
5160            drop(handle_1);
5161            view.other.take();
5162        });
5163
5164        assert_eq!(cx.cx.views.len(), 2);
5165        assert!(cx.subscriptions.lock().is_empty());
5166        assert!(cx.observations.lock().is_empty());
5167    }
5168
5169    #[crate::test(self)]
5170    fn test_add_window(cx: &mut MutableAppContext) {
5171        struct View {
5172            mouse_down_count: Arc<AtomicUsize>,
5173        }
5174
5175        impl Entity for View {
5176            type Event = ();
5177        }
5178
5179        impl super::View for View {
5180            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5181                let mouse_down_count = self.mouse_down_count.clone();
5182                EventHandler::new(Empty::new().boxed())
5183                    .on_mouse_down(move |_| {
5184                        mouse_down_count.fetch_add(1, SeqCst);
5185                        true
5186                    })
5187                    .boxed()
5188            }
5189
5190            fn ui_name() -> &'static str {
5191                "View"
5192            }
5193        }
5194
5195        let mouse_down_count = Arc::new(AtomicUsize::new(0));
5196        let (window_id, _) = cx.add_window(Default::default(), |_| View {
5197            mouse_down_count: mouse_down_count.clone(),
5198        });
5199        let presenter = cx.presenters_and_platform_windows[&window_id].0.clone();
5200        // Ensure window's root element is in a valid lifecycle state.
5201        presenter.borrow_mut().dispatch_event(
5202            Event::LeftMouseDown {
5203                position: Default::default(),
5204                ctrl: false,
5205                alt: false,
5206                shift: false,
5207                cmd: false,
5208                click_count: 1,
5209            },
5210            cx,
5211        );
5212        assert_eq!(mouse_down_count.load(SeqCst), 1);
5213    }
5214
5215    #[crate::test(self)]
5216    fn test_entity_release_hooks(cx: &mut MutableAppContext) {
5217        struct Model {
5218            released: Rc<Cell<bool>>,
5219        }
5220
5221        struct View {
5222            released: Rc<Cell<bool>>,
5223        }
5224
5225        impl Entity for Model {
5226            type Event = ();
5227
5228            fn release(&mut self, _: &mut MutableAppContext) {
5229                self.released.set(true);
5230            }
5231        }
5232
5233        impl Entity for View {
5234            type Event = ();
5235
5236            fn release(&mut self, _: &mut MutableAppContext) {
5237                self.released.set(true);
5238            }
5239        }
5240
5241        impl super::View for View {
5242            fn ui_name() -> &'static str {
5243                "View"
5244            }
5245
5246            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5247                Empty::new().boxed()
5248            }
5249        }
5250
5251        let model_released = Rc::new(Cell::new(false));
5252        let model_release_observed = Rc::new(Cell::new(false));
5253        let view_released = Rc::new(Cell::new(false));
5254        let view_release_observed = Rc::new(Cell::new(false));
5255
5256        let model = cx.add_model(|_| Model {
5257            released: model_released.clone(),
5258        });
5259        let (window_id, view) = cx.add_window(Default::default(), |_| View {
5260            released: view_released.clone(),
5261        });
5262        assert!(!model_released.get());
5263        assert!(!view_released.get());
5264
5265        cx.observe_release(&model, {
5266            let model_release_observed = model_release_observed.clone();
5267            move |_, _| model_release_observed.set(true)
5268        })
5269        .detach();
5270        cx.observe_release(&view, {
5271            let view_release_observed = view_release_observed.clone();
5272            move |_, _| view_release_observed.set(true)
5273        })
5274        .detach();
5275
5276        cx.update(move |_| {
5277            drop(model);
5278        });
5279        assert!(model_released.get());
5280        assert!(model_release_observed.get());
5281
5282        drop(view);
5283        cx.remove_window(window_id);
5284        assert!(view_released.get());
5285        assert!(view_release_observed.get());
5286    }
5287
5288    #[crate::test(self)]
5289    fn test_view_events(cx: &mut MutableAppContext) {
5290        #[derive(Default)]
5291        struct View {
5292            events: Vec<usize>,
5293        }
5294
5295        impl Entity for View {
5296            type Event = usize;
5297        }
5298
5299        impl super::View for View {
5300            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5301                Empty::new().boxed()
5302            }
5303
5304            fn ui_name() -> &'static str {
5305                "View"
5306            }
5307        }
5308
5309        struct Model;
5310
5311        impl Entity for Model {
5312            type Event = usize;
5313        }
5314
5315        let (window_id, handle_1) = cx.add_window(Default::default(), |_| View::default());
5316        let handle_2 = cx.add_view(window_id, |_| View::default());
5317        let handle_3 = cx.add_model(|_| Model);
5318
5319        handle_1.update(cx, |_, cx| {
5320            cx.subscribe(&handle_2, move |me, emitter, event, cx| {
5321                me.events.push(*event);
5322
5323                cx.subscribe(&emitter, |me, _, event, _| {
5324                    me.events.push(*event * 2);
5325                })
5326                .detach();
5327            })
5328            .detach();
5329
5330            cx.subscribe(&handle_3, |me, _, event, _| {
5331                me.events.push(*event);
5332            })
5333            .detach();
5334        });
5335
5336        handle_2.update(cx, |_, c| c.emit(7));
5337        assert_eq!(handle_1.read(cx).events, vec![7]);
5338
5339        handle_2.update(cx, |_, c| c.emit(5));
5340        assert_eq!(handle_1.read(cx).events, vec![7, 5, 10]);
5341
5342        handle_3.update(cx, |_, c| c.emit(9));
5343        assert_eq!(handle_1.read(cx).events, vec![7, 5, 10, 9]);
5344    }
5345
5346    #[crate::test(self)]
5347    fn test_global_events(cx: &mut MutableAppContext) {
5348        #[derive(Clone, Debug, Eq, PartialEq)]
5349        struct GlobalEvent(u64);
5350
5351        let events = Rc::new(RefCell::new(Vec::new()));
5352        let first_subscription;
5353        let second_subscription;
5354
5355        {
5356            let events = events.clone();
5357            first_subscription = cx.subscribe_global(move |e: &GlobalEvent, _| {
5358                events.borrow_mut().push(("First", e.clone()));
5359            });
5360        }
5361
5362        {
5363            let events = events.clone();
5364            second_subscription = cx.subscribe_global(move |e: &GlobalEvent, _| {
5365                events.borrow_mut().push(("Second", e.clone()));
5366            });
5367        }
5368
5369        cx.update(|cx| {
5370            cx.emit_global(GlobalEvent(1));
5371            cx.emit_global(GlobalEvent(2));
5372        });
5373
5374        drop(first_subscription);
5375
5376        cx.update(|cx| {
5377            cx.emit_global(GlobalEvent(3));
5378        });
5379
5380        drop(second_subscription);
5381
5382        cx.update(|cx| {
5383            cx.emit_global(GlobalEvent(4));
5384        });
5385
5386        assert_eq!(
5387            &*events.borrow(),
5388            &[
5389                ("First", GlobalEvent(1)),
5390                ("Second", GlobalEvent(1)),
5391                ("First", GlobalEvent(2)),
5392                ("Second", GlobalEvent(2)),
5393                ("Second", GlobalEvent(3)),
5394            ]
5395        );
5396    }
5397
5398    #[crate::test(self)]
5399    fn test_global_events_emitted_before_subscription_in_same_update_cycle(
5400        cx: &mut MutableAppContext,
5401    ) {
5402        let events = Rc::new(RefCell::new(Vec::new()));
5403        cx.update(|cx| {
5404            {
5405                let events = events.clone();
5406                drop(cx.subscribe_global(move |_: &(), _| {
5407                    events.borrow_mut().push("dropped before emit");
5408                }));
5409            }
5410
5411            {
5412                let events = events.clone();
5413                cx.subscribe_global(move |_: &(), _| {
5414                    events.borrow_mut().push("before emit");
5415                })
5416                .detach();
5417            }
5418
5419            cx.emit_global(());
5420
5421            {
5422                let events = events.clone();
5423                cx.subscribe_global(move |_: &(), _| {
5424                    events.borrow_mut().push("after emit");
5425                })
5426                .detach();
5427            }
5428        });
5429
5430        assert_eq!(*events.borrow(), ["before emit"]);
5431    }
5432
5433    #[crate::test(self)]
5434    fn test_global_nested_events(cx: &mut MutableAppContext) {
5435        #[derive(Clone, Debug, Eq, PartialEq)]
5436        struct GlobalEvent(u64);
5437
5438        let events = Rc::new(RefCell::new(Vec::new()));
5439
5440        {
5441            let events = events.clone();
5442            cx.subscribe_global(move |e: &GlobalEvent, cx| {
5443                events.borrow_mut().push(("Outer", e.clone()));
5444
5445                if e.0 == 1 {
5446                    let events = events.clone();
5447                    cx.subscribe_global(move |e: &GlobalEvent, _| {
5448                        events.borrow_mut().push(("Inner", e.clone()));
5449                    })
5450                    .detach();
5451                }
5452            })
5453            .detach();
5454        }
5455
5456        cx.update(|cx| {
5457            cx.emit_global(GlobalEvent(1));
5458            cx.emit_global(GlobalEvent(2));
5459            cx.emit_global(GlobalEvent(3));
5460        });
5461        cx.update(|cx| {
5462            cx.emit_global(GlobalEvent(4));
5463        });
5464
5465        assert_eq!(
5466            &*events.borrow(),
5467            &[
5468                ("Outer", GlobalEvent(1)),
5469                ("Outer", GlobalEvent(2)),
5470                ("Outer", GlobalEvent(3)),
5471                ("Outer", GlobalEvent(4)),
5472                ("Inner", GlobalEvent(4)),
5473            ]
5474        );
5475    }
5476
5477    #[crate::test(self)]
5478    fn test_global(cx: &mut MutableAppContext) {
5479        type Global = usize;
5480
5481        let observation_count = Rc::new(RefCell::new(0));
5482        let subscription = cx.observe_global::<Global, _>({
5483            let observation_count = observation_count.clone();
5484            move |_, _| {
5485                *observation_count.borrow_mut() += 1;
5486            }
5487        });
5488
5489        assert!(!cx.has_global::<Global>());
5490        assert_eq!(cx.default_global::<Global>(), &0);
5491        assert_eq!(*observation_count.borrow(), 1);
5492        assert!(cx.has_global::<Global>());
5493        assert_eq!(
5494            cx.update_global::<Global, _, _>(|global, _| {
5495                *global = 1;
5496                "Update Result"
5497            }),
5498            "Update Result"
5499        );
5500        assert_eq!(*observation_count.borrow(), 2);
5501        assert_eq!(cx.global::<Global>(), &1);
5502
5503        drop(subscription);
5504        cx.update_global::<Global, _, _>(|global, _| {
5505            *global = 2;
5506        });
5507        assert_eq!(*observation_count.borrow(), 2);
5508
5509        type OtherGlobal = f32;
5510
5511        let observation_count = Rc::new(RefCell::new(0));
5512        cx.observe_global::<OtherGlobal, _>({
5513            let observation_count = observation_count.clone();
5514            move |_, _| {
5515                *observation_count.borrow_mut() += 1;
5516            }
5517        })
5518        .detach();
5519
5520        assert_eq!(
5521            cx.update_default_global::<OtherGlobal, _, _>(|global, _| {
5522                assert_eq!(global, &0.0);
5523                *global = 2.0;
5524                "Default update result"
5525            }),
5526            "Default update result"
5527        );
5528        assert_eq!(cx.global::<OtherGlobal>(), &2.0);
5529        assert_eq!(*observation_count.borrow(), 1);
5530    }
5531
5532    #[crate::test(self)]
5533    fn test_dropping_subscribers(cx: &mut MutableAppContext) {
5534        struct View;
5535
5536        impl Entity for View {
5537            type Event = ();
5538        }
5539
5540        impl super::View for View {
5541            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5542                Empty::new().boxed()
5543            }
5544
5545            fn ui_name() -> &'static str {
5546                "View"
5547            }
5548        }
5549
5550        struct Model;
5551
5552        impl Entity for Model {
5553            type Event = ();
5554        }
5555
5556        let (window_id, _) = cx.add_window(Default::default(), |_| View);
5557        let observing_view = cx.add_view(window_id, |_| View);
5558        let emitting_view = cx.add_view(window_id, |_| View);
5559        let observing_model = cx.add_model(|_| Model);
5560        let observed_model = cx.add_model(|_| Model);
5561
5562        observing_view.update(cx, |_, cx| {
5563            cx.subscribe(&emitting_view, |_, _, _, _| {}).detach();
5564            cx.subscribe(&observed_model, |_, _, _, _| {}).detach();
5565        });
5566        observing_model.update(cx, |_, cx| {
5567            cx.subscribe(&observed_model, |_, _, _, _| {}).detach();
5568        });
5569
5570        cx.update(|_| {
5571            drop(observing_view);
5572            drop(observing_model);
5573        });
5574
5575        emitting_view.update(cx, |_, cx| cx.emit(()));
5576        observed_model.update(cx, |_, cx| cx.emit(()));
5577    }
5578
5579    #[crate::test(self)]
5580    fn test_view_emit_before_subscribe_in_same_update_cycle(cx: &mut MutableAppContext) {
5581        #[derive(Default)]
5582        struct TestView;
5583
5584        impl Entity for TestView {
5585            type Event = ();
5586        }
5587
5588        impl View for TestView {
5589            fn ui_name() -> &'static str {
5590                "TestView"
5591            }
5592
5593            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5594                Empty::new().boxed()
5595            }
5596        }
5597
5598        let events = Rc::new(RefCell::new(Vec::new()));
5599        cx.add_window(Default::default(), |cx| {
5600            drop(cx.subscribe(&cx.handle(), {
5601                let events = events.clone();
5602                move |_, _, _, _| events.borrow_mut().push("dropped before flush")
5603            }));
5604            cx.subscribe(&cx.handle(), {
5605                let events = events.clone();
5606                move |_, _, _, _| events.borrow_mut().push("before emit")
5607            })
5608            .detach();
5609            cx.emit(());
5610            cx.subscribe(&cx.handle(), {
5611                let events = events.clone();
5612                move |_, _, _, _| events.borrow_mut().push("after emit")
5613            })
5614            .detach();
5615            TestView
5616        });
5617        assert_eq!(*events.borrow(), ["before emit"]);
5618    }
5619
5620    #[crate::test(self)]
5621    fn test_observe_and_notify_from_view(cx: &mut MutableAppContext) {
5622        #[derive(Default)]
5623        struct View {
5624            events: Vec<usize>,
5625        }
5626
5627        impl Entity for View {
5628            type Event = usize;
5629        }
5630
5631        impl super::View for View {
5632            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5633                Empty::new().boxed()
5634            }
5635
5636            fn ui_name() -> &'static str {
5637                "View"
5638            }
5639        }
5640
5641        #[derive(Default)]
5642        struct Model {
5643            count: usize,
5644        }
5645
5646        impl Entity for Model {
5647            type Event = ();
5648        }
5649
5650        let (_, view) = cx.add_window(Default::default(), |_| View::default());
5651        let model = cx.add_model(|_| Model::default());
5652
5653        view.update(cx, |_, c| {
5654            c.observe(&model, |me, observed, c| {
5655                me.events.push(observed.read(c).count)
5656            })
5657            .detach();
5658        });
5659
5660        model.update(cx, |model, c| {
5661            model.count = 11;
5662            c.notify();
5663        });
5664        assert_eq!(view.read(cx).events, vec![11]);
5665    }
5666
5667    #[crate::test(self)]
5668    fn test_view_notify_before_observe_in_same_update_cycle(cx: &mut MutableAppContext) {
5669        #[derive(Default)]
5670        struct TestView;
5671
5672        impl Entity for TestView {
5673            type Event = ();
5674        }
5675
5676        impl View for TestView {
5677            fn ui_name() -> &'static str {
5678                "TestView"
5679            }
5680
5681            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5682                Empty::new().boxed()
5683            }
5684        }
5685
5686        let events = Rc::new(RefCell::new(Vec::new()));
5687        cx.add_window(Default::default(), |cx| {
5688            drop(cx.observe(&cx.handle(), {
5689                let events = events.clone();
5690                move |_, _, _| events.borrow_mut().push("dropped before flush")
5691            }));
5692            cx.observe(&cx.handle(), {
5693                let events = events.clone();
5694                move |_, _, _| events.borrow_mut().push("before notify")
5695            })
5696            .detach();
5697            cx.notify();
5698            cx.observe(&cx.handle(), {
5699                let events = events.clone();
5700                move |_, _, _| events.borrow_mut().push("after notify")
5701            })
5702            .detach();
5703            TestView
5704        });
5705        assert_eq!(*events.borrow(), ["before notify"]);
5706    }
5707
5708    #[crate::test(self)]
5709    fn test_dropping_observers(cx: &mut MutableAppContext) {
5710        struct View;
5711
5712        impl Entity for View {
5713            type Event = ();
5714        }
5715
5716        impl super::View for View {
5717            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5718                Empty::new().boxed()
5719            }
5720
5721            fn ui_name() -> &'static str {
5722                "View"
5723            }
5724        }
5725
5726        struct Model;
5727
5728        impl Entity for Model {
5729            type Event = ();
5730        }
5731
5732        let (window_id, _) = cx.add_window(Default::default(), |_| View);
5733        let observing_view = cx.add_view(window_id, |_| View);
5734        let observing_model = cx.add_model(|_| Model);
5735        let observed_model = cx.add_model(|_| Model);
5736
5737        observing_view.update(cx, |_, cx| {
5738            cx.observe(&observed_model, |_, _, _| {}).detach();
5739        });
5740        observing_model.update(cx, |_, cx| {
5741            cx.observe(&observed_model, |_, _, _| {}).detach();
5742        });
5743
5744        cx.update(|_| {
5745            drop(observing_view);
5746            drop(observing_model);
5747        });
5748
5749        observed_model.update(cx, |_, cx| cx.notify());
5750    }
5751
5752    #[crate::test(self)]
5753    fn test_dropping_subscriptions_during_callback(cx: &mut MutableAppContext) {
5754        struct Model;
5755
5756        impl Entity for Model {
5757            type Event = u64;
5758        }
5759
5760        // Events
5761        let observing_model = cx.add_model(|_| Model);
5762        let observed_model = cx.add_model(|_| Model);
5763
5764        let events = Rc::new(RefCell::new(Vec::new()));
5765
5766        observing_model.update(cx, |_, cx| {
5767            let events = events.clone();
5768            let subscription = Rc::new(RefCell::new(None));
5769            *subscription.borrow_mut() = Some(cx.subscribe(&observed_model, {
5770                let subscription = subscription.clone();
5771                move |_, _, e, _| {
5772                    subscription.borrow_mut().take();
5773                    events.borrow_mut().push(e.clone());
5774                }
5775            }));
5776        });
5777
5778        observed_model.update(cx, |_, cx| {
5779            cx.emit(1);
5780            cx.emit(2);
5781        });
5782
5783        assert_eq!(*events.borrow(), [1]);
5784
5785        // Global Events
5786        #[derive(Clone, Debug, Eq, PartialEq)]
5787        struct GlobalEvent(u64);
5788
5789        let events = Rc::new(RefCell::new(Vec::new()));
5790
5791        {
5792            let events = events.clone();
5793            let subscription = Rc::new(RefCell::new(None));
5794            *subscription.borrow_mut() = Some(cx.subscribe_global({
5795                let subscription = subscription.clone();
5796                move |e: &GlobalEvent, _| {
5797                    subscription.borrow_mut().take();
5798                    events.borrow_mut().push(e.clone());
5799                }
5800            }));
5801        }
5802
5803        cx.update(|cx| {
5804            cx.emit_global(GlobalEvent(1));
5805            cx.emit_global(GlobalEvent(2));
5806        });
5807
5808        assert_eq!(*events.borrow(), [GlobalEvent(1)]);
5809
5810        // Model Observation
5811        let observing_model = cx.add_model(|_| Model);
5812        let observed_model = cx.add_model(|_| Model);
5813
5814        let observation_count = Rc::new(RefCell::new(0));
5815
5816        observing_model.update(cx, |_, cx| {
5817            let observation_count = observation_count.clone();
5818            let subscription = Rc::new(RefCell::new(None));
5819            *subscription.borrow_mut() = Some(cx.observe(&observed_model, {
5820                let subscription = subscription.clone();
5821                move |_, _, _| {
5822                    subscription.borrow_mut().take();
5823                    *observation_count.borrow_mut() += 1;
5824                }
5825            }));
5826        });
5827
5828        observed_model.update(cx, |_, cx| {
5829            cx.notify();
5830        });
5831
5832        observed_model.update(cx, |_, cx| {
5833            cx.notify();
5834        });
5835
5836        assert_eq!(*observation_count.borrow(), 1);
5837
5838        // View Observation
5839        struct View;
5840
5841        impl Entity for View {
5842            type Event = ();
5843        }
5844
5845        impl super::View for View {
5846            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5847                Empty::new().boxed()
5848            }
5849
5850            fn ui_name() -> &'static str {
5851                "View"
5852            }
5853        }
5854
5855        let (window_id, _) = cx.add_window(Default::default(), |_| View);
5856        let observing_view = cx.add_view(window_id, |_| View);
5857        let observed_view = cx.add_view(window_id, |_| View);
5858
5859        let observation_count = Rc::new(RefCell::new(0));
5860        observing_view.update(cx, |_, cx| {
5861            let observation_count = observation_count.clone();
5862            let subscription = Rc::new(RefCell::new(None));
5863            *subscription.borrow_mut() = Some(cx.observe(&observed_view, {
5864                let subscription = subscription.clone();
5865                move |_, _, _| {
5866                    subscription.borrow_mut().take();
5867                    *observation_count.borrow_mut() += 1;
5868                }
5869            }));
5870        });
5871
5872        observed_view.update(cx, |_, cx| {
5873            cx.notify();
5874        });
5875
5876        observed_view.update(cx, |_, cx| {
5877            cx.notify();
5878        });
5879
5880        assert_eq!(*observation_count.borrow(), 1);
5881
5882        // Global Observation
5883        let observation_count = Rc::new(RefCell::new(0));
5884        let subscription = Rc::new(RefCell::new(None));
5885        *subscription.borrow_mut() = Some(cx.observe_global::<(), _>({
5886            let observation_count = observation_count.clone();
5887            let subscription = subscription.clone();
5888            move |_, _| {
5889                subscription.borrow_mut().take();
5890                *observation_count.borrow_mut() += 1;
5891            }
5892        }));
5893
5894        cx.default_global::<()>();
5895        cx.set_global(());
5896        assert_eq!(*observation_count.borrow(), 1);
5897    }
5898
5899    #[crate::test(self)]
5900    fn test_focus(cx: &mut MutableAppContext) {
5901        struct View {
5902            name: String,
5903            events: Arc<Mutex<Vec<String>>>,
5904        }
5905
5906        impl Entity for View {
5907            type Event = ();
5908        }
5909
5910        impl super::View for View {
5911            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
5912                Empty::new().boxed()
5913            }
5914
5915            fn ui_name() -> &'static str {
5916                "View"
5917            }
5918
5919            fn on_focus(&mut self, _: &mut ViewContext<Self>) {
5920                self.events.lock().push(format!("{} focused", &self.name));
5921            }
5922
5923            fn on_blur(&mut self, _: &mut ViewContext<Self>) {
5924                self.events.lock().push(format!("{} blurred", &self.name));
5925            }
5926        }
5927
5928        let view_events: Arc<Mutex<Vec<String>>> = Default::default();
5929        let (window_id, view_1) = cx.add_window(Default::default(), |_| View {
5930            events: view_events.clone(),
5931            name: "view 1".to_string(),
5932        });
5933        let view_2 = cx.add_view(window_id, |_| View {
5934            events: view_events.clone(),
5935            name: "view 2".to_string(),
5936        });
5937
5938        let observed_events: Arc<Mutex<Vec<String>>> = Default::default();
5939        view_1.update(cx, |_, cx| {
5940            cx.observe_focus(&view_2, {
5941                let observed_events = observed_events.clone();
5942                move |this, view, cx| {
5943                    observed_events.lock().push(format!(
5944                        "{} observed {}'s focus",
5945                        this.name,
5946                        view.read(cx).name
5947                    ))
5948                }
5949            })
5950            .detach();
5951        });
5952        view_2.update(cx, |_, cx| {
5953            cx.observe_focus(&view_1, {
5954                let observed_events = observed_events.clone();
5955                move |this, view, cx| {
5956                    observed_events.lock().push(format!(
5957                        "{} observed {}'s focus",
5958                        this.name,
5959                        view.read(cx).name
5960                    ))
5961                }
5962            })
5963            .detach();
5964        });
5965
5966        view_1.update(cx, |_, cx| {
5967            // Ensure only the latest focus is honored.
5968            cx.focus(&view_2);
5969            cx.focus(&view_1);
5970            cx.focus(&view_2);
5971        });
5972        view_1.update(cx, |_, cx| cx.focus(&view_1));
5973        view_1.update(cx, |_, cx| cx.focus(&view_2));
5974        view_1.update(cx, |_, _| drop(view_2));
5975
5976        assert_eq!(
5977            *view_events.lock(),
5978            [
5979                "view 1 focused".to_string(),
5980                "view 1 blurred".to_string(),
5981                "view 2 focused".to_string(),
5982                "view 2 blurred".to_string(),
5983                "view 1 focused".to_string(),
5984                "view 1 blurred".to_string(),
5985                "view 2 focused".to_string(),
5986                "view 1 focused".to_string(),
5987            ],
5988        );
5989        assert_eq!(
5990            *observed_events.lock(),
5991            [
5992                "view 1 observed view 2's focus".to_string(),
5993                "view 2 observed view 1's focus".to_string(),
5994                "view 1 observed view 2's focus".to_string(),
5995            ]
5996        );
5997    }
5998
5999    #[crate::test(self)]
6000    fn test_deserialize_actions(cx: &mut MutableAppContext) {
6001        #[derive(Clone, Debug, Deserialize, PartialEq, Eq)]
6002        pub struct ComplexAction {
6003            arg: String,
6004            count: usize,
6005        }
6006
6007        actions!(test::something, [SimpleAction]);
6008        impl_actions!(test::something, [ComplexAction]);
6009
6010        cx.add_global_action(move |_: &SimpleAction, _: &mut MutableAppContext| {});
6011        cx.add_global_action(move |_: &ComplexAction, _: &mut MutableAppContext| {});
6012
6013        let action1 = cx
6014            .deserialize_action(
6015                "test::something::ComplexAction",
6016                Some(r#"{"arg": "a", "count": 5}"#),
6017            )
6018            .unwrap();
6019        let action2 = cx
6020            .deserialize_action("test::something::SimpleAction", None)
6021            .unwrap();
6022        assert_eq!(
6023            action1.as_any().downcast_ref::<ComplexAction>().unwrap(),
6024            &ComplexAction {
6025                arg: "a".to_string(),
6026                count: 5,
6027            }
6028        );
6029        assert_eq!(
6030            action2.as_any().downcast_ref::<SimpleAction>().unwrap(),
6031            &SimpleAction
6032        );
6033    }
6034
6035    #[crate::test(self)]
6036    fn test_dispatch_action(cx: &mut MutableAppContext) {
6037        struct ViewA {
6038            id: usize,
6039        }
6040
6041        impl Entity for ViewA {
6042            type Event = ();
6043        }
6044
6045        impl View for ViewA {
6046            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
6047                Empty::new().boxed()
6048            }
6049
6050            fn ui_name() -> &'static str {
6051                "View"
6052            }
6053        }
6054
6055        struct ViewB {
6056            id: usize,
6057        }
6058
6059        impl Entity for ViewB {
6060            type Event = ();
6061        }
6062
6063        impl View for ViewB {
6064            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
6065                Empty::new().boxed()
6066            }
6067
6068            fn ui_name() -> &'static str {
6069                "View"
6070            }
6071        }
6072
6073        #[derive(Clone, Deserialize)]
6074        pub struct Action(pub String);
6075
6076        impl_actions!(test, [Action]);
6077
6078        let actions = Rc::new(RefCell::new(Vec::new()));
6079
6080        cx.add_global_action({
6081            let actions = actions.clone();
6082            move |_: &Action, _: &mut MutableAppContext| {
6083                actions.borrow_mut().push("global".to_string());
6084            }
6085        });
6086
6087        cx.add_action({
6088            let actions = actions.clone();
6089            move |view: &mut ViewA, action: &Action, cx| {
6090                assert_eq!(action.0, "bar");
6091                cx.propagate_action();
6092                actions.borrow_mut().push(format!("{} a", view.id));
6093            }
6094        });
6095
6096        cx.add_action({
6097            let actions = actions.clone();
6098            move |view: &mut ViewA, _: &Action, cx| {
6099                if view.id != 1 {
6100                    cx.add_view(|cx| {
6101                        cx.propagate_action(); // Still works on a nested ViewContext
6102                        ViewB { id: 5 }
6103                    });
6104                }
6105                actions.borrow_mut().push(format!("{} b", view.id));
6106            }
6107        });
6108
6109        cx.add_action({
6110            let actions = actions.clone();
6111            move |view: &mut ViewB, _: &Action, cx| {
6112                cx.propagate_action();
6113                actions.borrow_mut().push(format!("{} c", view.id));
6114            }
6115        });
6116
6117        cx.add_action({
6118            let actions = actions.clone();
6119            move |view: &mut ViewB, _: &Action, cx| {
6120                cx.propagate_action();
6121                actions.borrow_mut().push(format!("{} d", view.id));
6122            }
6123        });
6124
6125        cx.capture_action({
6126            let actions = actions.clone();
6127            move |view: &mut ViewA, _: &Action, cx| {
6128                cx.propagate_action();
6129                actions.borrow_mut().push(format!("{} capture", view.id));
6130            }
6131        });
6132
6133        let (window_id, view_1) = cx.add_window(Default::default(), |_| ViewA { id: 1 });
6134        let view_2 = cx.add_view(window_id, |_| ViewB { id: 2 });
6135        let view_3 = cx.add_view(window_id, |_| ViewA { id: 3 });
6136        let view_4 = cx.add_view(window_id, |_| ViewB { id: 4 });
6137
6138        cx.dispatch_action(
6139            window_id,
6140            vec![view_1.id(), view_2.id(), view_3.id(), view_4.id()],
6141            &Action("bar".to_string()),
6142        );
6143
6144        assert_eq!(
6145            *actions.borrow(),
6146            vec![
6147                "1 capture",
6148                "3 capture",
6149                "4 d",
6150                "4 c",
6151                "3 b",
6152                "3 a",
6153                "2 d",
6154                "2 c",
6155                "1 b"
6156            ]
6157        );
6158
6159        // Remove view_1, which doesn't propagate the action
6160        actions.borrow_mut().clear();
6161        cx.dispatch_action(
6162            window_id,
6163            vec![view_2.id(), view_3.id(), view_4.id()],
6164            &Action("bar".to_string()),
6165        );
6166
6167        assert_eq!(
6168            *actions.borrow(),
6169            vec![
6170                "3 capture",
6171                "4 d",
6172                "4 c",
6173                "3 b",
6174                "3 a",
6175                "2 d",
6176                "2 c",
6177                "global"
6178            ]
6179        );
6180    }
6181
6182    #[crate::test(self)]
6183    fn test_dispatch_keystroke(cx: &mut MutableAppContext) {
6184        #[derive(Clone, Deserialize)]
6185        pub struct Action(String);
6186
6187        impl_actions!(test, [Action]);
6188
6189        struct View {
6190            id: usize,
6191            keymap_context: keymap::Context,
6192        }
6193
6194        impl Entity for View {
6195            type Event = ();
6196        }
6197
6198        impl super::View for View {
6199            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
6200                Empty::new().boxed()
6201            }
6202
6203            fn ui_name() -> &'static str {
6204                "View"
6205            }
6206
6207            fn keymap_context(&self, _: &AppContext) -> keymap::Context {
6208                self.keymap_context.clone()
6209            }
6210        }
6211
6212        impl View {
6213            fn new(id: usize) -> Self {
6214                View {
6215                    id,
6216                    keymap_context: keymap::Context::default(),
6217                }
6218            }
6219        }
6220
6221        let mut view_1 = View::new(1);
6222        let mut view_2 = View::new(2);
6223        let mut view_3 = View::new(3);
6224        view_1.keymap_context.set.insert("a".into());
6225        view_2.keymap_context.set.insert("a".into());
6226        view_2.keymap_context.set.insert("b".into());
6227        view_3.keymap_context.set.insert("a".into());
6228        view_3.keymap_context.set.insert("b".into());
6229        view_3.keymap_context.set.insert("c".into());
6230
6231        let (window_id, view_1) = cx.add_window(Default::default(), |_| view_1);
6232        let view_2 = cx.add_view(window_id, |_| view_2);
6233        let view_3 = cx.add_view(window_id, |_| view_3);
6234
6235        // This keymap's only binding dispatches an action on view 2 because that view will have
6236        // "a" and "b" in its context, but not "c".
6237        cx.add_bindings(vec![keymap::Binding::new(
6238            "a",
6239            Action("a".to_string()),
6240            Some("a && b && !c"),
6241        )]);
6242
6243        cx.add_bindings(vec![keymap::Binding::new(
6244            "b",
6245            Action("b".to_string()),
6246            None,
6247        )]);
6248
6249        let actions = Rc::new(RefCell::new(Vec::new()));
6250        cx.add_action({
6251            let actions = actions.clone();
6252            move |view: &mut View, action: &Action, cx| {
6253                if action.0 == "a" {
6254                    actions.borrow_mut().push(format!("{} a", view.id));
6255                } else {
6256                    actions
6257                        .borrow_mut()
6258                        .push(format!("{} {}", view.id, action.0));
6259                    cx.propagate_action();
6260                }
6261            }
6262        });
6263
6264        cx.add_global_action({
6265            let actions = actions.clone();
6266            move |action: &Action, _| {
6267                actions.borrow_mut().push(format!("global {}", action.0));
6268            }
6269        });
6270
6271        cx.dispatch_keystroke(
6272            window_id,
6273            vec![view_1.id(), view_2.id(), view_3.id()],
6274            &Keystroke::parse("a").unwrap(),
6275        );
6276
6277        assert_eq!(&*actions.borrow(), &["2 a"]);
6278
6279        actions.borrow_mut().clear();
6280        cx.dispatch_keystroke(
6281            window_id,
6282            vec![view_1.id(), view_2.id(), view_3.id()],
6283            &Keystroke::parse("b").unwrap(),
6284        );
6285
6286        assert_eq!(&*actions.borrow(), &["3 b", "2 b", "1 b", "global b"]);
6287    }
6288
6289    #[crate::test(self)]
6290    async fn test_model_condition(cx: &mut TestAppContext) {
6291        struct Counter(usize);
6292
6293        impl super::Entity for Counter {
6294            type Event = ();
6295        }
6296
6297        impl Counter {
6298            fn inc(&mut self, cx: &mut ModelContext<Self>) {
6299                self.0 += 1;
6300                cx.notify();
6301            }
6302        }
6303
6304        let model = cx.add_model(|_| Counter(0));
6305
6306        let condition1 = model.condition(&cx, |model, _| model.0 == 2);
6307        let condition2 = model.condition(&cx, |model, _| model.0 == 3);
6308        smol::pin!(condition1, condition2);
6309
6310        model.update(cx, |model, cx| model.inc(cx));
6311        assert_eq!(poll_once(&mut condition1).await, None);
6312        assert_eq!(poll_once(&mut condition2).await, None);
6313
6314        model.update(cx, |model, cx| model.inc(cx));
6315        assert_eq!(poll_once(&mut condition1).await, Some(()));
6316        assert_eq!(poll_once(&mut condition2).await, None);
6317
6318        model.update(cx, |model, cx| model.inc(cx));
6319        assert_eq!(poll_once(&mut condition2).await, Some(()));
6320
6321        model.update(cx, |_, cx| cx.notify());
6322    }
6323
6324    #[crate::test(self)]
6325    #[should_panic]
6326    async fn test_model_condition_timeout(cx: &mut TestAppContext) {
6327        struct Model;
6328
6329        impl super::Entity for Model {
6330            type Event = ();
6331        }
6332
6333        let model = cx.add_model(|_| Model);
6334        model.condition(&cx, |_, _| false).await;
6335    }
6336
6337    #[crate::test(self)]
6338    #[should_panic(expected = "model dropped with pending condition")]
6339    async fn test_model_condition_panic_on_drop(cx: &mut TestAppContext) {
6340        struct Model;
6341
6342        impl super::Entity for Model {
6343            type Event = ();
6344        }
6345
6346        let model = cx.add_model(|_| Model);
6347        let condition = model.condition(&cx, |_, _| false);
6348        cx.update(|_| drop(model));
6349        condition.await;
6350    }
6351
6352    #[crate::test(self)]
6353    async fn test_view_condition(cx: &mut TestAppContext) {
6354        struct Counter(usize);
6355
6356        impl super::Entity for Counter {
6357            type Event = ();
6358        }
6359
6360        impl super::View for Counter {
6361            fn ui_name() -> &'static str {
6362                "test view"
6363            }
6364
6365            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
6366                Empty::new().boxed()
6367            }
6368        }
6369
6370        impl Counter {
6371            fn inc(&mut self, cx: &mut ViewContext<Self>) {
6372                self.0 += 1;
6373                cx.notify();
6374            }
6375        }
6376
6377        let (_, view) = cx.add_window(|_| Counter(0));
6378
6379        let condition1 = view.condition(&cx, |view, _| view.0 == 2);
6380        let condition2 = view.condition(&cx, |view, _| view.0 == 3);
6381        smol::pin!(condition1, condition2);
6382
6383        view.update(cx, |view, cx| view.inc(cx));
6384        assert_eq!(poll_once(&mut condition1).await, None);
6385        assert_eq!(poll_once(&mut condition2).await, None);
6386
6387        view.update(cx, |view, cx| view.inc(cx));
6388        assert_eq!(poll_once(&mut condition1).await, Some(()));
6389        assert_eq!(poll_once(&mut condition2).await, None);
6390
6391        view.update(cx, |view, cx| view.inc(cx));
6392        assert_eq!(poll_once(&mut condition2).await, Some(()));
6393        view.update(cx, |_, cx| cx.notify());
6394    }
6395
6396    #[crate::test(self)]
6397    #[should_panic]
6398    async fn test_view_condition_timeout(cx: &mut TestAppContext) {
6399        struct View;
6400
6401        impl super::Entity for View {
6402            type Event = ();
6403        }
6404
6405        impl super::View for View {
6406            fn ui_name() -> &'static str {
6407                "test view"
6408            }
6409
6410            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
6411                Empty::new().boxed()
6412            }
6413        }
6414
6415        let (_, view) = cx.add_window(|_| View);
6416        view.condition(&cx, |_, _| false).await;
6417    }
6418
6419    #[crate::test(self)]
6420    #[should_panic(expected = "view dropped with pending condition")]
6421    async fn test_view_condition_panic_on_drop(cx: &mut TestAppContext) {
6422        struct View;
6423
6424        impl super::Entity for View {
6425            type Event = ();
6426        }
6427
6428        impl super::View for View {
6429            fn ui_name() -> &'static str {
6430                "test view"
6431            }
6432
6433            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
6434                Empty::new().boxed()
6435            }
6436        }
6437
6438        let window_id = cx.add_window(|_| View).0;
6439        let view = cx.add_view(window_id, |_| View);
6440
6441        let condition = view.condition(&cx, |_, _| false);
6442        cx.update(|_| drop(view));
6443        condition.await;
6444    }
6445
6446    #[crate::test(self)]
6447    fn test_refresh_windows(cx: &mut MutableAppContext) {
6448        struct View(usize);
6449
6450        impl super::Entity for View {
6451            type Event = ();
6452        }
6453
6454        impl super::View for View {
6455            fn ui_name() -> &'static str {
6456                "test view"
6457            }
6458
6459            fn render(&mut self, _: &mut RenderContext<Self>) -> ElementBox {
6460                Empty::new().named(format!("render count: {}", post_inc(&mut self.0)))
6461            }
6462        }
6463
6464        let (window_id, root_view) = cx.add_window(Default::default(), |_| View(0));
6465        let presenter = cx.presenters_and_platform_windows[&window_id].0.clone();
6466
6467        assert_eq!(
6468            presenter.borrow().rendered_views[&root_view.id()].name(),
6469            Some("render count: 0")
6470        );
6471
6472        let view = cx.add_view(window_id, |cx| {
6473            cx.refresh_windows();
6474            View(0)
6475        });
6476
6477        assert_eq!(
6478            presenter.borrow().rendered_views[&root_view.id()].name(),
6479            Some("render count: 1")
6480        );
6481        assert_eq!(
6482            presenter.borrow().rendered_views[&view.id()].name(),
6483            Some("render count: 0")
6484        );
6485
6486        cx.update(|cx| cx.refresh_windows());
6487        assert_eq!(
6488            presenter.borrow().rendered_views[&root_view.id()].name(),
6489            Some("render count: 2")
6490        );
6491        assert_eq!(
6492            presenter.borrow().rendered_views[&view.id()].name(),
6493            Some("render count: 1")
6494        );
6495
6496        cx.update(|cx| {
6497            cx.refresh_windows();
6498            drop(view);
6499        });
6500        assert_eq!(
6501            presenter.borrow().rendered_views[&root_view.id()].name(),
6502            Some("render count: 3")
6503        );
6504        assert_eq!(presenter.borrow().rendered_views.len(), 1);
6505    }
6506}