feat(calls): 'N Live' pill names who is in the call on hover/focus (#157)
CI / Build & Quality Checks (push) Successful in 1m51s
CI / Docker image build & smoke test (push) Skipped
CI / Secret scan (gitleaks) (push) Successful in 6s
CI / Trigger Desktop Build (push) Successful in 5s
CI / Playwright smoke (e2e) (push) Successful in 1m37s
CI / Build & Quality Checks (push) Successful in 1m51s
CI / Docker image build & smoke test (push) Skipped
CI / Secret scan (gitleaks) (push) Successful in 6s
CI / Trigger Desktop Build (push) Successful in 5s
CI / Playwright smoke (e2e) (push) Successful in 1m37s
Tooltip (folds TooltipProvider, 300 ms) on the room-list Live badge listing the call members' display names — deduped per user, capped at 6 + 'and N more' — plus an aria-label with the same text so keyboard/screen-reader users get it too (the badge is focusable). Names come from the same MatrixRTC memberships that produce the count; no new data. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01PPmy3tPq869XDW4njjVaKA
This commit is contained in:
@@ -30,6 +30,8 @@ import {
|
||||
RectCords,
|
||||
Badge,
|
||||
Spinner,
|
||||
Tooltip,
|
||||
TooltipProvider,
|
||||
} from 'folds';
|
||||
import { useFocusWithin, useHover } from 'react-aria';
|
||||
import FocusTrap from 'focus-trap-react';
|
||||
@@ -41,7 +43,12 @@ import isYesterday from 'dayjs/plugin/isYesterday';
|
||||
import { NavItem, NavItemContent, NavItemOptions, NavLink } from '../../components/nav';
|
||||
import { UnreadBadge, UnreadBadgeCenter } from '../../components/unread-badge';
|
||||
import { RoomAvatar, RoomIcon } from '../../components/room-avatar';
|
||||
import { getDirectRoomAvatarUrl, getRoomAvatarUrl, getStateEvent } from '../../utils/room';
|
||||
import {
|
||||
getDirectRoomAvatarUrl,
|
||||
getMemberName,
|
||||
getRoomAvatarUrl,
|
||||
getStateEvent,
|
||||
} from '../../utils/room';
|
||||
import { nameInitials } from '../../utils/common';
|
||||
import { useMatrixClient } from '../../hooks/useMatrixClient';
|
||||
import { useRoomUnread } from '../../state/hooks/unread';
|
||||
@@ -690,6 +697,14 @@ function RoomNavItem_({
|
||||
const optionsVisible = hover || !!menuAnchor;
|
||||
const callSession = useCallSession(room);
|
||||
const callMembers = useCallMembers(callSession);
|
||||
const liveNames = useMemo(() => {
|
||||
const names = Array.from(
|
||||
new Set(callMembers.map((m) => m.sender).filter((u): u is string => !!u)),
|
||||
).map((u) => getMemberName(room, u));
|
||||
const shown = names.slice(0, 6);
|
||||
const more = names.length - shown.length;
|
||||
return more > 0 ? `${shown.join(', ')} and ${more} more` : shown.join(', ');
|
||||
}, [callMembers, room]);
|
||||
const startCall = useCallStart(direct);
|
||||
const callEmbed = useCallEmbed();
|
||||
// [Gitea #30] Same voice-limit check the call prescreen uses, so the sidebar
|
||||
@@ -853,11 +868,32 @@ function RoomNavItem_({
|
||||
/>
|
||||
)}
|
||||
{callMembers.length > 0 && (
|
||||
<Badge variant="Critical" fill="Solid" size="400">
|
||||
<Text as="span" size="L400" truncate>
|
||||
{callMembers.length} Live
|
||||
</Text>
|
||||
</Badge>
|
||||
// [Gitea #157] The count alone doesn't tell you whether it's your
|
||||
// squad — name the people on hover/focus (long-press on touch).
|
||||
<TooltipProvider
|
||||
position="Right"
|
||||
delay={300}
|
||||
tooltip={
|
||||
<Tooltip>
|
||||
<Text size="T200">{liveNames}</Text>
|
||||
</Tooltip>
|
||||
}
|
||||
>
|
||||
{(tipRef) => (
|
||||
<Badge
|
||||
ref={tipRef}
|
||||
variant="Critical"
|
||||
fill="Solid"
|
||||
size="400"
|
||||
tabIndex={0}
|
||||
aria-label={`${callMembers.length} in call: ${liveNames}`}
|
||||
>
|
||||
<Text as="span" size="L400" truncate>
|
||||
{callMembers.length} Live
|
||||
</Text>
|
||||
</Badge>
|
||||
)}
|
||||
</TooltipProvider>
|
||||
)}
|
||||
</Box>
|
||||
</NavItemContent>
|
||||
|
||||
Reference in New Issue
Block a user