View contact modal from call participants list
This commit is contained in:
		
					parent
					
						
							
								49a6fa6007
							
						
					
				
			
			
				commit
				
					
						378bd7487f
					
				
			
		
					 13 changed files with 233 additions and 62 deletions
				
			
		| 
						 | 
					@ -3686,6 +3686,10 @@
 | 
				
			||||||
    "messageformat": "A window",
 | 
					    "messageformat": "A window",
 | 
				
			||||||
    "description": "Title for the select your screen sharing sources modal"
 | 
					    "description": "Title for the select your screen sharing sources modal"
 | 
				
			||||||
  },
 | 
					  },
 | 
				
			||||||
 | 
					  "icu:calling__ParticipantInfoButton": {
 | 
				
			||||||
 | 
					    "messageformat": "More info about this contact",
 | 
				
			||||||
 | 
					    "description": "Aria label for clickable contact info button in the in-call participant info popup. When clicked a popup appears with the contact's details and options to message them."
 | 
				
			||||||
 | 
					  },
 | 
				
			||||||
  "icu:CallingAdhocCallInfo__CopyLink": {
 | 
					  "icu:CallingAdhocCallInfo__CopyLink": {
 | 
				
			||||||
    "messageformat": "Copy call link",
 | 
					    "messageformat": "Copy call link",
 | 
				
			||||||
    "description": "Menu item in the in-call info popup for call link calls. The action is to add the call link to the clipboard."
 | 
					    "description": "Menu item in the in-call info popup for call link calls. The action is to add the call link to the clipboard."
 | 
				
			||||||
| 
						 | 
					@ -4666,6 +4670,10 @@
 | 
				
			||||||
    "messageformat": "Remove from group",
 | 
					    "messageformat": "Remove from group",
 | 
				
			||||||
    "description": "Button text for remove from group button in Group Contact Details modal"
 | 
					    "description": "Button text for remove from group button in Group Contact Details modal"
 | 
				
			||||||
  },
 | 
					  },
 | 
				
			||||||
 | 
					  "icu:ContactModal--already-in-call": {
 | 
				
			||||||
 | 
					    "messageformat": "You are already in a call",
 | 
				
			||||||
 | 
					    "description": "Tooltip text for video or audio call button in Contact Details modal"
 | 
				
			||||||
 | 
					  },
 | 
				
			||||||
  "icu:showChatColorEditor": {
 | 
					  "icu:showChatColorEditor": {
 | 
				
			||||||
    "messageformat": "Chat color",
 | 
					    "messageformat": "Chat color",
 | 
				
			||||||
    "description": "This is a button in the conversation context menu to show the chat color editor"
 | 
					    "description": "This is a button in the conversation context menu to show the chat color editor"
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -4450,17 +4450,23 @@ button.module-image__border-overlay:focus {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  &__contact {
 | 
					  &__contact {
 | 
				
			||||||
    @include font-body-1;
 | 
					    @include font-body-1;
 | 
				
			||||||
 | 
					    @include button-reset;
 | 
				
			||||||
    display: flex;
 | 
					    display: flex;
 | 
				
			||||||
    align-items: center;
 | 
					    align-items: center;
 | 
				
			||||||
 | 
					    width: 100%;
 | 
				
			||||||
    margin-block: 2px;
 | 
					    margin-block: 2px;
 | 
				
			||||||
    padding-block: 8px;
 | 
					    padding-block: 8px;
 | 
				
			||||||
    padding-inline-start: 10px;
 | 
					    padding-inline-start: 10px;
 | 
				
			||||||
    padding-inline-end: 2px;
 | 
					    padding-inline-end: 2px;
 | 
				
			||||||
    list-style-type: none;
 | 
					    list-style-type: none;
 | 
				
			||||||
    border-radius: 6px;
 | 
					    border-radius: 6px;
 | 
				
			||||||
 | 
					    cursor: auto;
 | 
				
			||||||
    &:hover {
 | 
					    &:hover {
 | 
				
			||||||
      background-color: $color-gray-62;
 | 
					      background-color: $color-gray-62;
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					    &[disabled] {
 | 
				
			||||||
 | 
					      cursor: auto;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  &__avatar-and-name {
 | 
					  &__avatar-and-name {
 | 
				
			||||||
| 
						 | 
					@ -4551,6 +4557,10 @@ button.module-image__border-overlay:focus {
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					button.module-calling-participants-list__contact {
 | 
				
			||||||
 | 
					  cursor: pointer;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
.module-call-need-permission-screen {
 | 
					.module-call-need-permission-screen {
 | 
				
			||||||
  align-items: center;
 | 
					  align-items: center;
 | 
				
			||||||
  background-color: $color-gray-95;
 | 
					  background-color: $color-gray-95;
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -309,4 +309,8 @@
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    margin-block: 8px 5px;
 | 
					    margin-block: 8px 5px;
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  &__tooltip {
 | 
				
			||||||
 | 
					    @include tooltip;
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -113,6 +113,7 @@ const createProps = (storyProps: Partial<PropsType> = {}): PropsType => ({
 | 
				
			||||||
  setPresenting: action('toggle-presenting'),
 | 
					  setPresenting: action('toggle-presenting'),
 | 
				
			||||||
  setRendererCanvas: action('set-renderer-canvas'),
 | 
					  setRendererCanvas: action('set-renderer-canvas'),
 | 
				
			||||||
  setOutgoingRing: action('set-outgoing-ring'),
 | 
					  setOutgoingRing: action('set-outgoing-ring'),
 | 
				
			||||||
 | 
					  showContactModal: action('show-contact-modal'),
 | 
				
			||||||
  showShareCallLinkViaSignal: action('show-share-call-link-via-signal'),
 | 
					  showShareCallLinkViaSignal: action('show-share-call-link-via-signal'),
 | 
				
			||||||
  startCall: action('start-call'),
 | 
					  startCall: action('start-call'),
 | 
				
			||||||
  stopRingtone: action('stop-ringtone'),
 | 
					  stopRingtone: action('stop-ringtone'),
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -96,6 +96,7 @@ export type PropsType = {
 | 
				
			||||||
  renderReactionPicker: (
 | 
					  renderReactionPicker: (
 | 
				
			||||||
    props: React.ComponentProps<typeof SmartReactionPicker>
 | 
					    props: React.ComponentProps<typeof SmartReactionPicker>
 | 
				
			||||||
  ) => JSX.Element;
 | 
					  ) => JSX.Element;
 | 
				
			||||||
 | 
					  showContactModal: (contactId: string, conversationId?: string) => void;
 | 
				
			||||||
  startCall: (payload: StartCallType) => void;
 | 
					  startCall: (payload: StartCallType) => void;
 | 
				
			||||||
  toggleParticipants: () => void;
 | 
					  toggleParticipants: () => void;
 | 
				
			||||||
  acceptCall: (_: AcceptCallType) => void;
 | 
					  acceptCall: (_: AcceptCallType) => void;
 | 
				
			||||||
| 
						 | 
					@ -188,6 +189,7 @@ function ActiveCallManager({
 | 
				
			||||||
  setPresenting,
 | 
					  setPresenting,
 | 
				
			||||||
  setRendererCanvas,
 | 
					  setRendererCanvas,
 | 
				
			||||||
  setOutgoingRing,
 | 
					  setOutgoingRing,
 | 
				
			||||||
 | 
					  showContactModal,
 | 
				
			||||||
  showShareCallLinkViaSignal,
 | 
					  showShareCallLinkViaSignal,
 | 
				
			||||||
  startCall,
 | 
					  startCall,
 | 
				
			||||||
  switchToPresentationView,
 | 
					  switchToPresentationView,
 | 
				
			||||||
| 
						 | 
					@ -395,13 +397,16 @@ function ActiveCallManager({
 | 
				
			||||||
              onCopyCallLink={onCopyCallLink}
 | 
					              onCopyCallLink={onCopyCallLink}
 | 
				
			||||||
              onShareCallLinkViaSignal={handleShareCallLinkViaSignal}
 | 
					              onShareCallLinkViaSignal={handleShareCallLinkViaSignal}
 | 
				
			||||||
              removeClient={removeClient}
 | 
					              removeClient={removeClient}
 | 
				
			||||||
 | 
					              showContactModal={showContactModal}
 | 
				
			||||||
            />
 | 
					            />
 | 
				
			||||||
          ) : (
 | 
					          ) : (
 | 
				
			||||||
            <CallingParticipantsList
 | 
					            <CallingParticipantsList
 | 
				
			||||||
 | 
					              conversationId={conversation.id}
 | 
				
			||||||
              i18n={i18n}
 | 
					              i18n={i18n}
 | 
				
			||||||
              onClose={toggleParticipants}
 | 
					              onClose={toggleParticipants}
 | 
				
			||||||
              ourServiceId={me.serviceId}
 | 
					              ourServiceId={me.serviceId}
 | 
				
			||||||
              participants={peekedParticipants}
 | 
					              participants={peekedParticipants}
 | 
				
			||||||
 | 
					              showContactModal={showContactModal}
 | 
				
			||||||
            />
 | 
					            />
 | 
				
			||||||
          ))}
 | 
					          ))}
 | 
				
			||||||
      </>
 | 
					      </>
 | 
				
			||||||
| 
						 | 
					@ -489,13 +494,16 @@ function ActiveCallManager({
 | 
				
			||||||
            onCopyCallLink={onCopyCallLink}
 | 
					            onCopyCallLink={onCopyCallLink}
 | 
				
			||||||
            onShareCallLinkViaSignal={handleShareCallLinkViaSignal}
 | 
					            onShareCallLinkViaSignal={handleShareCallLinkViaSignal}
 | 
				
			||||||
            removeClient={removeClient}
 | 
					            removeClient={removeClient}
 | 
				
			||||||
 | 
					            showContactModal={showContactModal}
 | 
				
			||||||
          />
 | 
					          />
 | 
				
			||||||
        ) : (
 | 
					        ) : (
 | 
				
			||||||
          <CallingParticipantsList
 | 
					          <CallingParticipantsList
 | 
				
			||||||
 | 
					            conversationId={conversation.id}
 | 
				
			||||||
            i18n={i18n}
 | 
					            i18n={i18n}
 | 
				
			||||||
            onClose={toggleParticipants}
 | 
					            onClose={toggleParticipants}
 | 
				
			||||||
            ourServiceId={me.serviceId}
 | 
					            ourServiceId={me.serviceId}
 | 
				
			||||||
            participants={groupCallParticipantsForParticipantsList}
 | 
					            participants={groupCallParticipantsForParticipantsList}
 | 
				
			||||||
 | 
					            showContactModal={showContactModal}
 | 
				
			||||||
          />
 | 
					          />
 | 
				
			||||||
        ))}
 | 
					        ))}
 | 
				
			||||||
    </>
 | 
					    </>
 | 
				
			||||||
| 
						 | 
					@ -543,6 +551,7 @@ export function CallManager({
 | 
				
			||||||
  setOutgoingRing,
 | 
					  setOutgoingRing,
 | 
				
			||||||
  setPresenting,
 | 
					  setPresenting,
 | 
				
			||||||
  setRendererCanvas,
 | 
					  setRendererCanvas,
 | 
				
			||||||
 | 
					  showContactModal,
 | 
				
			||||||
  showShareCallLinkViaSignal,
 | 
					  showShareCallLinkViaSignal,
 | 
				
			||||||
  startCall,
 | 
					  startCall,
 | 
				
			||||||
  stopRingtone,
 | 
					  stopRingtone,
 | 
				
			||||||
| 
						 | 
					@ -633,6 +642,7 @@ export function CallManager({
 | 
				
			||||||
          setOutgoingRing={setOutgoingRing}
 | 
					          setOutgoingRing={setOutgoingRing}
 | 
				
			||||||
          setPresenting={setPresenting}
 | 
					          setPresenting={setPresenting}
 | 
				
			||||||
          setRendererCanvas={setRendererCanvas}
 | 
					          setRendererCanvas={setRendererCanvas}
 | 
				
			||||||
 | 
					          showContactModal={showContactModal}
 | 
				
			||||||
          showShareCallLinkViaSignal={showShareCallLinkViaSignal}
 | 
					          showShareCallLinkViaSignal={showShareCallLinkViaSignal}
 | 
				
			||||||
          startCall={startCall}
 | 
					          startCall={startCall}
 | 
				
			||||||
          switchFromPresentationView={switchFromPresentationView}
 | 
					          switchFromPresentationView={switchFromPresentationView}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -68,6 +68,7 @@ const createProps = (overrideProps: Partial<PropsType> = {}): PropsType => ({
 | 
				
			||||||
  onCopyCallLink: action('on-copy-call-link'),
 | 
					  onCopyCallLink: action('on-copy-call-link'),
 | 
				
			||||||
  onShareCallLinkViaSignal: action('on-share-call-link-via-signal'),
 | 
					  onShareCallLinkViaSignal: action('on-share-call-link-via-signal'),
 | 
				
			||||||
  removeClient: overrideProps.removeClient || action('remove-client'),
 | 
					  removeClient: overrideProps.removeClient || action('remove-client'),
 | 
				
			||||||
 | 
					  showContactModal: action('show-contact-modal'),
 | 
				
			||||||
});
 | 
					});
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export default {
 | 
					export default {
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -41,6 +41,10 @@ export type PropsType = {
 | 
				
			||||||
  readonly onCopyCallLink: () => void;
 | 
					  readonly onCopyCallLink: () => void;
 | 
				
			||||||
  readonly onShareCallLinkViaSignal: () => void;
 | 
					  readonly onShareCallLinkViaSignal: () => void;
 | 
				
			||||||
  readonly removeClient: ((payload: RemoveClientType) => void) | null;
 | 
					  readonly removeClient: ((payload: RemoveClientType) => void) | null;
 | 
				
			||||||
 | 
					  readonly showContactModal: (
 | 
				
			||||||
 | 
					    contactId: string,
 | 
				
			||||||
 | 
					    conversationId?: string
 | 
				
			||||||
 | 
					  ) => void;
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
type UnknownContactsPropsType = {
 | 
					type UnknownContactsPropsType = {
 | 
				
			||||||
| 
						 | 
					@ -145,6 +149,7 @@ export function CallingAdhocCallInfo({
 | 
				
			||||||
  onCopyCallLink,
 | 
					  onCopyCallLink,
 | 
				
			||||||
  onShareCallLinkViaSignal,
 | 
					  onShareCallLinkViaSignal,
 | 
				
			||||||
  removeClient,
 | 
					  removeClient,
 | 
				
			||||||
 | 
					  showContactModal,
 | 
				
			||||||
}: PropsType): JSX.Element | null {
 | 
					}: PropsType): JSX.Element | null {
 | 
				
			||||||
  const [isUnknownContactDialogVisible, setIsUnknownContactDialogVisible] =
 | 
					  const [isUnknownContactDialogVisible, setIsUnknownContactDialogVisible] =
 | 
				
			||||||
    React.useState(false);
 | 
					    React.useState(false);
 | 
				
			||||||
| 
						 | 
					@ -173,12 +178,23 @@ export function CallingAdhocCallInfo({
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  const renderParticipant = React.useCallback(
 | 
					  const renderParticipant = React.useCallback(
 | 
				
			||||||
    (participant: ParticipantType, key: React.Key) => (
 | 
					    (participant: ParticipantType, key: React.Key) => (
 | 
				
			||||||
      <li
 | 
					      <button
 | 
				
			||||||
 | 
					        aria-label={i18n('icu:calling__ParticipantInfoButton')}
 | 
				
			||||||
        className="module-calling-participants-list__contact"
 | 
					        className="module-calling-participants-list__contact"
 | 
				
			||||||
 | 
					        disabled={participant.isMe}
 | 
				
			||||||
        // It's tempting to use `participant.serviceId` as the `key`
 | 
					        // It's tempting to use `participant.serviceId` as the `key`
 | 
				
			||||||
        //   here, but that can result in duplicate keys for
 | 
					        //   here, but that can result in duplicate keys for
 | 
				
			||||||
        //   participants who have joined on multiple devices.
 | 
					        //   participants who have joined on multiple devices.
 | 
				
			||||||
        key={key}
 | 
					        key={key}
 | 
				
			||||||
 | 
					        onClick={() => {
 | 
				
			||||||
 | 
					          if (participant.isMe) {
 | 
				
			||||||
 | 
					            return;
 | 
				
			||||||
 | 
					          }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					          onClose();
 | 
				
			||||||
 | 
					          showContactModal(participant.id);
 | 
				
			||||||
 | 
					        }}
 | 
				
			||||||
 | 
					        type="button"
 | 
				
			||||||
      >
 | 
					      >
 | 
				
			||||||
        <div className="module-calling-participants-list__avatar-and-name">
 | 
					        <div className="module-calling-participants-list__avatar-and-name">
 | 
				
			||||||
          <Avatar
 | 
					          <Avatar
 | 
				
			||||||
| 
						 | 
					@ -250,18 +266,28 @@ export function CallingAdhocCallInfo({
 | 
				
			||||||
              'module-calling-participants-list__status-icon',
 | 
					              'module-calling-participants-list__status-icon',
 | 
				
			||||||
              'module-calling-participants-list__remove'
 | 
					              'module-calling-participants-list__remove'
 | 
				
			||||||
            )}
 | 
					            )}
 | 
				
			||||||
            onClick={() => {
 | 
					            onClick={event => {
 | 
				
			||||||
              if (!participant.demuxId) {
 | 
					              if (!participant.demuxId) {
 | 
				
			||||||
                return;
 | 
					                return;
 | 
				
			||||||
              }
 | 
					              }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					              event.stopPropagation();
 | 
				
			||||||
 | 
					              event.preventDefault();
 | 
				
			||||||
              removeClient({ demuxId: participant.demuxId });
 | 
					              removeClient({ demuxId: participant.demuxId });
 | 
				
			||||||
            }}
 | 
					            }}
 | 
				
			||||||
            type="button"
 | 
					            type="button"
 | 
				
			||||||
          />
 | 
					          />
 | 
				
			||||||
        ) : null}
 | 
					        ) : null}
 | 
				
			||||||
      </li>
 | 
					      </button>
 | 
				
			||||||
    ),
 | 
					    ),
 | 
				
			||||||
    [i18n, isCallLinkAdmin, ourServiceId, removeClient]
 | 
					    [
 | 
				
			||||||
 | 
					      i18n,
 | 
				
			||||||
 | 
					      isCallLinkAdmin,
 | 
				
			||||||
 | 
					      onClose,
 | 
				
			||||||
 | 
					      ourServiceId,
 | 
				
			||||||
 | 
					      removeClient,
 | 
				
			||||||
 | 
					      showContactModal,
 | 
				
			||||||
 | 
					    ]
 | 
				
			||||||
  );
 | 
					  );
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  return (
 | 
					  return (
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -43,9 +43,11 @@ function createParticipant(
 | 
				
			||||||
 | 
					
 | 
				
			||||||
const createProps = (overrideProps: Partial<PropsType> = {}): PropsType => ({
 | 
					const createProps = (overrideProps: Partial<PropsType> = {}): PropsType => ({
 | 
				
			||||||
  i18n,
 | 
					  i18n,
 | 
				
			||||||
 | 
					  conversationId: 'fake-conversation-id',
 | 
				
			||||||
  onClose: action('on-close'),
 | 
					  onClose: action('on-close'),
 | 
				
			||||||
  ourServiceId: generateAci(),
 | 
					  ourServiceId: generateAci(),
 | 
				
			||||||
  participants: overrideProps.participants || [],
 | 
					  participants: overrideProps.participants || [],
 | 
				
			||||||
 | 
					  showContactModal: action('show-contact-modal'),
 | 
				
			||||||
});
 | 
					});
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export default {
 | 
					export default {
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -26,18 +26,25 @@ type ParticipantType = ConversationType & {
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export type PropsType = {
 | 
					export type PropsType = {
 | 
				
			||||||
 | 
					  readonly conversationId: string;
 | 
				
			||||||
  readonly i18n: LocalizerType;
 | 
					  readonly i18n: LocalizerType;
 | 
				
			||||||
  readonly onClose: () => void;
 | 
					  readonly onClose: () => void;
 | 
				
			||||||
  readonly ourServiceId: ServiceIdString | undefined;
 | 
					  readonly ourServiceId: ServiceIdString | undefined;
 | 
				
			||||||
  readonly participants: Array<ParticipantType>;
 | 
					  readonly participants: Array<ParticipantType>;
 | 
				
			||||||
 | 
					  readonly showContactModal: (
 | 
				
			||||||
 | 
					    contactId: string,
 | 
				
			||||||
 | 
					    conversationId?: string
 | 
				
			||||||
 | 
					  ) => void;
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export const CallingParticipantsList = React.memo(
 | 
					export const CallingParticipantsList = React.memo(
 | 
				
			||||||
  function CallingParticipantsListInner({
 | 
					  function CallingParticipantsListInner({
 | 
				
			||||||
 | 
					    conversationId,
 | 
				
			||||||
    i18n,
 | 
					    i18n,
 | 
				
			||||||
    onClose,
 | 
					    onClose,
 | 
				
			||||||
    ourServiceId,
 | 
					    ourServiceId,
 | 
				
			||||||
    participants,
 | 
					    participants,
 | 
				
			||||||
 | 
					    showContactModal,
 | 
				
			||||||
  }: PropsType) {
 | 
					  }: PropsType) {
 | 
				
			||||||
    const [root, setRoot] = React.useState<HTMLElement | null>(null);
 | 
					    const [root, setRoot] = React.useState<HTMLElement | null>(null);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -96,15 +103,26 @@ export const CallingParticipantsList = React.memo(
 | 
				
			||||||
                aria-label={i18n('icu:close')}
 | 
					                aria-label={i18n('icu:close')}
 | 
				
			||||||
              />
 | 
					              />
 | 
				
			||||||
            </div>
 | 
					            </div>
 | 
				
			||||||
            <ul className="module-calling-participants-list__list">
 | 
					            <div className="module-calling-participants-list__list">
 | 
				
			||||||
              {sortedParticipants.map(
 | 
					              {sortedParticipants.map(
 | 
				
			||||||
                (participant: ParticipantType, index: number) => (
 | 
					                (participant: ParticipantType, index: number) => (
 | 
				
			||||||
                  <li
 | 
					                  <button
 | 
				
			||||||
 | 
					                    aria-label={i18n('icu:calling__ParticipantInfoButton')}
 | 
				
			||||||
                    className="module-calling-participants-list__contact"
 | 
					                    className="module-calling-participants-list__contact"
 | 
				
			||||||
 | 
					                    disabled={participant.isMe}
 | 
				
			||||||
                    // It's tempting to use `participant.serviceId` as the `key`
 | 
					                    // It's tempting to use `participant.serviceId` as the `key`
 | 
				
			||||||
                    //   here, but that can result in duplicate keys for
 | 
					                    //   here, but that can result in duplicate keys for
 | 
				
			||||||
                    //   participants who have joined on multiple devices.
 | 
					                    //   participants who have joined on multiple devices.
 | 
				
			||||||
                    key={index}
 | 
					                    key={index}
 | 
				
			||||||
 | 
					                    onClick={() => {
 | 
				
			||||||
 | 
					                      if (participant.isMe) {
 | 
				
			||||||
 | 
					                        return;
 | 
				
			||||||
 | 
					                      }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					                      onClose();
 | 
				
			||||||
 | 
					                      showContactModal(participant.id, conversationId);
 | 
				
			||||||
 | 
					                    }}
 | 
				
			||||||
 | 
					                    type="button"
 | 
				
			||||||
                  >
 | 
					                  >
 | 
				
			||||||
                    <div className="module-calling-participants-list__avatar-and-name">
 | 
					                    <div className="module-calling-participants-list__avatar-and-name">
 | 
				
			||||||
                      <Avatar
 | 
					                      <Avatar
 | 
				
			||||||
| 
						 | 
					@ -165,10 +183,10 @@ export const CallingParticipantsList = React.memo(
 | 
				
			||||||
                          'module-calling-participants-list__muted--audio'
 | 
					                          'module-calling-participants-list__muted--audio'
 | 
				
			||||||
                      )}
 | 
					                      )}
 | 
				
			||||||
                    />
 | 
					                    />
 | 
				
			||||||
                  </li>
 | 
					                  </button>
 | 
				
			||||||
                )
 | 
					                )
 | 
				
			||||||
              )}
 | 
					              )}
 | 
				
			||||||
            </ul>
 | 
					            </div>
 | 
				
			||||||
          </div>
 | 
					          </div>
 | 
				
			||||||
        </div>
 | 
					        </div>
 | 
				
			||||||
      </FocusTrap>,
 | 
					      </FocusTrap>,
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -26,6 +26,9 @@ import { Button, ButtonIconType, ButtonVariant } from '../Button';
 | 
				
			||||||
import { isInSystemContacts } from '../../util/isInSystemContacts';
 | 
					import { isInSystemContacts } from '../../util/isInSystemContacts';
 | 
				
			||||||
import { InContactsIcon } from '../InContactsIcon';
 | 
					import { InContactsIcon } from '../InContactsIcon';
 | 
				
			||||||
import { canHaveNicknameAndNote } from '../../util/nicknames';
 | 
					import { canHaveNicknameAndNote } from '../../util/nicknames';
 | 
				
			||||||
 | 
					import { Tooltip, TooltipPlacement } from '../Tooltip';
 | 
				
			||||||
 | 
					import { offsetDistanceModifier } from '../../util/popperUtil';
 | 
				
			||||||
 | 
					import { getThemeByThemeType } from '../../util/theme';
 | 
				
			||||||
 | 
					
 | 
				
			||||||
export type PropsDataType = {
 | 
					export type PropsDataType = {
 | 
				
			||||||
  areWeASubscriber: boolean;
 | 
					  areWeASubscriber: boolean;
 | 
				
			||||||
| 
						 | 
					@ -39,6 +42,7 @@ export type PropsDataType = {
 | 
				
			||||||
  isMember: boolean;
 | 
					  isMember: boolean;
 | 
				
			||||||
  theme: ThemeType;
 | 
					  theme: ThemeType;
 | 
				
			||||||
  hasActiveCall: boolean;
 | 
					  hasActiveCall: boolean;
 | 
				
			||||||
 | 
					  isInFullScreenCall: boolean;
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
type PropsActionType = {
 | 
					type PropsActionType = {
 | 
				
			||||||
| 
						 | 
					@ -51,6 +55,7 @@ type PropsActionType = {
 | 
				
			||||||
  showConversation: ShowConversationType;
 | 
					  showConversation: ShowConversationType;
 | 
				
			||||||
  toggleAdmin: (conversationId: string, contactId: string) => void;
 | 
					  toggleAdmin: (conversationId: string, contactId: string) => void;
 | 
				
			||||||
  toggleAboutContactModal: (conversationId: string) => unknown;
 | 
					  toggleAboutContactModal: (conversationId: string) => unknown;
 | 
				
			||||||
 | 
					  togglePip: () => void;
 | 
				
			||||||
  toggleSafetyNumberModal: (conversationId: string) => unknown;
 | 
					  toggleSafetyNumberModal: (conversationId: string) => unknown;
 | 
				
			||||||
  toggleAddUserToAnotherGroupModal: (conversationId: string) => void;
 | 
					  toggleAddUserToAnotherGroupModal: (conversationId: string) => void;
 | 
				
			||||||
  updateConversationModelSharedGroups: (conversationId: string) => void;
 | 
					  updateConversationModelSharedGroups: (conversationId: string) => void;
 | 
				
			||||||
| 
						 | 
					@ -82,6 +87,7 @@ export function ContactModal({
 | 
				
			||||||
  hasActiveCall,
 | 
					  hasActiveCall,
 | 
				
			||||||
  hasStories,
 | 
					  hasStories,
 | 
				
			||||||
  hideContactModal,
 | 
					  hideContactModal,
 | 
				
			||||||
 | 
					  isInFullScreenCall,
 | 
				
			||||||
  i18n,
 | 
					  i18n,
 | 
				
			||||||
  isAdmin,
 | 
					  isAdmin,
 | 
				
			||||||
  isMember,
 | 
					  isMember,
 | 
				
			||||||
| 
						 | 
					@ -94,6 +100,7 @@ export function ContactModal({
 | 
				
			||||||
  toggleAboutContactModal,
 | 
					  toggleAboutContactModal,
 | 
				
			||||||
  toggleAddUserToAnotherGroupModal,
 | 
					  toggleAddUserToAnotherGroupModal,
 | 
				
			||||||
  toggleAdmin,
 | 
					  toggleAdmin,
 | 
				
			||||||
 | 
					  togglePip,
 | 
				
			||||||
  toggleSafetyNumberModal,
 | 
					  toggleSafetyNumberModal,
 | 
				
			||||||
  updateConversationModelSharedGroups,
 | 
					  updateConversationModelSharedGroups,
 | 
				
			||||||
  viewUserStories,
 | 
					  viewUserStories,
 | 
				
			||||||
| 
						 | 
					@ -106,6 +113,7 @@ export function ContactModal({
 | 
				
			||||||
  const [subModalState, setSubModalState] = useState<SubModalState>(
 | 
					  const [subModalState, setSubModalState] = useState<SubModalState>(
 | 
				
			||||||
    SubModalState.None
 | 
					    SubModalState.None
 | 
				
			||||||
  );
 | 
					  );
 | 
				
			||||||
 | 
					  const modalTheme = getThemeByThemeType(theme);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  useEffect(() => {
 | 
					  useEffect(() => {
 | 
				
			||||||
    if (contact?.id) {
 | 
					    if (contact?.id) {
 | 
				
			||||||
| 
						 | 
					@ -114,6 +122,94 @@ export function ContactModal({
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
  }, [contact?.id, updateConversationModelSharedGroups]);
 | 
					  }, [contact?.id, updateConversationModelSharedGroups]);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  const renderQuickActions = React.useCallback(
 | 
				
			||||||
 | 
					    (conversationId: string) => {
 | 
				
			||||||
 | 
					      const videoCallButton = (
 | 
				
			||||||
 | 
					        <Button
 | 
				
			||||||
 | 
					          icon={ButtonIconType.video}
 | 
				
			||||||
 | 
					          variant={ButtonVariant.Details}
 | 
				
			||||||
 | 
					          disabled={hasActiveCall}
 | 
				
			||||||
 | 
					          onClick={() => {
 | 
				
			||||||
 | 
					            hideContactModal();
 | 
				
			||||||
 | 
					            onOutgoingVideoCallInConversation(conversationId);
 | 
				
			||||||
 | 
					          }}
 | 
				
			||||||
 | 
					        >
 | 
				
			||||||
 | 
					          {i18n('icu:video')}
 | 
				
			||||||
 | 
					        </Button>
 | 
				
			||||||
 | 
					      );
 | 
				
			||||||
 | 
					      const audioCallButton = (
 | 
				
			||||||
 | 
					        <Button
 | 
				
			||||||
 | 
					          icon={ButtonIconType.audio}
 | 
				
			||||||
 | 
					          variant={ButtonVariant.Details}
 | 
				
			||||||
 | 
					          disabled={hasActiveCall}
 | 
				
			||||||
 | 
					          onClick={() => {
 | 
				
			||||||
 | 
					            hideContactModal();
 | 
				
			||||||
 | 
					            onOutgoingAudioCallInConversation(conversationId);
 | 
				
			||||||
 | 
					          }}
 | 
				
			||||||
 | 
					        >
 | 
				
			||||||
 | 
					          {i18n('icu:audio')}
 | 
				
			||||||
 | 
					        </Button>
 | 
				
			||||||
 | 
					      );
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      return (
 | 
				
			||||||
 | 
					        <div className="ContactModal__quick-actions">
 | 
				
			||||||
 | 
					          <Button
 | 
				
			||||||
 | 
					            icon={ButtonIconType.message}
 | 
				
			||||||
 | 
					            variant={ButtonVariant.Details}
 | 
				
			||||||
 | 
					            onClick={() => {
 | 
				
			||||||
 | 
					              hideContactModal();
 | 
				
			||||||
 | 
					              showConversation({
 | 
				
			||||||
 | 
					                conversationId,
 | 
				
			||||||
 | 
					                switchToAssociatedView: true,
 | 
				
			||||||
 | 
					              });
 | 
				
			||||||
 | 
					              if (isInFullScreenCall) {
 | 
				
			||||||
 | 
					                togglePip();
 | 
				
			||||||
 | 
					              }
 | 
				
			||||||
 | 
					            }}
 | 
				
			||||||
 | 
					          >
 | 
				
			||||||
 | 
					            {i18n('icu:ConversationDetails__HeaderButton--Message')}
 | 
				
			||||||
 | 
					          </Button>
 | 
				
			||||||
 | 
					          {hasActiveCall ? (
 | 
				
			||||||
 | 
					            <Tooltip
 | 
				
			||||||
 | 
					              className="ContactModal__tooltip"
 | 
				
			||||||
 | 
					              wrapperClassName="ContactModal__tooltip-wrapper"
 | 
				
			||||||
 | 
					              content={i18n('icu:ContactModal--already-in-call')}
 | 
				
			||||||
 | 
					              direction={TooltipPlacement.Top}
 | 
				
			||||||
 | 
					              popperModifiers={[offsetDistanceModifier(5)]}
 | 
				
			||||||
 | 
					            >
 | 
				
			||||||
 | 
					              {videoCallButton}
 | 
				
			||||||
 | 
					            </Tooltip>
 | 
				
			||||||
 | 
					          ) : (
 | 
				
			||||||
 | 
					            videoCallButton
 | 
				
			||||||
 | 
					          )}
 | 
				
			||||||
 | 
					          {hasActiveCall ? (
 | 
				
			||||||
 | 
					            <Tooltip
 | 
				
			||||||
 | 
					              className="ContactModal__tooltip"
 | 
				
			||||||
 | 
					              wrapperClassName="ContactModal__tooltip-wrapper"
 | 
				
			||||||
 | 
					              content={i18n('icu:ContactModal--already-in-call')}
 | 
				
			||||||
 | 
					              direction={TooltipPlacement.Top}
 | 
				
			||||||
 | 
					              popperModifiers={[offsetDistanceModifier(5)]}
 | 
				
			||||||
 | 
					            >
 | 
				
			||||||
 | 
					              {audioCallButton}
 | 
				
			||||||
 | 
					            </Tooltip>
 | 
				
			||||||
 | 
					          ) : (
 | 
				
			||||||
 | 
					            audioCallButton
 | 
				
			||||||
 | 
					          )}
 | 
				
			||||||
 | 
					        </div>
 | 
				
			||||||
 | 
					      );
 | 
				
			||||||
 | 
					    },
 | 
				
			||||||
 | 
					    [
 | 
				
			||||||
 | 
					      hasActiveCall,
 | 
				
			||||||
 | 
					      hideContactModal,
 | 
				
			||||||
 | 
					      i18n,
 | 
				
			||||||
 | 
					      isInFullScreenCall,
 | 
				
			||||||
 | 
					      onOutgoingAudioCallInConversation,
 | 
				
			||||||
 | 
					      onOutgoingVideoCallInConversation,
 | 
				
			||||||
 | 
					      showConversation,
 | 
				
			||||||
 | 
					      togglePip,
 | 
				
			||||||
 | 
					    ]
 | 
				
			||||||
 | 
					  );
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  let modalNode: ReactNode;
 | 
					  let modalNode: ReactNode;
 | 
				
			||||||
  switch (subModalState) {
 | 
					  switch (subModalState) {
 | 
				
			||||||
    case SubModalState.None:
 | 
					    case SubModalState.None:
 | 
				
			||||||
| 
						 | 
					@ -213,6 +309,7 @@ export function ContactModal({
 | 
				
			||||||
          i18n={i18n}
 | 
					          i18n={i18n}
 | 
				
			||||||
          onClose={hideContactModal}
 | 
					          onClose={hideContactModal}
 | 
				
			||||||
          padded={false}
 | 
					          padded={false}
 | 
				
			||||||
 | 
					          theme={modalTheme}
 | 
				
			||||||
        >
 | 
					        >
 | 
				
			||||||
          <div className="ContactModal">
 | 
					          <div className="ContactModal">
 | 
				
			||||||
            <Avatar
 | 
					            <Avatar
 | 
				
			||||||
| 
						 | 
					@ -265,45 +362,7 @@ export function ContactModal({
 | 
				
			||||||
              </div>
 | 
					              </div>
 | 
				
			||||||
              <i className="ContactModal__name__chevron" />
 | 
					              <i className="ContactModal__name__chevron" />
 | 
				
			||||||
            </button>
 | 
					            </button>
 | 
				
			||||||
            {!contact.isMe && (
 | 
					            {!contact.isMe && renderQuickActions(contact.id)}
 | 
				
			||||||
              <div className="ContactModal__quick-actions">
 | 
					 | 
				
			||||||
                <Button
 | 
					 | 
				
			||||||
                  icon={ButtonIconType.message}
 | 
					 | 
				
			||||||
                  variant={ButtonVariant.Details}
 | 
					 | 
				
			||||||
                  onClick={() => {
 | 
					 | 
				
			||||||
                    hideContactModal();
 | 
					 | 
				
			||||||
                    showConversation({
 | 
					 | 
				
			||||||
                      conversationId: contact?.id,
 | 
					 | 
				
			||||||
                      switchToAssociatedView: true,
 | 
					 | 
				
			||||||
                    });
 | 
					 | 
				
			||||||
                  }}
 | 
					 | 
				
			||||||
                >
 | 
					 | 
				
			||||||
                  {i18n('icu:ConversationDetails__HeaderButton--Message')}
 | 
					 | 
				
			||||||
                </Button>
 | 
					 | 
				
			||||||
                <Button
 | 
					 | 
				
			||||||
                  icon={ButtonIconType.video}
 | 
					 | 
				
			||||||
                  variant={ButtonVariant.Details}
 | 
					 | 
				
			||||||
                  disabled={hasActiveCall}
 | 
					 | 
				
			||||||
                  onClick={() => {
 | 
					 | 
				
			||||||
                    hideContactModal();
 | 
					 | 
				
			||||||
                    onOutgoingVideoCallInConversation(contact.id);
 | 
					 | 
				
			||||||
                  }}
 | 
					 | 
				
			||||||
                >
 | 
					 | 
				
			||||||
                  {i18n('icu:video')}
 | 
					 | 
				
			||||||
                </Button>
 | 
					 | 
				
			||||||
                <Button
 | 
					 | 
				
			||||||
                  icon={ButtonIconType.audio}
 | 
					 | 
				
			||||||
                  variant={ButtonVariant.Details}
 | 
					 | 
				
			||||||
                  disabled={hasActiveCall}
 | 
					 | 
				
			||||||
                  onClick={() => {
 | 
					 | 
				
			||||||
                    hideContactModal();
 | 
					 | 
				
			||||||
                    onOutgoingAudioCallInConversation(contact.id);
 | 
					 | 
				
			||||||
                  }}
 | 
					 | 
				
			||||||
                >
 | 
					 | 
				
			||||||
                  {i18n('icu:audio')}
 | 
					 | 
				
			||||||
                </Button>
 | 
					 | 
				
			||||||
              </div>
 | 
					 | 
				
			||||||
            )}
 | 
					 | 
				
			||||||
            <div className="ContactModal__divider" />
 | 
					            <div className="ContactModal__divider" />
 | 
				
			||||||
            <div className="ContactModal__button-container">
 | 
					            <div className="ContactModal__button-container">
 | 
				
			||||||
              {canHaveNicknameAndNote(contact) && (
 | 
					              {canHaveNicknameAndNote(contact) && (
 | 
				
			||||||
| 
						 | 
					@ -319,7 +378,19 @@ export function ContactModal({
 | 
				
			||||||
                </button>
 | 
					                </button>
 | 
				
			||||||
              )}
 | 
					              )}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
              {!contact.isMe && (
 | 
					              {!contact.isMe &&
 | 
				
			||||||
 | 
					                (contact.isBlocked ? (
 | 
				
			||||||
 | 
					                  <div className="ContactModal__button ContactModal__block">
 | 
				
			||||||
 | 
					                    <div className="ContactModal__bubble-icon">
 | 
				
			||||||
 | 
					                      <div className="ContactModal__block__bubble-icon" />
 | 
				
			||||||
 | 
					                    </div>
 | 
				
			||||||
 | 
					                    <span>
 | 
				
			||||||
 | 
					                      {i18n('icu:AboutContactModal__blocked', {
 | 
				
			||||||
 | 
					                        name: contact.title,
 | 
				
			||||||
 | 
					                      })}
 | 
				
			||||||
 | 
					                    </span>
 | 
				
			||||||
 | 
					                  </div>
 | 
				
			||||||
 | 
					                ) : (
 | 
				
			||||||
                  <button
 | 
					                  <button
 | 
				
			||||||
                    type="button"
 | 
					                    type="button"
 | 
				
			||||||
                    className="ContactModal__button ContactModal__block"
 | 
					                    className="ContactModal__button ContactModal__block"
 | 
				
			||||||
| 
						 | 
					@ -332,7 +403,7 @@ export function ContactModal({
 | 
				
			||||||
                    </div>
 | 
					                    </div>
 | 
				
			||||||
                    <span>{i18n('icu:MessageRequests--block')}</span>
 | 
					                    <span>{i18n('icu:MessageRequests--block')}</span>
 | 
				
			||||||
                  </button>
 | 
					                  </button>
 | 
				
			||||||
              )}
 | 
					                ))}
 | 
				
			||||||
              {!contact.isMe && (
 | 
					              {!contact.isMe && (
 | 
				
			||||||
                <button
 | 
					                <button
 | 
				
			||||||
                  type="button"
 | 
					                  type="button"
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -455,7 +455,8 @@ export const SmartCallManager = memo(function SmartCallManager() {
 | 
				
			||||||
    toggleSettings,
 | 
					    toggleSettings,
 | 
				
			||||||
  } = useCallingActions();
 | 
					  } = useCallingActions();
 | 
				
			||||||
  const { pauseVoiceNotePlayer } = useAudioPlayerActions();
 | 
					  const { pauseVoiceNotePlayer } = useAudioPlayerActions();
 | 
				
			||||||
  const { showShareCallLinkViaSignal } = useGlobalModalActions();
 | 
					  const { showContactModal, showShareCallLinkViaSignal } =
 | 
				
			||||||
 | 
					    useGlobalModalActions();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  return (
 | 
					  return (
 | 
				
			||||||
    <CallManager
 | 
					    <CallManager
 | 
				
			||||||
| 
						 | 
					@ -501,6 +502,7 @@ export const SmartCallManager = memo(function SmartCallManager() {
 | 
				
			||||||
      setOutgoingRing={setOutgoingRing}
 | 
					      setOutgoingRing={setOutgoingRing}
 | 
				
			||||||
      setPresenting={setPresenting}
 | 
					      setPresenting={setPresenting}
 | 
				
			||||||
      setRendererCanvas={setRendererCanvas}
 | 
					      setRendererCanvas={setRendererCanvas}
 | 
				
			||||||
 | 
					      showContactModal={showContactModal}
 | 
				
			||||||
      showShareCallLinkViaSignal={showShareCallLinkViaSignal}
 | 
					      showShareCallLinkViaSignal={showShareCallLinkViaSignal}
 | 
				
			||||||
      startCall={startCall}
 | 
					      startCall={startCall}
 | 
				
			||||||
      stopRingtone={stopRingtone}
 | 
					      stopRingtone={stopRingtone}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -9,7 +9,10 @@ import { getIntl, getTheme } from '../selectors/user';
 | 
				
			||||||
import { getBadgesSelector } from '../selectors/badges';
 | 
					import { getBadgesSelector } from '../selectors/badges';
 | 
				
			||||||
import { getConversationSelector } from '../selectors/conversations';
 | 
					import { getConversationSelector } from '../selectors/conversations';
 | 
				
			||||||
import { getHasStoriesSelector } from '../selectors/stories2';
 | 
					import { getHasStoriesSelector } from '../selectors/stories2';
 | 
				
			||||||
import { getActiveCallState } from '../selectors/calling';
 | 
					import {
 | 
				
			||||||
 | 
					  getActiveCallState,
 | 
				
			||||||
 | 
					  isInFullScreenCall as getIsInFullScreenCall,
 | 
				
			||||||
 | 
					} from '../selectors/calling';
 | 
				
			||||||
import { useStoriesActions } from '../ducks/stories';
 | 
					import { useStoriesActions } from '../ducks/stories';
 | 
				
			||||||
import { useConversationsActions } from '../ducks/conversations';
 | 
					import { useConversationsActions } from '../ducks/conversations';
 | 
				
			||||||
import { useGlobalModalActions } from '../ducks/globalModals';
 | 
					import { useGlobalModalActions } from '../ducks/globalModals';
 | 
				
			||||||
| 
						 | 
					@ -24,6 +27,7 @@ export const SmartContactModal = memo(function SmartContactModal() {
 | 
				
			||||||
  const conversationSelector = useSelector(getConversationSelector);
 | 
					  const conversationSelector = useSelector(getConversationSelector);
 | 
				
			||||||
  const hasStoriesSelector = useSelector(getHasStoriesSelector);
 | 
					  const hasStoriesSelector = useSelector(getHasStoriesSelector);
 | 
				
			||||||
  const activeCallState = useSelector(getActiveCallState);
 | 
					  const activeCallState = useSelector(getActiveCallState);
 | 
				
			||||||
 | 
					  const isInFullScreenCall = useSelector(getIsInFullScreenCall);
 | 
				
			||||||
  const badgesSelector = useSelector(getBadgesSelector);
 | 
					  const badgesSelector = useSelector(getBadgesSelector);
 | 
				
			||||||
  const areWeASubscriber = useSelector(getAreWeASubscriber);
 | 
					  const areWeASubscriber = useSelector(getAreWeASubscriber);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -62,6 +66,7 @@ export const SmartContactModal = memo(function SmartContactModal() {
 | 
				
			||||||
  const {
 | 
					  const {
 | 
				
			||||||
    onOutgoingVideoCallInConversation,
 | 
					    onOutgoingVideoCallInConversation,
 | 
				
			||||||
    onOutgoingAudioCallInConversation,
 | 
					    onOutgoingAudioCallInConversation,
 | 
				
			||||||
 | 
					    togglePip,
 | 
				
			||||||
  } = useCallingActions();
 | 
					  } = useCallingActions();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  const handleOpenEditNicknameAndNoteModal = useCallback(() => {
 | 
					  const handleOpenEditNicknameAndNoteModal = useCallback(() => {
 | 
				
			||||||
| 
						 | 
					@ -82,6 +87,7 @@ export const SmartContactModal = memo(function SmartContactModal() {
 | 
				
			||||||
      hideContactModal={hideContactModal}
 | 
					      hideContactModal={hideContactModal}
 | 
				
			||||||
      i18n={i18n}
 | 
					      i18n={i18n}
 | 
				
			||||||
      isAdmin={isAdmin}
 | 
					      isAdmin={isAdmin}
 | 
				
			||||||
 | 
					      isInFullScreenCall={isInFullScreenCall}
 | 
				
			||||||
      isMember={isMember}
 | 
					      isMember={isMember}
 | 
				
			||||||
      onOpenEditNicknameAndNoteModal={handleOpenEditNicknameAndNoteModal}
 | 
					      onOpenEditNicknameAndNoteModal={handleOpenEditNicknameAndNoteModal}
 | 
				
			||||||
      onOutgoingAudioCallInConversation={onOutgoingAudioCallInConversation}
 | 
					      onOutgoingAudioCallInConversation={onOutgoingAudioCallInConversation}
 | 
				
			||||||
| 
						 | 
					@ -92,6 +98,7 @@ export const SmartContactModal = memo(function SmartContactModal() {
 | 
				
			||||||
      toggleAboutContactModal={toggleAboutContactModal}
 | 
					      toggleAboutContactModal={toggleAboutContactModal}
 | 
				
			||||||
      toggleAddUserToAnotherGroupModal={toggleAddUserToAnotherGroupModal}
 | 
					      toggleAddUserToAnotherGroupModal={toggleAddUserToAnotherGroupModal}
 | 
				
			||||||
      toggleAdmin={toggleAdmin}
 | 
					      toggleAdmin={toggleAdmin}
 | 
				
			||||||
 | 
					      togglePip={togglePip}
 | 
				
			||||||
      toggleSafetyNumberModal={toggleSafetyNumberModal}
 | 
					      toggleSafetyNumberModal={toggleSafetyNumberModal}
 | 
				
			||||||
      updateConversationModelSharedGroups={updateConversationModelSharedGroups}
 | 
					      updateConversationModelSharedGroups={updateConversationModelSharedGroups}
 | 
				
			||||||
      viewUserStories={viewUserStories}
 | 
					      viewUserStories={viewUserStories}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -30,3 +30,14 @@ export function themeClassName2(theme: ThemeType): string {
 | 
				
			||||||
      throw missingCaseError(theme);
 | 
					      throw missingCaseError(theme);
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					export function getThemeByThemeType(theme: ThemeType): Theme {
 | 
				
			||||||
 | 
					  switch (theme) {
 | 
				
			||||||
 | 
					    case ThemeType.light:
 | 
				
			||||||
 | 
					      return Theme.Light;
 | 
				
			||||||
 | 
					    case ThemeType.dark:
 | 
				
			||||||
 | 
					      return Theme.Dark;
 | 
				
			||||||
 | 
					    default:
 | 
				
			||||||
 | 
					      throw missingCaseError(theme);
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue