@@ -149,7 +149,7 @@ impl ContactsPanel {
theme: &theme::ContactsPanel,
cx: &mut LayoutContext,
) -> ElementBox {
- let project_count = contact.projects.len();
+ let project_count = contact.non_empty_projects().count();
let font_cache = cx.font_cache();
let line_height = theme.unshared_project.name.text.line_height(font_cache);
let cap_height = theme.unshared_project.name.text.cap_height(font_cache);
@@ -188,121 +188,128 @@ impl ContactsPanel {
.with_height(theme.row_height)
.boxed(),
)
- .with_children(contact.projects.iter().enumerate().map(|(ix, project)| {
- let project_id = project.id;
-
- Flex::row()
- .with_child(
- Canvas::new(move |bounds, _, cx| {
- let start_x =
- bounds.min_x() + (bounds.width() / 2.) - (tree_branch_width / 2.);
- let end_x = bounds.max_x();
- let start_y = bounds.min_y();
- let end_y = bounds.min_y() + baseline_offset - (cap_height / 2.);
-
- cx.scene.push_quad(gpui::Quad {
- bounds: RectF::from_points(
- vec2f(start_x, start_y),
- vec2f(
- start_x + tree_branch_width,
- if ix + 1 == project_count {
- end_y
- } else {
- bounds.max_y()
- },
- ),
- ),
- background: Some(tree_branch_color),
- border: gpui::Border::default(),
- corner_radius: 0.,
- });
- cx.scene.push_quad(gpui::Quad {
- bounds: RectF::from_points(
- vec2f(start_x, end_y),
- vec2f(end_x, end_y + tree_branch_width),
- ),
- background: Some(tree_branch_color),
- border: gpui::Border::default(),
- corner_radius: 0.,
- });
- })
- .constrained()
- .with_width(host_avatar_height)
- .boxed(),
- )
- .with_child({
- let is_host = Some(contact.user.id) == current_user_id;
- let is_guest = !is_host
- && project
- .guests
- .iter()
- .any(|guest| Some(guest.id) == current_user_id);
- let is_shared = project.is_shared;
- let app_state = app_state.clone();
-
- MouseEventHandler::new::<ContactsPanel, _, _>(
- project_id as usize,
- cx,
- |mouse_state, _| {
- let style = match (project.is_shared, mouse_state.hovered) {
- (false, false) => &theme.unshared_project,
- (false, true) => &theme.hovered_unshared_project,
- (true, false) => &theme.shared_project,
- (true, true) => &theme.hovered_shared_project,
- };
-
- Flex::row()
- .with_child(
- Label::new(
- project.worktree_root_names.join(", "),
- style.name.text.clone(),
- )
- .aligned()
- .left()
- .contained()
- .with_style(style.name.container)
- .boxed(),
- )
- .with_children(project.guests.iter().filter_map(
- |participant| {
- participant.avatar.clone().map(|avatar| {
- Image::new(avatar)
- .with_style(style.guest_avatar)
- .aligned()
- .left()
- .contained()
- .with_margin_right(style.guest_avatar_spacing)
- .boxed()
- })
- },
- ))
- .contained()
- .with_style(style.container)
- .constrained()
- .with_height(style.height)
- .boxed()
- },
- )
- .with_cursor_style(if is_host || is_shared {
- CursorStyle::PointingHand
- } else {
- CursorStyle::Arrow
- })
- .on_click(move |_, cx| {
- if !is_host && !is_guest {
- cx.dispatch_global_action(JoinProject {
- project_id,
- app_state: app_state.clone(),
- });
- }
- })
- .flex(1., true)
- .boxed()
- })
- .constrained()
- .with_height(theme.unshared_project.height)
- .boxed()
- }))
+ .with_children(
+ contact
+ .non_empty_projects()
+ .enumerate()
+ .map(|(ix, project)| {
+ let project_id = project.id;
+ Flex::row()
+ .with_child(
+ Canvas::new(move |bounds, _, cx| {
+ let start_x = bounds.min_x() + (bounds.width() / 2.)
+ - (tree_branch_width / 2.);
+ let end_x = bounds.max_x();
+ let start_y = bounds.min_y();
+ let end_y =
+ bounds.min_y() + baseline_offset - (cap_height / 2.);
+
+ cx.scene.push_quad(gpui::Quad {
+ bounds: RectF::from_points(
+ vec2f(start_x, start_y),
+ vec2f(
+ start_x + tree_branch_width,
+ if ix + 1 == project_count {
+ end_y
+ } else {
+ bounds.max_y()
+ },
+ ),
+ ),
+ background: Some(tree_branch_color),
+ border: gpui::Border::default(),
+ corner_radius: 0.,
+ });
+ cx.scene.push_quad(gpui::Quad {
+ bounds: RectF::from_points(
+ vec2f(start_x, end_y),
+ vec2f(end_x, end_y + tree_branch_width),
+ ),
+ background: Some(tree_branch_color),
+ border: gpui::Border::default(),
+ corner_radius: 0.,
+ });
+ })
+ .constrained()
+ .with_width(host_avatar_height)
+ .boxed(),
+ )
+ .with_child({
+ let is_host = Some(contact.user.id) == current_user_id;
+ let is_guest = !is_host
+ && project
+ .guests
+ .iter()
+ .any(|guest| Some(guest.id) == current_user_id);
+ let is_shared = project.is_shared;
+ let app_state = app_state.clone();
+
+ MouseEventHandler::new::<ContactsPanel, _, _>(
+ project_id as usize,
+ cx,
+ |mouse_state, _| {
+ let style = match (project.is_shared, mouse_state.hovered) {
+ (false, false) => &theme.unshared_project,
+ (false, true) => &theme.hovered_unshared_project,
+ (true, false) => &theme.shared_project,
+ (true, true) => &theme.hovered_shared_project,
+ };
+
+ Flex::row()
+ .with_child(
+ Label::new(
+ project.worktree_root_names.join(", "),
+ style.name.text.clone(),
+ )
+ .aligned()
+ .left()
+ .contained()
+ .with_style(style.name.container)
+ .boxed(),
+ )
+ .with_children(project.guests.iter().filter_map(
+ |participant| {
+ participant.avatar.clone().map(|avatar| {
+ Image::new(avatar)
+ .with_style(style.guest_avatar)
+ .aligned()
+ .left()
+ .contained()
+ .with_margin_right(
+ style.guest_avatar_spacing,
+ )
+ .boxed()
+ })
+ },
+ ))
+ .contained()
+ .with_style(style.container)
+ .constrained()
+ .with_height(style.height)
+ .boxed()
+ },
+ )
+ .with_cursor_style(if is_host || is_shared {
+ CursorStyle::PointingHand
+ } else {
+ CursorStyle::Arrow
+ })
+ .on_click(move |_, cx| {
+ if !is_host && !is_guest {
+ cx.dispatch_global_action(JoinProject {
+ project_id,
+ app_state: app_state.clone(),
+ });
+ }
+ })
+ .flex(1., true)
+ .boxed()
+ })
+ .constrained()
+ .with_height(theme.unshared_project.height)
+ .boxed()
+ }),
+ )
.boxed()
}