gpui2.rs

  1mod action;
  2mod app;
  3mod assets;
  4mod color;
  5mod element;
  6mod elements;
  7mod executor;
  8mod focusable;
  9mod geometry;
 10mod image_cache;
 11mod interactive;
 12mod keymap;
 13mod platform;
 14mod scene;
 15mod style;
 16mod styled;
 17mod subscription;
 18mod svg_renderer;
 19mod taffy;
 20#[cfg(any(test, feature = "test-support"))]
 21mod test;
 22mod text_system;
 23mod util;
 24mod view;
 25mod window;
 26
 27pub use action::*;
 28pub use anyhow::Result;
 29pub use app::*;
 30pub use assets::*;
 31pub use color::*;
 32pub use element::*;
 33pub use elements::*;
 34pub use executor::*;
 35pub use focusable::*;
 36pub use geometry::*;
 37pub use gpui2_macros::*;
 38pub use image_cache::*;
 39pub use interactive::*;
 40pub use keymap::*;
 41pub use platform::*;
 42pub use refineable::*;
 43pub use scene::*;
 44pub use serde;
 45pub use serde_json;
 46pub use smallvec;
 47pub use smol::Timer;
 48pub use style::*;
 49pub use styled::*;
 50pub use subscription::*;
 51pub use svg_renderer::*;
 52pub use taffy::{AvailableSpace, LayoutId};
 53#[cfg(any(test, feature = "test-support"))]
 54pub use test::*;
 55pub use text_system::*;
 56pub use util::arc_cow::ArcCow;
 57pub use view::*;
 58pub use window::*;
 59
 60use derive_more::{Deref, DerefMut};
 61use std::{
 62    any::{Any, TypeId},
 63    borrow::{Borrow, BorrowMut},
 64    mem,
 65    ops::{Deref, DerefMut},
 66    sync::Arc,
 67};
 68use taffy::TaffyLayoutEngine;
 69
 70type AnyBox = Box<dyn Any + Send>;
 71
 72pub trait Context {
 73    type EntityContext<'a, T>;
 74    type Result<T>;
 75
 76    fn entity<T>(
 77        &mut self,
 78        build_entity: impl FnOnce(&mut Self::EntityContext<'_, T>) -> T,
 79    ) -> Self::Result<Handle<T>>
 80    where
 81        T: 'static + Send;
 82
 83    fn update_entity<T: 'static, R>(
 84        &mut self,
 85        handle: &Handle<T>,
 86        update: impl FnOnce(&mut T, &mut Self::EntityContext<'_, T>) -> R,
 87    ) -> Self::Result<R>;
 88}
 89
 90pub trait VisualContext: Context {
 91    type ViewContext<'a, 'w, V>;
 92
 93    fn build_view<E, V>(
 94        &mut self,
 95        build_entity: impl FnOnce(&mut Self::ViewContext<'_, '_, V>) -> V,
 96        render: impl Fn(&mut V, &mut ViewContext<'_, '_, V>) -> E + Send + 'static,
 97    ) -> Self::Result<View<V>>
 98    where
 99        E: Component<V>,
100        V: 'static + Send;
101
102    fn update_view<V: 'static, R>(
103        &mut self,
104        view: &View<V>,
105        update: impl FnOnce(&mut V, &mut Self::ViewContext<'_, '_, V>) -> R,
106    ) -> Self::Result<R>;
107}
108
109pub enum GlobalKey {
110    Numeric(usize),
111    View(EntityId),
112    Type(TypeId),
113}
114
115#[repr(transparent)]
116pub struct MainThread<T>(T);
117
118impl<T> Deref for MainThread<T> {
119    type Target = T;
120
121    fn deref(&self) -> &Self::Target {
122        &self.0
123    }
124}
125
126impl<T> DerefMut for MainThread<T> {
127    fn deref_mut(&mut self) -> &mut Self::Target {
128        &mut self.0
129    }
130}
131
132impl<C: Context> Context for MainThread<C> {
133    type EntityContext<'a, T> = MainThread<C::EntityContext<'a, T>>;
134    type Result<T> = C::Result<T>;
135
136    fn entity<T>(
137        &mut self,
138        build_entity: impl FnOnce(&mut Self::EntityContext<'_, T>) -> T,
139    ) -> Self::Result<Handle<T>>
140    where
141        T: 'static + Send,
142    {
143        self.0.entity(|cx| {
144            let cx = unsafe {
145                mem::transmute::<
146                    &mut C::EntityContext<'_, T>,
147                    &mut MainThread<C::EntityContext<'_, T>>,
148                >(cx)
149            };
150            build_entity(cx)
151        })
152    }
153
154    fn update_entity<T: 'static, R>(
155        &mut self,
156        handle: &Handle<T>,
157        update: impl FnOnce(&mut T, &mut Self::EntityContext<'_, T>) -> R,
158    ) -> Self::Result<R> {
159        self.0.update_entity(handle, |entity, cx| {
160            let cx = unsafe {
161                mem::transmute::<
162                    &mut C::EntityContext<'_, T>,
163                    &mut MainThread<C::EntityContext<'_, T>>,
164                >(cx)
165            };
166            update(entity, cx)
167        })
168    }
169}
170
171impl<C: VisualContext> VisualContext for MainThread<C> {
172    type ViewContext<'a, 'w, V> = MainThread<C::ViewContext<'a, 'w, V>>;
173
174    fn build_view<E, V>(
175        &mut self,
176        build_entity: impl FnOnce(&mut Self::ViewContext<'_, '_, V>) -> V,
177        render: impl Fn(&mut V, &mut ViewContext<'_, '_, V>) -> E + Send + 'static,
178    ) -> Self::Result<View<V>>
179    where
180        E: Component<V>,
181        V: 'static + Send,
182    {
183        self.0.build_view(
184            |cx| {
185                let cx = unsafe {
186                    mem::transmute::<
187                        &mut C::ViewContext<'_, '_, V>,
188                        &mut MainThread<C::ViewContext<'_, '_, V>>,
189                    >(cx)
190                };
191                build_entity(cx)
192            },
193            render,
194        )
195    }
196
197    fn update_view<V: 'static, R>(
198        &mut self,
199        view: &View<V>,
200        update: impl FnOnce(&mut V, &mut Self::ViewContext<'_, '_, V>) -> R,
201    ) -> Self::Result<R> {
202        self.0.update_view(view, |view_state, cx| {
203            let cx = unsafe {
204                mem::transmute::<
205                    &mut C::ViewContext<'_, '_, V>,
206                    &mut MainThread<C::ViewContext<'_, '_, V>>,
207                >(cx)
208            };
209            update(view_state, cx)
210        })
211    }
212}
213
214pub trait BorrowAppContext {
215    fn with_text_style<F, R>(&mut self, style: TextStyleRefinement, f: F) -> R
216    where
217        F: FnOnce(&mut Self) -> R;
218
219    fn set_global<T: Send + 'static>(&mut self, global: T);
220}
221
222impl<C> BorrowAppContext for C
223where
224    C: BorrowMut<AppContext>,
225{
226    fn with_text_style<F, R>(&mut self, style: TextStyleRefinement, f: F) -> R
227    where
228        F: FnOnce(&mut Self) -> R,
229    {
230        self.borrow_mut().push_text_style(style);
231        let result = f(self);
232        self.borrow_mut().pop_text_style();
233        result
234    }
235
236    fn set_global<G: 'static + Send>(&mut self, global: G) {
237        self.borrow_mut().set_global(global)
238    }
239}
240
241pub trait EventEmitter: 'static {
242    type Event: Any;
243}
244
245pub trait Flatten<T> {
246    fn flatten(self) -> Result<T>;
247}
248
249impl<T> Flatten<T> for Result<Result<T>> {
250    fn flatten(self) -> Result<T> {
251        self?
252    }
253}
254
255impl<T> Flatten<T> for Result<T> {
256    fn flatten(self) -> Result<T> {
257        self
258    }
259}
260
261#[derive(Deref, DerefMut, Eq, PartialEq, Hash, Clone)]
262pub struct SharedString(ArcCow<'static, str>);
263
264impl Default for SharedString {
265    fn default() -> Self {
266        Self(ArcCow::Owned("".into()))
267    }
268}
269
270impl AsRef<str> for SharedString {
271    fn as_ref(&self) -> &str {
272        &self.0
273    }
274}
275
276impl Borrow<str> for SharedString {
277    fn borrow(&self) -> &str {
278        self.as_ref()
279    }
280}
281
282impl std::fmt::Debug for SharedString {
283    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
284        self.0.fmt(f)
285    }
286}
287
288impl std::fmt::Display for SharedString {
289    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
290        write!(f, "{}", self.0.as_ref())
291    }
292}
293
294impl<T: Into<ArcCow<'static, str>>> From<T> for SharedString {
295    fn from(value: T) -> Self {
296        Self(value.into())
297    }
298}
299
300pub enum Reference<'a, T> {
301    Immutable(&'a T),
302    Mutable(&'a mut T),
303}
304
305impl<'a, T> Deref for Reference<'a, T> {
306    type Target = T;
307
308    fn deref(&self) -> &Self::Target {
309        match self {
310            Reference::Immutable(target) => target,
311            Reference::Mutable(target) => target,
312        }
313    }
314}
315
316impl<'a, T> DerefMut for Reference<'a, T> {
317    fn deref_mut(&mut self) -> &mut Self::Target {
318        match self {
319            Reference::Immutable(_) => {
320                panic!("cannot mutably deref an immutable reference. this is a bug in GPUI.");
321            }
322            Reference::Mutable(target) => target,
323        }
324    }
325}
326
327pub(crate) struct MainThreadOnly<T: ?Sized> {
328    executor: Executor,
329    value: Arc<T>,
330}
331
332impl<T: ?Sized> Clone for MainThreadOnly<T> {
333    fn clone(&self) -> Self {
334        Self {
335            executor: self.executor.clone(),
336            value: self.value.clone(),
337        }
338    }
339}
340
341/// Allows a value to be accessed only on the main thread, allowing a non-`Send` type
342/// to become `Send`.
343impl<T: 'static + ?Sized> MainThreadOnly<T> {
344    pub(crate) fn new(value: Arc<T>, executor: Executor) -> Self {
345        Self { executor, value }
346    }
347
348    pub(crate) fn borrow_on_main_thread(&self) -> &T {
349        assert!(self.executor.is_main_thread());
350        &self.value
351    }
352}
353
354unsafe impl<T: ?Sized> Send for MainThreadOnly<T> {}