diff --git a/crates/collab_ui/src/collab_titlebar_item.rs b/crates/collab_ui/src/collab_titlebar_item.rs index dc449e9d96..72e885b84e 100644 --- a/crates/collab_ui/src/collab_titlebar_item.rs +++ b/crates/collab_ui/src/collab_titlebar_item.rs @@ -17,7 +17,7 @@ use gpui::{ }; use settings::Settings; use std::{ops::Range, sync::Arc}; -use theme::Theme; +use theme::{AvatarStyle, Theme}; use util::ResultExt; use workspace::{FollowNextCollaborator, JoinProject, ToggleFollow, Workspace}; @@ -614,21 +614,22 @@ impl CollabTitlebarItem { if let Some(location) = location { if let ParticipantLocation::SharedProject { project_id } = location { if Some(project_id) == workspace.read(cx).project().read(cx).remote_id() { - avatar_style = theme.workspace.titlebar.avatar; + avatar_style = &theme.workspace.titlebar.avatar; } else { - avatar_style = theme.workspace.titlebar.inactive_avatar; + avatar_style = &theme.workspace.titlebar.inactive_avatar; } } else { - avatar_style = theme.workspace.titlebar.inactive_avatar; + avatar_style = &theme.workspace.titlebar.inactive_avatar; } } else { - avatar_style = theme.workspace.titlebar.avatar; + avatar_style = &theme.workspace.titlebar.avatar; } let content = Stack::new() .with_children(user.avatar.as_ref().map(|avatar| { let flex = Flex::row() - .with_child(Self::render_face(avatar.clone(), avatar_style, theme)) + // .with_reversed_paint_order() + .with_child(Self::render_face(avatar.clone(), avatar_style.clone())) .with_children( (|| { let room = room?.read(cx); @@ -652,14 +653,22 @@ impl CollabTitlebarItem { } })?; - Some(Self::render_face(avatar.clone(), avatar_style, theme)) + Some( + Container::new(Self::render_face( + avatar.clone(), + theme.workspace.titlebar.follower_avatar.clone(), + )) + .with_margin_left( + -1.0 * theme.workspace.titlebar.follower_avatar_overlap, + ) + .boxed(), + ) })) })() .into_iter() .flatten(), ); - let room = ActiveCall::global(cx).read(cx).room(); if let (Some(replica_id), Some(room)) = (replica_id, room) { let followed_by_self = is_being_followed && room @@ -669,7 +678,6 @@ impl CollabTitlebarItem { .any(|&follower| { Some(follower) == workspace.read(cx).client().peer_id() }); - if followed_by_self { let color = theme.editor.replica_selection_style(replica_id).selection; return flex.contained().with_background_color(color).boxed(); @@ -742,11 +750,14 @@ impl CollabTitlebarItem { } } - fn render_face(avatar: Arc, avatar_style: ImageStyle, theme: &Theme) -> ElementBox { + fn render_face(avatar: Arc, avatar_style: AvatarStyle) -> ElementBox { Image::new(avatar) - .with_style(avatar_style) + .with_style(avatar_style.image) .constrained() - .with_width(theme.workspace.titlebar.avatar_width) + .with_width(avatar_style.width) + .contained() + .with_background_color(Color::white()) + .with_corner_radius(avatar_style.image.corner_radius) .aligned() .boxed() } diff --git a/crates/theme/src/theme.rs b/crates/theme/src/theme.rs index 904e6c2bd3..f4802f5eca 100644 --- a/crates/theme/src/theme.rs +++ b/crates/theme/src/theme.rs @@ -74,12 +74,13 @@ pub struct Titlebar { pub container: ContainerStyle, pub height: f32, pub title: TextStyle, - pub avatar_width: f32, pub avatar_margin: f32, pub avatar_ribbon: AvatarRibbon, + pub follower_avatar_overlap: f32, pub offline_icon: OfflineIcon, - pub avatar: ImageStyle, - pub inactive_avatar: ImageStyle, + pub avatar: AvatarStyle, + pub inactive_avatar: AvatarStyle, + pub follower_avatar: AvatarStyle, pub sign_in_prompt: Interactive, pub outdated_warning: ContainedText, pub share_button: Interactive, @@ -88,6 +89,13 @@ pub struct Titlebar { pub toggle_contacts_badge: ContainerStyle, } +#[derive(Clone, Deserialize, Default)] +pub struct AvatarStyle { + #[serde(flatten)] + pub image: ImageStyle, + pub width: f32, +} + #[derive(Deserialize, Default)] pub struct ContactsPopover { #[serde(flatten)] diff --git a/styles/src/styleTree/workspace.ts b/styles/src/styleTree/workspace.ts index f0a11db1f9..42f5540194 100644 --- a/styles/src/styleTree/workspace.ts +++ b/styles/src/styleTree/workspace.ts @@ -41,6 +41,7 @@ export default function workspace(colorScheme: ColorScheme) { }, }; const avatarWidth = 18; + const followerAvatarWidth = 14; return { background: background(layer), @@ -80,7 +81,6 @@ export default function workspace(colorScheme: ColorScheme) { }, statusBar: statusBar(colorScheme), titlebar: { - avatarWidth, avatarMargin: 8, height: 33, // 32px + 1px for overlaid border background: background(layer), @@ -95,6 +95,7 @@ export default function workspace(colorScheme: ColorScheme) { // Collaborators avatar: { + width: avatarWidth, cornerRadius: avatarWidth / 2, border: { color: "#00000088", @@ -102,6 +103,7 @@ export default function workspace(colorScheme: ColorScheme) { }, }, inactiveAvatar: { + width: avatarWidth, cornerRadius: avatarWidth / 2, border: { color: "#00000088", @@ -109,6 +111,15 @@ export default function workspace(colorScheme: ColorScheme) { }, grayscale: true, }, + followerAvatar: { + width: followerAvatarWidth, + cornerRadius: followerAvatarWidth / 2, + border: { + color: "#00000088", + width: 1, + }, + }, + followerAvatarOverlap: 4, avatarRibbon: { height: 3, width: 12, @@ -118,7 +129,7 @@ export default function workspace(colorScheme: ColorScheme) { // Sign in buttom // FlatButton, Variant signInPrompt: { - ...titlebarButton + ...titlebarButton, }, // Offline Indicator @@ -184,8 +195,8 @@ export default function workspace(colorScheme: ColorScheme) { background: foreground(layer, "accent"), }, shareButton: { - ...titlebarButton - } + ...titlebarButton, + }, }, toolbar: { @@ -241,9 +252,6 @@ export default function workspace(colorScheme: ColorScheme) { shadow: colorScheme.modalShadow, }, }, - dropTargetOverlayColor: withOpacity( - foreground(layer, "variant"), - 0.5 - ), + dropTargetOverlayColor: withOpacity(foreground(layer, "variant"), 0.5), }; }