import type { FC } from '../../lib/teact/teact'; import React, { memo, useCallback, useEffect, useState, } from '../../lib/teact/teact'; import { getActions, withGlobal } from '../../global'; import { ManagementScreens, ProfileState } from '../../types'; import type { ApiExportedInvite } from '../../api/types'; import { ANIMATION_END_DELAY } from '../../config'; import { IS_SINGLE_COLUMN_LAYOUT } from '../../util/environment'; import { debounce } from '../../util/schedulers'; import buildClassName from '../../util/buildClassName'; import { selectChat, selectCurrentGifSearch, selectCurrentStickerSearch, selectCurrentTextSearch, selectIsChatWithSelf, selectUser, } from '../../global/selectors'; import { getCanAddContact, isChatAdmin, isChatChannel, isUserId, } from '../../global/helpers'; import useCurrentOrPrev from '../../hooks/useCurrentOrPrev'; import useLang from '../../hooks/useLang'; import useFlag from '../../hooks/useFlag'; import { getDayStartAt } from '../../util/dateFormat'; import SearchInput from '../ui/SearchInput'; import Button from '../ui/Button'; import Transition from '../ui/Transition'; import ConfirmDialog from '../ui/ConfirmDialog'; import './RightHeader.scss'; type OwnProps = { chatId?: string; isColumnOpen?: boolean; isProfile?: boolean; isSearch?: boolean; isManagement?: boolean; isStatistics?: boolean; isMessageStatistics?: boolean; isStickerSearch?: boolean; isGifSearch?: boolean; isPollResults?: boolean; isAddingChatMembers?: boolean; profileState?: ProfileState; managementScreen?: ManagementScreens; onClose: () => void; onScreenSelect: (screen: ManagementScreens) => void; }; type StateProps = { canAddContact?: boolean; canManage?: boolean; canViewStatistics?: boolean; isChannel?: boolean; userId?: string; messageSearchQuery?: string; stickerSearchQuery?: string; gifSearchQuery?: string; isEditingInvite?: boolean; currentInviteInfo?: ApiExportedInvite; shouldSkipHistoryAnimations?: boolean; }; const COLUMN_ANIMATION_DURATION = 450 + ANIMATION_END_DELAY; const runDebouncedForSearch = debounce((cb) => cb(), 200, false); enum HeaderContent { Profile, MemberList, SharedMedia, Search, Statistics, MessageStatistics, Management, ManageInitial, ManageChannelSubscribers, ManageChatAdministrators, ManageChatPrivacyType, ManageDiscussion, ManageGroupPermissions, ManageGroupRemovedUsers, ManageChannelRemovedUsers, ManageGroupUserPermissionsCreate, ManageGroupUserPermissions, ManageGroupRecentActions, ManageGroupAdminRights, ManageGroupNewAdminRights, ManageGroupMembers, ManageGroupAddAdmins, StickerSearch, GifSearch, PollResults, AddingMembers, ManageInvites, ManageEditInvite, ManageReactions, ManageInviteInfo, ManageJoinRequests, } const RightHeader: FC = ({ chatId, isColumnOpen, isProfile, isSearch, isManagement, isStatistics, isMessageStatistics, isStickerSearch, isGifSearch, isPollResults, isAddingChatMembers, profileState, managementScreen, canAddContact, userId, canManage, isChannel, onClose, onScreenSelect, messageSearchQuery, stickerSearchQuery, gifSearchQuery, isEditingInvite, canViewStatistics, currentInviteInfo, shouldSkipHistoryAnimations, }) => { const { setLocalTextSearchQuery, setStickerSearchQuery, setGifSearchQuery, searchTextMessagesLocal, toggleManagement, openHistoryCalendar, openAddContactDialog, toggleStatistics, setEditingExportedInvite, deleteExportedChatInvite, } = getActions(); const [isDeleteDialogOpen, openDeleteDialog, closeDeleteDialog] = useFlag(); const handleEditInviteClick = useCallback(() => { setEditingExportedInvite({ chatId: chatId!, invite: currentInviteInfo! }); onScreenSelect(ManagementScreens.EditInvite); }, [chatId, currentInviteInfo, onScreenSelect, setEditingExportedInvite]); const handleDeleteInviteClick = useCallback(() => { deleteExportedChatInvite({ chatId: chatId!, link: currentInviteInfo!.link }); onScreenSelect(ManagementScreens.Invites); closeDeleteDialog(); }, [chatId, closeDeleteDialog, currentInviteInfo, deleteExportedChatInvite, onScreenSelect]); const handleMessageSearchQueryChange = useCallback((query: string) => { setLocalTextSearchQuery({ query }); if (query.length) { runDebouncedForSearch(searchTextMessagesLocal); } }, [searchTextMessagesLocal, setLocalTextSearchQuery]); const handleStickerSearchQueryChange = useCallback((query: string) => { setStickerSearchQuery({ query }); }, [setStickerSearchQuery]); const handleGifSearchQueryChange = useCallback((query: string) => { setGifSearchQuery({ query }); }, [setGifSearchQuery]); const handleAddContact = useCallback(() => { openAddContactDialog({ userId }); }, [openAddContactDialog, userId]); const [shouldSkipTransition, setShouldSkipTransition] = useState(!isColumnOpen); useEffect(() => { setTimeout(() => { setShouldSkipTransition(!isColumnOpen); }, COLUMN_ANIMATION_DURATION); }, [isColumnOpen]); const lang = useLang(); const contentKey = isProfile ? ( profileState === ProfileState.Profile ? ( HeaderContent.Profile ) : profileState === ProfileState.SharedMedia ? ( HeaderContent.SharedMedia ) : profileState === ProfileState.MemberList ? ( HeaderContent.MemberList ) : -1 // Never reached ) : isSearch ? ( HeaderContent.Search ) : isPollResults ? ( HeaderContent.PollResults ) : isStickerSearch ? ( HeaderContent.StickerSearch ) : isGifSearch ? ( HeaderContent.GifSearch ) : isAddingChatMembers ? ( HeaderContent.AddingMembers ) : isManagement ? ( managementScreen === ManagementScreens.Initial ? ( HeaderContent.ManageInitial ) : managementScreen === ManagementScreens.ChatPrivacyType ? ( HeaderContent.ManageChatPrivacyType ) : managementScreen === ManagementScreens.Discussion ? ( HeaderContent.ManageDiscussion ) : managementScreen === ManagementScreens.ChannelSubscribers ? ( HeaderContent.ManageChannelSubscribers ) : managementScreen === ManagementScreens.GroupPermissions ? ( HeaderContent.ManageGroupPermissions ) : managementScreen === ManagementScreens.ChatAdministrators ? ( HeaderContent.ManageChatAdministrators ) : managementScreen === ManagementScreens.GroupRemovedUsers ? ( HeaderContent.ManageGroupRemovedUsers ) : managementScreen === ManagementScreens.ChannelRemovedUsers ? ( HeaderContent.ManageChannelRemovedUsers ) : managementScreen === ManagementScreens.GroupUserPermissionsCreate ? ( HeaderContent.ManageGroupUserPermissionsCreate ) : managementScreen === ManagementScreens.GroupUserPermissions ? ( HeaderContent.ManageGroupUserPermissions ) : managementScreen === ManagementScreens.GroupRecentActions ? ( HeaderContent.ManageGroupRecentActions ) : managementScreen === ManagementScreens.ChatAdminRights ? ( HeaderContent.ManageGroupAdminRights ) : managementScreen === ManagementScreens.ChatNewAdminRights ? ( HeaderContent.ManageGroupNewAdminRights ) : managementScreen === ManagementScreens.GroupMembers ? ( HeaderContent.ManageGroupMembers ) : managementScreen === ManagementScreens.Invites ? ( HeaderContent.ManageInvites ) : managementScreen === ManagementScreens.EditInvite ? ( HeaderContent.ManageEditInvite ) : managementScreen === ManagementScreens.GroupAddAdmins ? ( HeaderContent.ManageGroupAddAdmins ) : managementScreen === ManagementScreens.Reactions ? ( HeaderContent.ManageReactions ) : managementScreen === ManagementScreens.InviteInfo ? ( HeaderContent.ManageInviteInfo ) : managementScreen === ManagementScreens.JoinRequests ? ( HeaderContent.ManageJoinRequests ) : undefined // Never reached ) : isStatistics ? ( HeaderContent.Statistics ) : isMessageStatistics ? ( HeaderContent.MessageStatistics ) : undefined; // When column is closed const renderingContentKey = useCurrentOrPrev(contentKey, true) ?? -1; function renderHeaderContent() { if (renderingContentKey === -1) { return undefined; } switch (renderingContentKey) { case HeaderContent.PollResults: return

{lang('PollResults')}

; case HeaderContent.Search: return ( <> ); case HeaderContent.AddingMembers: return

{lang(isChannel ? 'ChannelAddSubscribers' : 'GroupAddMembers')}

; case HeaderContent.ManageInitial: return

{lang('Edit')}

; case HeaderContent.ManageChatPrivacyType: return

{lang(isChannel ? 'ChannelTypeHeader' : 'GroupTypeHeader')}

; case HeaderContent.ManageDiscussion: return

{lang('Discussion')}

; case HeaderContent.ManageChatAdministrators: return

{lang('ChannelAdministrators')}

; case HeaderContent.ManageGroupRecentActions: return

{lang('Group.Info.AdminLog')}

; case HeaderContent.ManageGroupAdminRights: return

{lang('EditAdminRights')}

; case HeaderContent.ManageGroupNewAdminRights: return

{lang('SetAsAdmin')}

; case HeaderContent.ManageGroupPermissions: return

{lang('ChannelPermissions')}

; case HeaderContent.ManageGroupRemovedUsers: return

{lang('BlockedUsers')}

; case HeaderContent.ManageChannelRemovedUsers: return

{lang('ChannelBlockedUsers')}

; case HeaderContent.ManageGroupUserPermissionsCreate: return

{lang('ChannelAddException')}

; case HeaderContent.ManageGroupUserPermissions: return

{lang('UserRestrictions')}

; case HeaderContent.ManageInvites: return

{lang('lng_group_invite_title')}

; case HeaderContent.ManageEditInvite: return

{isEditingInvite ? lang('EditLink') : lang('NewLink')}

; case HeaderContent.ManageInviteInfo: return ( <>

{lang('InviteLink')}

{currentInviteInfo && !currentInviteInfo.isRevoked && ( )} {currentInviteInfo && currentInviteInfo.isRevoked && ( <> )}
); case HeaderContent.ManageJoinRequests: return

{isChannel ? lang('SubscribeRequests') : lang('MemberRequests')}

; case HeaderContent.ManageGroupAddAdmins: return

{lang('Channel.Management.AddModerator')}

; case HeaderContent.StickerSearch: return ( ); case HeaderContent.GifSearch: return ( ); case HeaderContent.Statistics: return

{lang(isChannel ? 'ChannelStats.Title' : 'GroupStats.Title')}

; case HeaderContent.MessageStatistics: return

{lang('Stats.MessageTitle')}

; case HeaderContent.SharedMedia: return

{lang('SharedMedia')}

; case HeaderContent.ManageChannelSubscribers: return

{lang('ChannelSubscribers')}

; case HeaderContent.MemberList: case HeaderContent.ManageGroupMembers: return

{lang('GroupMembers')}

; case HeaderContent.ManageReactions: return

{lang('Reactions')}

; default: return ( <>

Profile

{canAddContact && ( )} {canManage && ( )} {canViewStatistics && ( )}
); } } const isBackButton = ( IS_SINGLE_COLUMN_LAYOUT || contentKey === HeaderContent.SharedMedia || contentKey === HeaderContent.MemberList || contentKey === HeaderContent.AddingMembers || contentKey === HeaderContent.MessageStatistics || isManagement ); const buttonClassName = buildClassName( 'animated-close-icon', isBackButton && 'state-back', (shouldSkipTransition || shouldSkipHistoryAnimations) && 'no-transition', ); return (
{renderHeaderContent()}
); }; export default memo(withGlobal( (global, { chatId, isProfile, isManagement }): StateProps => { const { query: messageSearchQuery } = selectCurrentTextSearch(global) || {}; const { query: stickerSearchQuery } = selectCurrentStickerSearch(global) || {}; const { query: gifSearchQuery } = selectCurrentGifSearch(global) || {}; const chat = chatId ? selectChat(global, chatId) : undefined; const isChannel = chat && isChatChannel(chat); const user = isProfile && chatId && isUserId(chatId) ? selectUser(global, chatId) : undefined; const canAddContact = user && getCanAddContact(user); const canManage = Boolean( !isManagement && isProfile && !canAddContact && chat && !selectIsChatWithSelf(global, chat.id) // chat.isCreator is for Basic Groups && (isUserId(chat.id) || ((isChatAdmin(chat) || chat.isCreator) && !chat.isNotJoined)), ); const isEditingInvite = Boolean(chatId && global.management.byChatId[chatId]?.editingInvite); const canViewStatistics = chat?.fullInfo?.canViewStatistics; const currentInviteInfo = chatId ? global.management.byChatId[chatId]?.inviteInfo?.invite : undefined; return { canManage, canAddContact, canViewStatistics, isChannel, userId: user?.id, messageSearchQuery, stickerSearchQuery, gifSearchQuery, isEditingInvite, currentInviteInfo, shouldSkipHistoryAnimations: global.shouldSkipHistoryAnimations, }; }, )(RightHeader));