Calling missing media keys indicator
This commit is contained in:
parent
436ee1a18f
commit
d97aa68716
13 changed files with 280 additions and 84 deletions
|
@ -1864,6 +1864,14 @@
|
|||
"messageformat": "You won't receive their voice or video and they won't receive yours.",
|
||||
"description": "Shown in the modal dialog to describe how blocking works in a group call"
|
||||
},
|
||||
"icu:calling__missing-media-keys": {
|
||||
"messageformat": "Can't receive audio and video from {name}",
|
||||
"description": "When you can't view someone's audio and video in a call because their media keys are unavailable"
|
||||
},
|
||||
"icu:calling__missing-media-keys-info": {
|
||||
"messageformat": "This may be because they have not verified your safety number change, there's a problem with their device, or they have blocked you.",
|
||||
"description": "Detailed explanation why you can't view someone's audio and video in a call because their media keys are unavailable."
|
||||
},
|
||||
"icu:calling__overflow__scroll-up": {
|
||||
"messageformat": "Scroll up",
|
||||
"description": "Label for the \"scroll up\" button in a call's overflow area"
|
||||
|
|
3
images/icons/v3/error/error-circle-solid.svg
Normal file
3
images/icons/v3/error/error-circle-solid.svg
Normal file
|
@ -0,0 +1,3 @@
|
|||
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M12 1C9.82441 1 7.69767 1.64514 5.88873 2.85383C4.07979 4.06253 2.66989 5.78049 1.83733 7.79048C1.00477 9.80047 0.786929 12.0122 1.21137 14.146C1.6358 16.2798 2.68345 18.2398 4.22183 19.7782C5.76021 21.3166 7.72022 22.3642 9.85401 22.7886C11.9878 23.2131 14.1995 22.9952 16.2095 22.1627C18.2195 21.3301 19.9375 19.9202 21.1462 18.1113C22.3549 16.3023 23 14.1756 23 12C23 9.08262 21.8411 6.28473 19.7782 4.22183C17.7153 2.15893 14.9174 1 12 1ZM13.25 6L12.75 13.5H11.25L10.75 6H13.25ZM12 18C11.7033 18 11.4133 17.912 11.1666 17.7472C10.92 17.5824 10.7277 17.3481 10.6142 17.074C10.5007 16.7999 10.4709 16.4983 10.5288 16.2074C10.5867 15.9164 10.7296 15.6491 10.9393 15.4393C11.1491 15.2296 11.4164 15.0867 11.7074 15.0288C11.9983 14.9709 12.2999 15.0006 12.574 15.1142C12.8481 15.2277 13.0824 15.42 13.2472 15.6666C13.412 15.9133 13.5 16.2033 13.5 16.5C13.5 16.8978 13.342 17.2794 13.0607 17.5607C12.7794 17.842 12.3978 18 12 18Z" fill="black"/>
|
||||
</svg>
|
After Width: | Height: | Size: 1 KiB |
|
@ -3824,6 +3824,14 @@ button.module-image__border-overlay:focus {
|
|||
padding-block: 0 14px;
|
||||
padding-inline: 16px;
|
||||
}
|
||||
|
||||
.module-ongoing-call__group-call-remote-participant__error-icon {
|
||||
margin-block-end: 16px;
|
||||
}
|
||||
|
||||
.module-ongoing-call__group-call-remote-participant__error {
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
|
||||
&--hand-raised {
|
||||
|
@ -3861,6 +3869,7 @@ button.module-image__border-overlay:focus {
|
|||
margin-bottom: 1rem;
|
||||
|
||||
&__footer {
|
||||
height: 40px;
|
||||
padding-block: 0 8px;
|
||||
padding-inline: 10px;
|
||||
}
|
||||
|
@ -4029,23 +4038,38 @@ button.module-image__border-overlay:focus {
|
|||
background-color: $color-gray-78;
|
||||
}
|
||||
|
||||
&__blocked {
|
||||
@include color-svg('../images/icons/v3/block/block.svg', $color-white);
|
||||
height: 24px;
|
||||
margin-bottom: 16px;
|
||||
width: 24px;
|
||||
&-background .module-calling__background--blur {
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
&--info {
|
||||
@include button-reset;
|
||||
background-color: $color-gray-75;
|
||||
border-radius: 16px;
|
||||
color: $color-white;
|
||||
line-height: 16px;
|
||||
padding-block: 3px;
|
||||
padding-inline: 10px;
|
||||
}
|
||||
&__error {
|
||||
// Hide it here in the general case, and reveal it in the grid layout
|
||||
// when @container size is big enough
|
||||
display: none;
|
||||
|
||||
&--modal-title {
|
||||
margin-block-end: 12px;
|
||||
margin-inline: 8px;
|
||||
font-size: 12px;
|
||||
line-height: 16px;
|
||||
color: $color-white;
|
||||
text-align: center;
|
||||
z-index: $z-index-base;
|
||||
}
|
||||
|
||||
&__more-info {
|
||||
@include button-reset;
|
||||
padding-block: 3px;
|
||||
padding-inline: 10px;
|
||||
border-radius: 16px;
|
||||
background-color: $color-gray-75;
|
||||
color: $color-white;
|
||||
font-size: 12px;
|
||||
line-height: 16px;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
z-index: $z-index-above-base;
|
||||
|
||||
&-modal-title {
|
||||
-webkit-box-orient: vertical;
|
||||
-webkit-line-clamp: 2;
|
||||
display: -webkit-box;
|
||||
|
@ -4054,6 +4078,23 @@ button.module-image__border-overlay:focus {
|
|||
}
|
||||
}
|
||||
|
||||
&__error-icon {
|
||||
width: 24px;
|
||||
height: 24px;
|
||||
margin-block-end: 8px;
|
||||
|
||||
&--blocked {
|
||||
@include color-svg('../images/icons/v3/block/block.svg', $color-white);
|
||||
}
|
||||
|
||||
&--missing-media-keys {
|
||||
@include color-svg(
|
||||
'../images/icons/v3/error/error-circle-solid.svg',
|
||||
$color-white
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
&__footer {
|
||||
display: flex;
|
||||
position: absolute;
|
||||
|
|
|
@ -326,6 +326,7 @@ export function GroupCall1(): JSX.Element {
|
|||
hasRemoteAudio: true,
|
||||
hasRemoteVideo: true,
|
||||
isHandRaised: false,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 1.3,
|
||||
|
@ -353,6 +354,7 @@ export function GroupCallYourHandRaised(): JSX.Element {
|
|||
hasRemoteAudio: true,
|
||||
hasRemoteVideo: true,
|
||||
isHandRaised: false,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 1.3,
|
||||
|
@ -372,26 +374,32 @@ export function GroupCallYourHandRaised(): JSX.Element {
|
|||
const PARTICIPANT_EMOJIS = ['❤️', '🤔', '✨', '😂', '🦄'] as const;
|
||||
|
||||
// We generate these upfront so that the list is stable when you move the slider.
|
||||
const allRemoteParticipants = times(MAX_PARTICIPANTS).map(index => ({
|
||||
aci: generateAci(),
|
||||
demuxId: index,
|
||||
hasRemoteAudio: index % 3 !== 0,
|
||||
hasRemoteVideo: index % 4 !== 0,
|
||||
isHandRaised: (index - 3) % 10 === 0,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: Math.random() < 0.7 ? 1.3 : Math.random() * 0.4 + 0.6,
|
||||
...getDefaultConversationWithServiceId({
|
||||
isBlocked: index === 10 || index === MAX_PARTICIPANTS - 1,
|
||||
title: `Participant ${
|
||||
(index - 2) % 4 === 0
|
||||
? PARTICIPANT_EMOJIS[
|
||||
Math.floor((index - 2) / 4) % PARTICIPANT_EMOJIS.length
|
||||
]
|
||||
: ''
|
||||
} ${index + 1}`,
|
||||
}),
|
||||
}));
|
||||
const allRemoteParticipants = times(MAX_PARTICIPANTS).map(index => {
|
||||
const mediaKeysReceived = (index + 1) % 20 !== 0;
|
||||
|
||||
return {
|
||||
aci: generateAci(),
|
||||
addedTime: Date.now() - 60000,
|
||||
demuxId: index,
|
||||
hasRemoteAudio: mediaKeysReceived ? index % 3 !== 0 : false,
|
||||
hasRemoteVideo: mediaKeysReceived ? index % 4 !== 0 : false,
|
||||
isHandRaised: (index - 3) % 10 === 0,
|
||||
mediaKeysReceived,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: Math.random() < 0.7 ? 1.3 : Math.random() * 0.4 + 0.6,
|
||||
...getDefaultConversationWithServiceId({
|
||||
isBlocked: index === 10 || index === MAX_PARTICIPANTS - 1,
|
||||
title: `Participant ${
|
||||
(index - 2) % 4 === 0
|
||||
? PARTICIPANT_EMOJIS[
|
||||
Math.floor((index - 2) / 4) % PARTICIPANT_EMOJIS.length
|
||||
]
|
||||
: ''
|
||||
} ${index + 1}`,
|
||||
}),
|
||||
};
|
||||
});
|
||||
|
||||
export function GroupCallManyPaginated(): JSX.Element {
|
||||
const props = createProps({
|
||||
|
@ -471,6 +479,7 @@ export function GroupCallReconnecting(): JSX.Element {
|
|||
hasRemoteAudio: true,
|
||||
hasRemoteVideo: true,
|
||||
isHandRaised: false,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 1.3,
|
||||
|
@ -793,3 +802,38 @@ function useHandRaiser(
|
|||
}, [frequency, call, max, min]);
|
||||
return call;
|
||||
}
|
||||
|
||||
export function GroupCallSomeoneMissingMediaKeys(): JSX.Element {
|
||||
return (
|
||||
<CallScreen
|
||||
{...createProps({
|
||||
callMode: CallMode.Group,
|
||||
remoteParticipants: allRemoteParticipants
|
||||
.slice(0, 5)
|
||||
.map((participant, index) => ({
|
||||
...participant,
|
||||
addedTime: index === 1 ? Date.now() - 60000 : undefined,
|
||||
hasRemoteAudio: false,
|
||||
hasRemoteVideo: false,
|
||||
mediaKeysReceived: index !== 1,
|
||||
})),
|
||||
})}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
export function GroupCallSomeoneBlocked(): JSX.Element {
|
||||
return (
|
||||
<CallScreen
|
||||
{...createProps({
|
||||
callMode: CallMode.Group,
|
||||
remoteParticipants: allRemoteParticipants
|
||||
.slice(0, 5)
|
||||
.map((participant, index) => ({
|
||||
...participant,
|
||||
isBlocked: index === 1,
|
||||
})),
|
||||
})}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -26,6 +26,7 @@ function createParticipant(
|
|||
hasRemoteAudio: Boolean(participantProps.hasRemoteAudio),
|
||||
hasRemoteVideo: Boolean(participantProps.hasRemoteVideo),
|
||||
isHandRaised: Boolean(participantProps.isHandRaised),
|
||||
mediaKeysReceived: Boolean(participantProps.mediaKeysReceived),
|
||||
presenting: Boolean(participantProps.presenting),
|
||||
sharingScreen: Boolean(participantProps.sharingScreen),
|
||||
videoAspectRatio: 1.3,
|
||||
|
|
|
@ -24,6 +24,7 @@ const allRemoteParticipants = times(MAX_PARTICIPANTS).map(index => ({
|
|||
hasRemoteAudio: index % 3 !== 0,
|
||||
hasRemoteVideo: index % 4 !== 0,
|
||||
isHandRaised: (index - 2) % 8 === 0,
|
||||
mediaKeysReceived: (index + 1) % 20 !== 0,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 1.3,
|
||||
|
|
|
@ -35,13 +35,17 @@ const getFrameBuffer = memoize(() => Buffer.alloc(FRAME_BUFFER_SIZE));
|
|||
const createProps = (
|
||||
overrideProps: OverridePropsType,
|
||||
{
|
||||
addedTime,
|
||||
isBlocked = false,
|
||||
hasRemoteAudio = false,
|
||||
presenting = false,
|
||||
isHandRaised = false,
|
||||
hasRemoteAudio = false,
|
||||
mediaKeysReceived = true,
|
||||
presenting = false,
|
||||
}: {
|
||||
addedTime?: number;
|
||||
isBlocked?: boolean;
|
||||
hasRemoteAudio?: boolean;
|
||||
mediaKeysReceived?: boolean;
|
||||
presenting?: boolean;
|
||||
isHandRaised?: boolean;
|
||||
} = {}
|
||||
|
@ -54,10 +58,12 @@ const createProps = (
|
|||
audioLevel: 0,
|
||||
remoteParticipant: {
|
||||
aci: generateAci(),
|
||||
addedTime,
|
||||
demuxId: 123,
|
||||
hasRemoteAudio,
|
||||
hasRemoteVideo: true,
|
||||
isHandRaised,
|
||||
mediaKeysReceived,
|
||||
presenting,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 1.3,
|
||||
|
@ -165,3 +171,24 @@ export function Blocked(): JSX.Element {
|
|||
/>
|
||||
);
|
||||
}
|
||||
|
||||
export function NoMediaKeys(): JSX.Element {
|
||||
return (
|
||||
<GroupCallRemoteParticipant
|
||||
{...createProps(
|
||||
{
|
||||
isInPip: false,
|
||||
height: 120,
|
||||
left: 0,
|
||||
top: 0,
|
||||
width: 120,
|
||||
},
|
||||
{
|
||||
addedTime: Date.now() - 60 * 1000,
|
||||
hasRemoteAudio: true,
|
||||
mediaKeysReceived: false,
|
||||
}
|
||||
)}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -27,9 +27,12 @@ import { ContactName } from './conversation/ContactName';
|
|||
import { useIntersectionObserver } from '../hooks/useIntersectionObserver';
|
||||
import { MAX_FRAME_HEIGHT, MAX_FRAME_WIDTH } from '../calling/constants';
|
||||
import { useValueAtFixedRate } from '../hooks/useValueAtFixedRate';
|
||||
import { Theme } from '../util/theme';
|
||||
import { isOlderThan } from '../util/timestamp';
|
||||
|
||||
const MAX_TIME_TO_SHOW_STALE_VIDEO_FRAMES = 10000;
|
||||
const MAX_TIME_TO_SHOW_STALE_SCREENSHARE_FRAMES = 60000;
|
||||
const DELAY_TO_SHOW_MISSING_MEDIA_KEYS = 5000;
|
||||
|
||||
type BasePropsType = {
|
||||
getFrameBuffer: () => Buffer;
|
||||
|
@ -77,6 +80,7 @@ export const GroupCallRemoteParticipant: React.FC<PropsType> = React.memo(
|
|||
|
||||
const {
|
||||
acceptedMessageRequest,
|
||||
addedTime,
|
||||
avatarPath,
|
||||
color,
|
||||
demuxId,
|
||||
|
@ -85,6 +89,7 @@ export const GroupCallRemoteParticipant: React.FC<PropsType> = React.memo(
|
|||
isHandRaised,
|
||||
isBlocked,
|
||||
isMe,
|
||||
mediaKeysReceived,
|
||||
profileName,
|
||||
sharedGroupNames,
|
||||
sharingScreen,
|
||||
|
@ -102,7 +107,7 @@ export const GroupCallRemoteParticipant: React.FC<PropsType> = React.memo(
|
|||
const [isWide, setIsWide] = useState<boolean>(
|
||||
videoAspectRatio ? videoAspectRatio >= 1 : true
|
||||
);
|
||||
const [showBlockInfo, setShowBlockInfo] = useState(false);
|
||||
const [showErrorDialog, setShowErrorDialog] = useState(false);
|
||||
|
||||
// We have some state (`hasReceivedVideoRecently`) and this ref. We can't have a
|
||||
// single state value like `lastReceivedVideoAt` because (1) it won't automatically
|
||||
|
@ -129,6 +134,11 @@ export const GroupCallRemoteParticipant: React.FC<PropsType> = React.memo(
|
|||
|
||||
const wantsToShowVideo = hasRemoteVideo && !isBlocked && isVisible;
|
||||
const hasVideoToShow = wantsToShowVideo && hasReceivedVideoRecently;
|
||||
const showMissingMediaKeys = Boolean(
|
||||
!mediaKeysReceived &&
|
||||
addedTime &&
|
||||
isOlderThan(addedTime, DELAY_TO_SHOW_MISSING_MEDIA_KEYS)
|
||||
);
|
||||
|
||||
const videoFrameSource = useMemo(
|
||||
() => getGroupCallVideoFrameSource(demuxId),
|
||||
|
@ -293,29 +303,94 @@ export const GroupCallRemoteParticipant: React.FC<PropsType> = React.memo(
|
|||
}
|
||||
}
|
||||
|
||||
let noVideoNode: ReactNode;
|
||||
let errorDialogTitle: ReactNode;
|
||||
let errorDialogBody = '';
|
||||
if (!hasVideoToShow) {
|
||||
const showDialogButton = (
|
||||
<button
|
||||
type="button"
|
||||
className="module-ongoing-call__group-call-remote-participant__more-info"
|
||||
onClick={() => {
|
||||
setShowErrorDialog(true);
|
||||
}}
|
||||
>
|
||||
{i18n('icu:moreInfo')}
|
||||
</button>
|
||||
);
|
||||
if (isBlocked) {
|
||||
noVideoNode = (
|
||||
<>
|
||||
<i className="module-ongoing-call__group-call-remote-participant__error-icon module-ongoing-call__group-call-remote-participant__error-icon--blocked" />
|
||||
{showDialogButton}
|
||||
</>
|
||||
);
|
||||
errorDialogTitle = (
|
||||
<div className="module-ongoing-call__group-call-remote-participant__more-info-modal-title">
|
||||
<Intl
|
||||
i18n={i18n}
|
||||
id="icu:calling__you-have-blocked"
|
||||
components={{
|
||||
name: <ContactName key="name" title={title} />,
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
errorDialogBody = i18n('icu:calling__block-info');
|
||||
} else if (showMissingMediaKeys) {
|
||||
noVideoNode = (
|
||||
<>
|
||||
<i className="module-ongoing-call__group-call-remote-participant__error-icon module-ongoing-call__group-call-remote-participant__error-icon--missing-media-keys" />
|
||||
<div className="module-ongoing-call__group-call-remote-participant__error">
|
||||
{i18n('icu:calling__missing-media-keys', { name: title })}
|
||||
</div>
|
||||
{showDialogButton}
|
||||
</>
|
||||
);
|
||||
errorDialogTitle = (
|
||||
<div className="module-ongoing-call__group-call-remote-participant__more-info-modal-title">
|
||||
<Intl
|
||||
i18n={i18n}
|
||||
id="icu:calling__missing-media-keys"
|
||||
components={{
|
||||
name: <ContactName key="name" title={title} />,
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
errorDialogBody = i18n('icu:calling__missing-media-keys-info');
|
||||
} else {
|
||||
noVideoNode = (
|
||||
<Avatar
|
||||
acceptedMessageRequest={acceptedMessageRequest}
|
||||
avatarPath={avatarPath}
|
||||
badge={undefined}
|
||||
color={color || AvatarColors[0]}
|
||||
noteToSelf={false}
|
||||
conversationType="direct"
|
||||
i18n={i18n}
|
||||
isMe={isMe}
|
||||
profileName={profileName}
|
||||
title={title}
|
||||
sharedGroupNames={sharedGroupNames}
|
||||
size={avatarSize}
|
||||
/>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
{showBlockInfo && (
|
||||
{showErrorDialog && (
|
||||
<ConfirmationDialog
|
||||
dialogName="GroupCallRemoteParticipant.blockInfo"
|
||||
cancelText={i18n('icu:ok')}
|
||||
i18n={i18n}
|
||||
onClose={() => {
|
||||
setShowBlockInfo(false);
|
||||
}}
|
||||
title={
|
||||
<div className="module-ongoing-call__group-call-remote-participant__blocked--modal-title">
|
||||
<Intl
|
||||
i18n={i18n}
|
||||
id="icu:calling__you-have-blocked"
|
||||
components={{
|
||||
name: <ContactName key="name" title={title} />,
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
}
|
||||
onClose={() => setShowErrorDialog(false)}
|
||||
theme={Theme.Dark}
|
||||
title={errorDialogTitle}
|
||||
>
|
||||
{i18n('icu:calling__block-info')}
|
||||
{errorDialogBody}
|
||||
</ConfirmationDialog>
|
||||
)}
|
||||
|
||||
|
@ -372,40 +447,12 @@ export const GroupCallRemoteParticipant: React.FC<PropsType> = React.memo(
|
|||
}}
|
||||
/>
|
||||
)}
|
||||
{!hasVideoToShow && (
|
||||
{noVideoNode && (
|
||||
<CallBackgroundBlur
|
||||
avatarPath={avatarPath}
|
||||
className="module-ongoing-call__group-call-remote-participant-background"
|
||||
>
|
||||
{isBlocked ? (
|
||||
<>
|
||||
<i className="module-ongoing-call__group-call-remote-participant__blocked" />
|
||||
<button
|
||||
type="button"
|
||||
className="module-ongoing-call__group-call-remote-participant__blocked--info"
|
||||
onClick={() => {
|
||||
setShowBlockInfo(true);
|
||||
}}
|
||||
>
|
||||
{i18n('icu:moreInfo')}
|
||||
</button>
|
||||
</>
|
||||
) : (
|
||||
<Avatar
|
||||
acceptedMessageRequest={acceptedMessageRequest}
|
||||
avatarPath={avatarPath}
|
||||
badge={undefined}
|
||||
color={color || AvatarColors[0]}
|
||||
noteToSelf={false}
|
||||
conversationType="direct"
|
||||
i18n={i18n}
|
||||
isMe={isMe}
|
||||
profileName={profileName}
|
||||
title={title}
|
||||
sharedGroupNames={sharedGroupNames}
|
||||
size={avatarSize}
|
||||
/>
|
||||
)}
|
||||
{noVideoNode}
|
||||
</CallBackgroundBlur>
|
||||
)}
|
||||
</div>
|
||||
|
|
|
@ -1086,11 +1086,14 @@ export class CallingClass {
|
|||
aci = '00000000-0000-4000-8000-000000000000';
|
||||
}
|
||||
assertDev(isAciString(aci), 'remote participant aci must be a aci');
|
||||
|
||||
return {
|
||||
aci,
|
||||
addedTime: normalizeGroupCallTimestamp(remoteDeviceState.addedTime),
|
||||
demuxId: remoteDeviceState.demuxId,
|
||||
hasRemoteAudio: !remoteDeviceState.audioMuted,
|
||||
hasRemoteVideo: !remoteDeviceState.videoMuted,
|
||||
mediaKeysReceived: remoteDeviceState.mediaKeysReceived,
|
||||
presenting: Boolean(remoteDeviceState.presenting),
|
||||
sharingScreen: Boolean(remoteDeviceState.sharingScreen),
|
||||
speakerTime: normalizeGroupCallTimestamp(
|
||||
|
|
|
@ -76,9 +76,11 @@ export type GroupCallPeekInfoType = ReadonlyDeep<{
|
|||
// eslint-disable-next-line local-rules/type-alias-readonlydeep
|
||||
export type GroupCallParticipantInfoType = {
|
||||
aci: AciString;
|
||||
addedTime?: number;
|
||||
demuxId: number;
|
||||
hasRemoteAudio: boolean;
|
||||
hasRemoteVideo: boolean;
|
||||
mediaKeysReceived: boolean;
|
||||
presenting: boolean;
|
||||
sharingScreen: boolean;
|
||||
speakerTime?: number;
|
||||
|
|
|
@ -246,10 +246,12 @@ const mapStateToActiveCallProp = (
|
|||
remoteParticipants.push({
|
||||
...remoteConversation,
|
||||
aci: remoteParticipant.aci,
|
||||
addedTime: remoteParticipant.addedTime,
|
||||
demuxId: remoteParticipant.demuxId,
|
||||
hasRemoteAudio: remoteParticipant.hasRemoteAudio,
|
||||
hasRemoteVideo: remoteParticipant.hasRemoteVideo,
|
||||
isHandRaised: raisedHands.has(remoteParticipant.demuxId),
|
||||
mediaKeysReceived: remoteParticipant.mediaKeysReceived,
|
||||
presenting: remoteParticipant.presenting,
|
||||
sharingScreen: remoteParticipant.sharingScreen,
|
||||
speakerTime: remoteParticipant.speakerTime,
|
||||
|
|
|
@ -118,6 +118,7 @@ describe('calling duck', () => {
|
|||
demuxId: 123,
|
||||
hasRemoteAudio: true,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 4 / 3,
|
||||
|
@ -906,6 +907,7 @@ describe('calling duck', () => {
|
|||
demuxId: 123,
|
||||
hasRemoteAudio: true,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 4 / 3,
|
||||
|
@ -935,6 +937,7 @@ describe('calling duck', () => {
|
|||
demuxId: 123,
|
||||
hasRemoteAudio: true,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 4 / 3,
|
||||
|
@ -966,6 +969,7 @@ describe('calling duck', () => {
|
|||
demuxId: 456,
|
||||
hasRemoteAudio: false,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 16 / 9,
|
||||
|
@ -993,6 +997,7 @@ describe('calling duck', () => {
|
|||
demuxId: 456,
|
||||
hasRemoteAudio: false,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 16 / 9,
|
||||
|
@ -1037,6 +1042,7 @@ describe('calling duck', () => {
|
|||
demuxId: 456,
|
||||
hasRemoteAudio: false,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 16 / 9,
|
||||
|
@ -1089,6 +1095,7 @@ describe('calling duck', () => {
|
|||
demuxId: 456,
|
||||
hasRemoteAudio: false,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 16 / 9,
|
||||
|
@ -1128,6 +1135,7 @@ describe('calling duck', () => {
|
|||
demuxId: 456,
|
||||
hasRemoteAudio: false,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 16 / 9,
|
||||
|
@ -1160,6 +1168,7 @@ describe('calling duck', () => {
|
|||
demuxId: 456,
|
||||
hasRemoteAudio: false,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 16 / 9,
|
||||
|
@ -1204,6 +1213,7 @@ describe('calling duck', () => {
|
|||
demuxId: 456,
|
||||
hasRemoteAudio: false,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 16 / 9,
|
||||
|
@ -1882,6 +1892,7 @@ describe('calling duck', () => {
|
|||
demuxId: 123,
|
||||
hasRemoteAudio: true,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 4 / 3,
|
||||
|
@ -1908,6 +1919,7 @@ describe('calling duck', () => {
|
|||
demuxId: 123,
|
||||
hasRemoteAudio: true,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 4 / 3,
|
||||
|
@ -1954,6 +1966,7 @@ describe('calling duck', () => {
|
|||
demuxId: 123,
|
||||
hasRemoteAudio: true,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 4 / 3,
|
||||
|
@ -2004,6 +2017,7 @@ describe('calling duck', () => {
|
|||
demuxId: 123,
|
||||
hasRemoteAudio: true,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 4 / 3,
|
||||
|
@ -2048,6 +2062,7 @@ describe('calling duck', () => {
|
|||
demuxId: 123,
|
||||
hasRemoteAudio: true,
|
||||
hasRemoteVideo: true,
|
||||
mediaKeysReceived: true,
|
||||
presenting: false,
|
||||
sharingScreen: false,
|
||||
videoAspectRatio: 4 / 3,
|
||||
|
|
|
@ -156,10 +156,12 @@ export enum GroupCallJoinState {
|
|||
|
||||
export type GroupCallRemoteParticipantType = ConversationType & {
|
||||
aci: AciString;
|
||||
addedTime?: number;
|
||||
demuxId: number;
|
||||
hasRemoteAudio: boolean;
|
||||
hasRemoteVideo: boolean;
|
||||
isHandRaised: boolean;
|
||||
mediaKeysReceived: boolean;
|
||||
presenting: boolean;
|
||||
sharingScreen: boolean;
|
||||
speakerTime?: number;
|
||||
|
|
Loading…
Reference in a new issue