collab_notification.rs

  1use gpui::{AnyElement, SharedUri, prelude::*};
  2use smallvec::SmallVec;
  3
  4use crate::{Avatar, prelude::*};
  5
  6#[derive(IntoElement, RegisterComponent)]
  7pub struct CollabNotification {
  8    avatar_uri: SharedUri,
  9    accept_button: Button,
 10    dismiss_button: Button,
 11    children: SmallVec<[AnyElement; 2]>,
 12}
 13
 14impl CollabNotification {
 15    pub fn new(
 16        avatar_uri: impl Into<SharedUri>,
 17        accept_button: Button,
 18        dismiss_button: Button,
 19    ) -> Self {
 20        Self {
 21            avatar_uri: avatar_uri.into(),
 22            accept_button,
 23            dismiss_button,
 24            children: SmallVec::new(),
 25        }
 26    }
 27}
 28
 29impl ParentElement for CollabNotification {
 30    fn extend(&mut self, elements: impl IntoIterator<Item = AnyElement>) {
 31        self.children.extend(elements)
 32    }
 33}
 34
 35impl RenderOnce for CollabNotification {
 36    fn render(self, _: &mut Window, cx: &mut App) -> impl IntoElement {
 37        h_flex()
 38            .p_2()
 39            .size_full()
 40            .text_ui(cx)
 41            .justify_between()
 42            .overflow_hidden()
 43            .elevation_3(cx)
 44            .gap_1()
 45            .child(
 46                h_flex()
 47                    .min_w_0()
 48                    .gap_4()
 49                    .child(Avatar::new(self.avatar_uri).size(px(40.)))
 50                    .child(v_flex().truncate().children(self.children)),
 51            )
 52            .child(
 53                v_flex()
 54                    .items_center()
 55                    .child(self.accept_button)
 56                    .child(self.dismiss_button),
 57            )
 58    }
 59}
 60
 61impl Component for CollabNotification {
 62    fn scope() -> ComponentScope {
 63        ComponentScope::Collaboration
 64    }
 65
 66    fn preview(_window: &mut Window, _cx: &mut App) -> Option<AnyElement> {
 67        let avatar = "https://avatars.githubusercontent.com/u/67129314?v=4";
 68        let container = || div().h(px(72.)).w(px(400.)); // Size of the actual notification window
 69
 70        let examples = vec![
 71            single_example(
 72                "Incoming Call",
 73                container()
 74                    .child(
 75                        CollabNotification::new(
 76                            avatar,
 77                            Button::new("accept", "Accept"),
 78                            Button::new("decline", "Decline"),
 79                        )
 80                        .child(Label::new("the user is inviting you to a call")),
 81                    )
 82                    .into_any_element(),
 83            ),
 84            single_example(
 85                "Screen Share Request",
 86                container()
 87                    .child(
 88                        CollabNotification::new(
 89                            avatar,
 90                            Button::new("accept", "View"),
 91                            Button::new("decline", "Ignore"),
 92                        )
 93                        .child(Label::new("the user is sharing their screen")),
 94                    )
 95                    .into_any_element(),
 96            ),
 97            single_example(
 98                "Project Shared",
 99                container()
100                    .child(
101                        CollabNotification::new(
102                            avatar,
103                            Button::new("accept", "Open"),
104                            Button::new("decline", "Dismiss"),
105                        )
106                        .child(Label::new("the user is sharing a project"))
107                        .child(Label::new("zed").color(Color::Muted)),
108                    )
109                    .into_any_element(),
110            ),
111            single_example(
112                "Overflowing Content",
113                container()
114                    .child(
115                        CollabNotification::new(
116                            avatar,
117                            Button::new("accept", "Accept"),
118                            Button::new("decline", "Decline"),
119                        )
120                        .child(Label::new(
121                            "a_very_long_username_that_might_overflow is sharing a project in Zed:",
122                        ))
123                        .child(
124                            Label::new("zed-cloud, zed, edit-prediction-bench, zed.dev")
125                                .color(Color::Muted),
126                        ),
127                    )
128                    .into_any_element(),
129            ),
130        ];
131
132        Some(example_group(examples).vertical().into_any_element())
133    }
134}