T22: Collaboration
- presence: avatars ringed in each peer's color with where they are, press to follow; a breathing live dot; follow mode frames the view and stops on Escape - remote cursors and selections painted over a field from its own layout - comment threads with replies, reactions and resolve; a marker that opens a thread in a bubble; a sidebar of open and resolved threads - annotations washed in their authors' colors, notes on hover - suggestion mode: edits become suggestions word by word; track changes shows them struck and underlined, to accept or reject - sharing: invite by email with checked chips, roles, the access list and who the link lets in, in one dialog - primitives::hold_focus gives a mode its own focus, shared with ZenMode - AvatarGroup's tuck and count shared; Avatar::ring_color; TagInput::check; TextInput::bounds_for_range; Popover::size - icons: smile-plus, user-plus, message-square-diff - gallery: the Collaboration page with scripted states
This commit is contained in:
34 files changed
+3297
-86
No files matched your search
@@ -170,6 +170,46 @@ pub(crate) fn give_back(state: &Entity<Takeover>, window: &mut Window, cx: &mut
|
||||
}
|
||||
}
|
||||
|
||||
/// A mode's own focus, where focus was before the mode took it, and whether the mode was on last frame.
|
||||
pub(crate) struct Held {
|
||||
pub focus: FocusHandle,
|
||||
previous: Option<FocusHandle>,
|
||||
was_on: bool,
|
||||
}
|
||||
|
||||
/// The focus a mode keyed `key` holds: turned on while focus is elsewhere, it takes focus so Escape reaches it.
|
||||
pub(crate) fn hold_focus(
|
||||
key: impl Into<ElementId>,
|
||||
on: bool,
|
||||
window: &mut Window,
|
||||
cx: &mut App,
|
||||
) -> Entity<Held> {
|
||||
let held = window.use_keyed_state(key, cx, |_, cx| Held {
|
||||
focus: cx.focus_handle(),
|
||||
previous: None,
|
||||
was_on: false,
|
||||
});
|
||||
let (focus, was_on) = (held.read(cx).focus.clone(), held.read(cx).was_on);
|
||||
if on && !was_on && !focus.contains_focused(window, cx) {
|
||||
log::info!("focus: a mode takes it, so Escape reaches it");
|
||||
let previous = window.focused(cx);
|
||||
window.focus(&focus);
|
||||
held.update(cx, |held, _| held.previous = previous);
|
||||
}
|
||||
if on != was_on {
|
||||
held.update(cx, |held, _| held.was_on = on);
|
||||
}
|
||||
held
|
||||
}
|
||||
|
||||
/// Hands focus back to where it was before the mode took it.
|
||||
pub(crate) fn hand_back(held: &Entity<Held>, window: &mut Window, cx: &mut App) {
|
||||
if let Some(previous) = held.update(cx, |held, _| held.previous.take()) {
|
||||
log::info!("focus: handed back after a mode");
|
||||
window.focus(&previous);
|
||||
}
|
||||
}
|
||||
|
||||
/// A focus handle kept for `id`, a Tab stop while enabled.
|
||||
pub(crate) fn tab_stop(
|
||||
id: ElementId,
|
||||
|
||||
@@ -187,6 +187,7 @@ icons! {
|
||||
Menu => "menu",
|
||||
Merge => "merge",
|
||||
MessageSquare => "message-square",
|
||||
MessageSquareDiff => "message-square-diff",
|
||||
MicOff => "mic-off",
|
||||
Mic => "mic",
|
||||
Minimize2 => "minimize-2",
|
||||
@@ -242,6 +243,7 @@ icons! {
|
||||
SlidersHorizontal => "sliders-horizontal",
|
||||
Smartphone => "smartphone",
|
||||
Smile => "smile",
|
||||
SmilePlus => "smile-plus",
|
||||
Sparkles => "sparkles",
|
||||
Spline => "spline",
|
||||
SquareCheck => "square-check",
|
||||
@@ -267,6 +269,7 @@ icons! {
|
||||
Undo2 => "undo-2",
|
||||
Upload => "upload",
|
||||
User => "user",
|
||||
UserPlus => "user-plus",
|
||||
Users => "users",
|
||||
Variable => "variable",
|
||||
VideoOff => "video-off",
|
||||
|
||||
@@ -14,7 +14,7 @@ pub use backdrop::{Backdrop, Place};
|
||||
pub use disclosure::Disclosure;
|
||||
pub use divider::Divider;
|
||||
pub use focus::{FocusNext, FocusPrev, FocusRing, FocusScope};
|
||||
pub(crate) use focus::{Takeover, give_back, tab_stop, take_focus};
|
||||
pub(crate) use focus::{Takeover, give_back, hand_back, hold_focus, tab_stop, take_focus};
|
||||
pub use ghost::DragGhost;
|
||||
pub use icon::{Icon, IconName};
|
||||
pub use image::Image;
|
||||
|
||||
Reference in new issue
Block a user