element-web-synapse01pim.gr.jp

Unnamed repository; edit this file 'description' to name the repository.
Log | Files | Refs

init.js.map (6583979B)


      1 {"version":3,"file":"bundles/9cacd6575f4c8ee1aedb/init.js","mappings":"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","sources":["webpack://element-web/./res/img/element-desktop-logo.svg","webpack://element-web/./res/img/element-icons/email-prompt.svg","webpack://element-web/./res/img/icon-email-pill-avatar.svg","webpack://element-web/./res/img/location/live-location.svg","webpack://element-web/./src/audio/RecorderWorklet.ts","webpack://element-web/./src/@types/media_preview.ts","webpack://element-web/./src/Avatar.ts","webpack://element-web/./src/utils/tokens/pickling.ts","webpack://element-web/./src/vector/getconfig.ts","webpack://element-web/./src/BasePlatform.ts","webpack://element-web/./src/DateUtils.ts","webpack://element-web/./src/Editing.ts","webpack://element-web/./src/HtmlUtils.tsx","webpack://element-web/./src/IConfigOptions.ts","webpack://element-web/./src/IdentityAuthClient.tsx","webpack://element-web/./src/KeyBindingsDefaults.ts","webpack://element-web/./src/KeyBindingsManager.ts","webpack://element-web/./src/Keyboard.ts","webpack://element-web/./src/toasts/IncomingLegacyCallToast.tsx","webpack://element-web/./src/LegacyCallHandler.tsx","webpack://element-web/./src/Linkify.tsx","webpack://element-web/./src/Markdown.ts","webpack://element-web/./src/actions/MatrixActionCreators.ts","webpack://element-web/./src/MatrixClientPeg.ts","webpack://element-web/./src/MediaDeviceHandler.ts","webpack://element-web/./src/AsyncWrapper.tsx","webpack://element-web/./src/Modal.tsx","webpack://element-web/./src/toasts/IncomingCallToast.tsx","webpack://element-web/./src/Notifier.ts","webpack://element-web/./src/PageTypes.ts","webpack://element-web/./src/PlatformPeg.ts","webpack://element-web/./src/PosthogAnalytics.ts","webpack://element-web/./src/PosthogTrackers.ts","webpack://element-web/./src/Resend.ts","webpack://element-web/./src/Roles.ts","webpack://element-web/./src/RoomAliasCache.ts","webpack://element-web/./src/RoomInvite.tsx","webpack://element-web/./src/RoomNotifs.ts","webpack://element-web/./src/Rooms.ts","webpack://element-web/./src/SdkConfig.ts","webpack://element-web/./src/components/views/dialogs/security/AccessSecretStorageDialog.tsx","webpack://element-web/./src/SecurityManager.ts","webpack://element-web/./src/SendHistoryManager.ts","webpack://element-web/./src/SlidingSyncManager.ts","webpack://element-web/./src/SupportedBrowser.ts","webpack://element-web/./src/components/views/dialogs/TermsDialog.tsx","webpack://element-web/./src/Terms.ts","webpack://element-web/./src/utils/event/getSenderName.ts","webpack://element-web/./src/TextForEvent.tsx","webpack://element-web/./src/TimezoneHandler.ts","webpack://element-web/./src/Typeguards.ts","webpack://element-web/./src/Unread.ts","webpack://element-web/./src/UserActivity.ts","webpack://element-web/./src/UserAddress.ts","webpack://element-web/./src/Views.ts","webpack://element-web/./src/WorkerManager.ts","webpack://element-web/./src/accessibility/KeyboardShortcutUtils.ts","webpack://element-web/./src/accessibility/KeyboardShortcuts.ts","webpack://element-web/./src/accessibility/LandmarkNavigation.ts","webpack://element-web/./src/accessibility/roving/RovingTabIndexWrapper.tsx","webpack://element-web/./src/accessibility/roving/RovingAccessibleButton.tsx","webpack://element-web/./src/accessibility/RovingTabIndex.tsx","webpack://element-web/./src/accessibility/Toolbar.tsx","webpack://element-web/./src/accessibility/context_menu/ContextMenuButton.tsx","webpack://element-web/./src/accessibility/context_menu/ContextMenuTooltipButton.tsx","webpack://element-web/./src/accessibility/context_menu/MenuItemRadio.tsx","webpack://element-web/./src/actions/RoomListActions.ts","webpack://element-web/./src/actions/actionCreators.ts","webpack://element-web/./src/audio/BackgroundAudio.ts","webpack://element-web/./src/audio/PlaybackClock.ts","webpack://element-web/./src/PlaybackEncoder.ts","webpack://element-web/./src/workers/playbackWorkerFactory.ts","webpack://element-web/./src/audio/Playback.ts","webpack://element-web/./src/audio/ManagedPlayback.ts","webpack://element-web/./src/audio/PlaybackManager.ts","webpack://element-web/./src/utils/FixedRollingArray.ts","webpack://element-web/./src/audio/VoiceRecording.ts","webpack://element-web/./src/audio/recorderWorkletFactory.ts","webpack://element-web/./src/audio/compat.ts","webpack://element-web/./src/audio/consts.ts","webpack://element-web/./src/autocomplete/AutocompleteProvider.tsx","webpack://element-web/./src/autocomplete/CommandProvider.tsx","webpack://element-web/./src/autocomplete/Components.tsx","webpack://element-web/./src/autocomplete/QueryMatcher.ts","webpack://element-web/./src/autocomplete/UserProvider.tsx","webpack://element-web/./src/call-types.ts","webpack://element-web/./src/components/structures/AutoHideScrollbar.tsx","webpack://element-web/./src/accessibility/context_menu/MenuItem.tsx","webpack://element-web/./src/accessibility/context_menu/MenuItemCheckbox.tsx","webpack://element-web/./src/accessibility/context_menu/StyledMenuItemCheckbox.tsx","webpack://element-web/./src/accessibility/context_menu/StyledMenuItemRadio.tsx","webpack://element-web/./src/components/structures/ContextMenu.tsx","webpack://element-web/./src/components/structures/InteractiveAuth.tsx","webpack://element-web/./src/components/structures/LegacyCallEventGrouper.ts","webpack://element-web/./src/components/structures/ScrollPanel.tsx","webpack://element-web/./src/components/structures/SearchBox.tsx","webpack://element-web/./src/components/structures/SpacePillButton.tsx","webpack://element-web/./src/components/structures/TabbedView.tsx","webpack://element-web/./src/hooks/useWindowWidth.ts","webpack://element-web/./src/components/structures/ViewSource.tsx","webpack://element-web/./src/components/structures/auth/header/AuthHeaderContext.tsx","webpack://element-web/./src/components/structures/auth/header/AuthHeaderProvider.tsx","webpack://element-web/./src/components/views/audio_messages/PlayPauseButton.tsx","webpack://element-web/./src/components/views/audio_messages/PlaybackClock.tsx","webpack://element-web/./src/components/views/audio_messages/AudioPlayerBase.tsx","webpack://element-web/./src/components/views/audio_messages/LegacySeekBar.tsx","webpack://element-web/./src/components/views/audio_messages/PlaybackWaveform.tsx","webpack://element-web/./src/components/views/audio_messages/RecordingPlayback.tsx","webpack://element-web/./src/components/views/audio_messages/Waveform.tsx","webpack://element-web/./src/components/structures/auth/header/AuthHeaderModifier.tsx","webpack://element-web/./src/components/views/auth/CaptchaForm.tsx","webpack://element-web/./src/components/views/auth/InteractiveAuthEntryComponents.tsx","webpack://element-web/./src/components/views/avatars/BaseAvatar.tsx","webpack://element-web/./src/components/views/avatars/DecoratedRoomAvatar.tsx","webpack://element-web/./src/components/views/avatars/MemberAvatar.tsx","webpack://element-web/./src/components/views/avatars/RoomAvatar.tsx","webpack://element-web/./src/hooks/room/useRoomIdName.ts","webpack://element-web/./src/components/views/avatars/SearchResultAvatar.tsx","webpack://element-web/./src/components/views/avatars/WithPresenceIndicator.tsx","webpack://element-web/./src/components/views/beacon/LiveTimeRemaining.tsx","webpack://element-web/./src/components/views/beacon/BeaconStatus.tsx","webpack://element-web/./src/components/views/beacon/OwnBeaconStatus.tsx","webpack://element-web/./src/components/views/beacon/StyledLiveBeaconIcon.tsx","webpack://element-web/./src/components/views/beacon/displayStatus.ts","webpack://element-web/./src/components/views/dialogs/GenericFeatureFeedbackDialog.tsx","webpack://element-web/./src/components/views/dialogs/BetaFeedbackDialog.tsx","webpack://element-web/./src/components/views/beta/BetaCard.tsx","webpack://element-web/./src/components/views/context_menus/IconizedContextMenu.tsx","webpack://element-web/./src/components/views/dialogs/EndPollDialog.tsx","webpack://element-web/./src/components/views/context_menus/MessageContextMenu.tsx","webpack://element-web/./src/components/views/context_menus/DeveloperToolsOption.tsx","webpack://element-web/./src/components/views/context_menus/RoomGeneralContextMenu.tsx","webpack://element-web/./src/components/views/context_menus/RoomNotificationContextMenu.tsx","webpack://element-web/./src/components/views/context_menus/SpaceContextMenu.tsx","webpack://element-web/./src/components/views/dialogs/AddExistingToSpaceDialog.tsx","webpack://element-web/./src/components/views/dialogs/AskInviteAnywayDialog.tsx","webpack://element-web/./src/components/views/dialogs/BaseDialog.tsx","webpack://element-web/./src/components/views/dialogs/BugReportDialog.tsx","webpack://element-web/./src/components/views/dialogs/ConfirmRedactDialog.tsx","webpack://element-web/./src/components/views/dialogs/ConfirmUserActionDialog.tsx","webpack://element-web/./src/components/views/dialogs/CreateRoomDialog.tsx","webpack://element-web/./src/components/views/dialogs/devtools/ServersInRoom.tsx","webpack://element-web/./src/components/views/dialogs/devtools/SettingExplorer.tsx","webpack://element-web/./src/components/views/dialogs/devtools/WidgetExplorer.tsx","webpack://element-web/./src/components/views/dialogs/devtools/Users.tsx","webpack://element-web/./src/components/views/dialogs/devtools/AccountData.tsx","webpack://element-web/./src/components/views/dialogs/devtools/RoomNotifications.tsx","webpack://element-web/./src/components/views/dialogs/devtools/Crypto.tsx","webpack://element-web/./src/components/views/elements/SettingsField.tsx","webpack://element-web/./src/components/views/dialogs/DevtoolsDialog.tsx","webpack://element-web/./src/components/views/dialogs/ErrorDialog.tsx","webpack://element-web/./src/components/views/dialogs/InfoDialog.tsx","webpack://element-web/./src/components/views/dialogs/InteractiveAuthDialog.tsx","webpack://element-web/./src/components/views/dialogs/InviteDialog.tsx","webpack://element-web/./src/components/views/dialogs/InviteDialogTypes.ts","webpack://element-web/./src/components/views/dialogs/InviteProgressBody.tsx","webpack://element-web/./src/components/views/dialogs/ManualDeviceKeyVerificationDialog.tsx","webpack://element-web/./src/components/views/dialogs/QuestionDialog.tsx","webpack://element-web/./src/components/views/room_settings/RoomProfileSettings.tsx","webpack://element-web/./src/components/views/room_settings/UrlPreviewSettings.tsx","webpack://element-web/./src/components/views/settings/tabs/room/GeneralRoomSettingsTab.tsx","webpack://element-web/./src/components/views/settings/tabs/room/SecurityRoomSettingsTab.tsx","webpack://element-web/./src/components/views/settings/tabs/room/NotificationSettingsTab.tsx","webpack://element-web/./src/components/views/settings/BridgeTile.tsx","webpack://element-web/./src/components/views/settings/tabs/room/BridgeSettingsTab.tsx","webpack://element-web/./src/components/views/settings/tabs/room/VoipRoomSettingsTab.tsx","webpack://element-web/./src/components/views/settings/tabs/room/PollHistoryTab.tsx","webpack://element-web/./src/components/views/settings/tabs/room/PeopleRoomSettingsTab.tsx","webpack://element-web/./src/components/views/dialogs/RoomSettingsDialog.tsx","webpack://element-web/./src/components/views/dialogs/RoomUpgradeDialog.tsx","webpack://element-web/./src/components/views/dialogs/RoomUpgradeWarningDialog.tsx","webpack://element-web/./src/components/views/dialogs/ScrollableBaseModal.tsx","webpack://element-web/./src/components/views/dialogs/ShareDialog.tsx","webpack://element-web/./src/components/views/dialogs/TextInputDialog.tsx","webpack://element-web/./src/components/views/dialogs/UploadConfirmDialog.tsx","webpack://element-web/./src/components/views/dialogs/UserTab.ts","webpack://element-web/./src/components/views/dialogs/devtools/BaseTool.tsx","webpack://element-web/./src/components/views/dialogs/devtools/Event.tsx","webpack://element-web/./src/components/views/dialogs/devtools/FilteredList.tsx","webpack://element-web/./src/components/views/dialogs/devtools/RoomState.tsx","webpack://element-web/./src/components/views/dialogs/devtools/ServerInfo.tsx","webpack://element-web/./src/components/views/dialogs/security/RestoreKeyBackupDialog.tsx","webpack://element-web/./src/components/views/dialogs/spotlight/Filter.ts","webpack://element-web/./src/components/views/dialogs/spotlight/RoomResultContextMenus.tsx","webpack://element-web/./src/components/views/elements/AccessibleButton.tsx","webpack://element-web/./src/components/views/elements/BugReportDialogButton.tsx","webpack://element-web/./src/components/views/elements/CopyableText.tsx","webpack://element-web/./src/components/views/elements/DialPadBackspaceButton.tsx","webpack://element-web/./src/components/views/elements/DialogButtons.tsx","webpack://element-web/./src/components/views/elements/Dropdown.tsx","webpack://element-web/./src/components/views/elements/ErrorBoundary.tsx","webpack://element-web/./src/components/views/elements/ExternalLink.tsx","webpack://element-web/./src/components/views/elements/FacePile.tsx","webpack://element-web/./src/components/views/elements/Field.tsx","webpack://element-web/./src/utils/Mouse.ts","webpack://element-web/./src/components/views/elements/ImageView.tsx","webpack://element-web/./src/components/views/elements/InfoTooltip.tsx","webpack://element-web/./src/components/views/elements/InlineSpinner.tsx","webpack://element-web/./src/components/views/elements/JoinRuleDropdown.tsx","webpack://element-web/./src/components/views/elements/LabelledCheckbox.tsx","webpack://element-web/./src/components/views/elements/LazyRenderList.tsx","webpack://element-web/./src/hooks/usePermalinkTargetRoom.ts","webpack://element-web/./src/hooks/usePermalinkMember.ts","webpack://element-web/./src/hooks/usePermalink.ts","webpack://element-web/./src/hooks/usePermalinkEvent.ts","webpack://element-web/./src/components/views/elements/Pill.tsx","webpack://element-web/./src/components/views/elements/PollCreateDialog.tsx","webpack://element-web/./src/components/views/elements/PowerSelector.tsx","webpack://element-web/./src/hooks/useAnimation.ts","webpack://element-web/./src/hooks/useSmoothAnimation.ts","webpack://element-web/./src/components/views/elements/ProgressBar.tsx","webpack://element-web/./src/components/views/elements/QRCode.tsx","webpack://element-web/./src/components/views/elements/RoomAliasField.tsx","webpack://element-web/./src/components/views/elements/SettingsFlag.tsx","webpack://element-web/./src/components/views/elements/Spinner.tsx","webpack://element-web/./src/components/views/elements/StyledCheckbox.tsx","webpack://element-web/./src/components/views/elements/StyledRadioButton.tsx","webpack://element-web/./src/components/views/elements/StyledRadioGroup.tsx","webpack://element-web/./src/components/views/elements/SyntaxHighlight.tsx","webpack://element-web/./src/components/views/elements/TextWithTooltip.tsx","webpack://element-web/./src/components/views/elements/TruncatedList.tsx","webpack://element-web/./src/components/views/elements/Validation.tsx","webpack://element-web/./src/components/views/emojipicker/Header.tsx","webpack://element-web/./src/components/views/emojipicker/Search.tsx","webpack://element-web/./src/components/views/emojipicker/Preview.tsx","webpack://element-web/./src/components/views/emojipicker/Emoji.tsx","webpack://element-web/./src/components/views/emojipicker/QuickReactions.tsx","webpack://element-web/./src/components/views/emojipicker/Category.tsx","webpack://element-web/./src/components/views/emojipicker/EmojiPicker.tsx","webpack://element-web/./src/components/views/emojipicker/ReactionPicker.tsx","webpack://element-web/./src/components/views/location/MapError.tsx","webpack://element-web/./res/img/location/map.svg","webpack://element-web/./src/components/views/location/MapFallback.tsx","webpack://element-web/./src/components/views/location/index.tsx","webpack://element-web/./src/components/views/messages/JumpToDatePicker.tsx","webpack://element-web/./src/components/views/messages/DateSeparator.tsx","webpack://element-web/./src/components/views/messages/EncryptionEvent.tsx","webpack://element-web/./src/components/views/messages/HiddenMediaPlaceholder.tsx","webpack://element-web/./src/components/views/messages/LegacyCallEvent.tsx","webpack://element-web/./src/viewmodels/audio/AudioPlayerViewModel.ts","webpack://element-web/./src/components/views/messages/MAudioBody.tsx","webpack://element-web/./src/components/views/messages/MFileBody.tsx","webpack://element-web/./src/components/views/messages/MImageBody.tsx","webpack://element-web/./src/components/views/messages/MPollBody.tsx","webpack://element-web/./src/audio/PlaybackQueue.ts","webpack://element-web/./src/components/views/messages/MVoiceMessageBody.tsx","webpack://element-web/./src/components/views/messages/UnknownBody.tsx","webpack://element-web/./src/components/views/elements/LinkWithTooltip.tsx","webpack://element-web/./src/renderer/utils.tsx","webpack://element-web/./src/renderer/link-tooltip.tsx","webpack://element-web/./src/renderer/pill.tsx","webpack://element-web/./src/components/views/elements/Spoiler.tsx","webpack://element-web/./src/renderer/spoiler.tsx","webpack://element-web/./src/components/views/messages/CodeBlock.tsx","webpack://element-web/./src/renderer/code-block.tsx","webpack://element-web/./src/components/views/messages/EventContentBody.tsx","webpack://element-web/./src/utils/MessageDiffUtils.tsx","webpack://element-web/./src/components/views/dialogs/ConfirmAndWaitRedactDialog.tsx","webpack://element-web/./src/components/views/messages/EditHistoryMessage.tsx","webpack://element-web/./src/components/views/dialogs/MessageEditHistoryDialog.tsx","webpack://element-web/./src/components/views/rooms/EditMessageComposer.tsx","webpack://element-web/./src/components/views/rooms/LinkPreviewWidget.tsx","webpack://element-web/./src/ImageUtils.ts","webpack://element-web/./src/components/views/rooms/LinkPreviewGroup.tsx","webpack://element-web/./src/components/views/messages/TextualBody.tsx","webpack://element-web/./src/components/views/messages/MVoiceOrAudioBody.tsx","webpack://element-web/./src/components/views/messages/MVideoBody.tsx","webpack://element-web/./src/components/views/messages/MStickerBody.tsx","webpack://element-web/./res/img/icons-show-stickers.svg","webpack://element-web/./src/components/views/messages/MLocationBody.tsx","webpack://element-web/./src/components/views/messages/MjolnirBody.tsx","webpack://element-web/./src/components/views/beacon/index.tsx","webpack://element-web/./src/components/views/messages/MBeaconBody.tsx","webpack://element-web/./src/components/views/messages/MessageEvent.tsx","webpack://element-web/./res/img/sensor.svg","webpack://element-web/./src/components/views/messages/MessageTimestamp.tsx","webpack://element-web/./src/components/views/messages/RedactedBody.tsx","webpack://element-web/./src/components/views/messages/shared/MediaProcessingError.tsx","webpack://element-web/./res/img/element-icons/trophy.svg","webpack://element-web/./src/components/views/polls/PollOption.tsx","webpack://element-web/./src/components/views/elements/FilterTabGroup.tsx","webpack://element-web/./src/components/views/polls/pollHistory/PollListItem.tsx","webpack://element-web/./src/components/views/polls/pollHistory/PollListItemEnded.tsx","webpack://element-web/./src/components/views/polls/pollHistory/PollHistoryList.tsx","webpack://element-web/./src/components/views/polls/pollHistory/PollDetailHeader.tsx","webpack://element-web/./src/components/views/polls/pollHistory/PollDetail.tsx","webpack://element-web/./src/components/views/polls/pollHistory/usePollHistory.ts","webpack://element-web/./src/components/views/polls/pollHistory/fetchPastPolls.ts","webpack://element-web/./src/components/views/polls/pollHistory/PollHistory.tsx","webpack://element-web/./src/components/views/right_panel/BaseCard.tsx","webpack://element-web/./src/components/views/right_panel/EncryptionInfo.tsx","webpack://element-web/./src/components/views/elements/crypto/VerificationQRCode.tsx","webpack://element-web/./src/components/views/right_panel/VerificationPanel.tsx","webpack://element-web/./src/components/views/right_panel/EncryptionPanel.tsx","webpack://element-web/./src/hooks/useUserTimezone.ts","webpack://element-web/./src/components/viewmodels/right_panel/user_info/UserInfoHeaderViewModel.tsx","webpack://element-web/./src/components/viewmodels/right_panel/user_info/UserInfoHeaderVerificationViewModel.tsx","webpack://element-web/./src/components/views/right_panel/user_info/UserInfoHeaderVerificationView.tsx","webpack://element-web/./src/components/views/right_panel/user_info/UserInfoHeaderView.tsx","webpack://element-web/./src/components/viewmodels/right_panel/user_info/UserInfoBasicViewModel.tsx","webpack://element-web/./src/components/viewmodels/right_panel/UserInfoPowerlevelViewModel.tsx","webpack://element-web/./src/components/views/right_panel/user_info/UserInfoPowerLevels.tsx","webpack://element-web/./src/components/viewmodels/right_panel/user_info/UserInfoIgnoreButtonViewModel.tsx","webpack://element-web/./src/components/views/right_panel/user_info/UserInfoIgnoreButtonView.tsx","webpack://element-web/./src/components/views/dialogs/ConfirmSpaceUserActionDialog.tsx","webpack://element-web/./src/components/viewmodels/right_panel/user_info/admin/UserInfoBanButtonViewModel.tsx","webpack://element-web/./src/components/views/dialogs/BulkRedactDialog.tsx","webpack://element-web/./src/components/views/right_panel/user_info/UserInfoAdminToolsContainer.tsx","webpack://element-web/./src/components/viewmodels/right_panel/user_info/admin/UserInfoKickButtonViewModel.tsx","webpack://element-web/./src/components/viewmodels/right_panel/user_info/admin/UserInfoRedactButtonViewModel.tsx","webpack://element-web/./src/components/viewmodels/right_panel/user_info/admin/UserInfoMuteButtonViewModel.tsx","webpack://element-web/./src/components/viewmodels/right_panel/user_info/admin/UserInfoAdminToolsContainerViewModel.tsx","webpack://element-web/./src/components/views/right_panel/user_info/UserInfoBasicOptionsView.tsx","webpack://element-web/./src/components/viewmodels/right_panel/user_info/UserInfoBasicOptionsViewModel.tsx","webpack://element-web/./src/components/views/right_panel/user_info/UserInfoBasicView.tsx","webpack://element-web/./src/components/views/right_panel/UserInfo.tsx","webpack://element-web/./src/components/views/right_panel/context.ts","webpack://element-web/./src/components/views/right_panel/types.ts","webpack://element-web/./src/components/views/elements/EditableItemList.tsx","webpack://element-web/./src/components/views/room_settings/RoomPublishSetting.tsx","webpack://element-web/./src/components/views/room_settings/AliasSettings.tsx","webpack://element-web/./src/autocomplete/RoomProvider.tsx","webpack://element-web/./src/autocomplete/EmojiProvider.tsx","webpack://element-web/./src/autocomplete/NotifProvider.tsx","webpack://element-web/./src/autocomplete/Autocompleter.ts","webpack://element-web/./src/autocomplete/SpaceProvider.tsx","webpack://element-web/./src/components/views/rooms/Autocomplete.tsx","webpack://element-web/./src/editor/history.ts","webpack://element-web/./src/editor/caret.ts","webpack://element-web/./src/components/views/rooms/MessageComposerFormatBar.tsx","webpack://element-web/./src/editor/operations.ts","webpack://element-web/./src/components/views/rooms/BasicMessageComposer.tsx","webpack://element-web/./src/components/views/rooms/E2EIcon.tsx","webpack://element-web/./src/components/views/rooms/ExtraTile.tsx","webpack://element-web/./src/hooks/useHover.ts","webpack://element-web/./src/components/views/rooms/LegacyRoomList.tsx","webpack://element-web/./src/components/views/rooms/LiveContentSummary.tsx","webpack://element-web/./src/components/views/rooms/NotificationBadge.tsx","webpack://element-web/./src/components/views/rooms/NotificationBadge/StatelessNotificationBadge.tsx","webpack://element-web/./src/components/views/rooms/PresenceLabel.tsx","webpack://element-web/./src/components/views/rooms/RoomHeader/toggle/useToggled.tsx","webpack://element-web/./src/components/views/rooms/RoomSublist.tsx","webpack://element-web/./src/@types/polyfill.ts","webpack://element-web/./src/components/views/rooms/RoomTileCallSummary.tsx","webpack://element-web/./src/components/views/rooms/RoomTileSubtitle.tsx","webpack://element-web/./src/components/views/rooms/RoomTile.tsx","webpack://element-web/./src/components/views/rooms/wysiwyg_composer/DynamicImportWysiwygComposer.tsx","webpack://element-web/./src/components/views/settings/AvatarSetting.tsx","webpack://element-web/./src/components/views/dialogs/ManageRestrictedJoinRuleDialog.tsx","webpack://element-web/./src/components/views/settings/JoinRuleSettings.tsx","webpack://element-web/./src/components/views/settings/SettingsFieldset.tsx","webpack://element-web/./src/components/views/settings/SettingsHeader.tsx","webpack://element-web/./src/components/views/settings/encryption/EncryptionCard.tsx","webpack://element-web/./src/components/views/settings/encryption/EncryptionCardButtons.tsx","webpack://element-web/./src/components/views/settings/shared/SettingsSection.tsx","webpack://element-web/./src/components/views/settings/shared/SettingsSubsection.tsx","webpack://element-web/./src/components/views/settings/shared/SettingsSubsectionHeading.tsx","webpack://element-web/./src/components/views/settings/tabs/SettingsTab.tsx","webpack://element-web/./src/components/views/settings/tabs/room/AdvancedRoomSettingsTab.tsx","webpack://element-web/./src/components/structures/AutocompleteInput.tsx","webpack://element-web/./src/components/views/settings/AddPrivilegedUsers.tsx","webpack://element-web/./src/components/views/settings/PowerLevelSelector.tsx","webpack://element-web/./src/components/views/settings/tabs/room/RolesRoomSettingsTab.tsx","webpack://element-web/./src/components/views/settings/tabs/user/MediaPreviewAccountSettings.tsx","webpack://element-web/./src/components/views/spaces/SpaceBasicSettings.tsx","webpack://element-web/./src/components/views/spaces/SpaceChildrenPicker.tsx","webpack://element-web/./src/components/views/spaces/SpaceCreateMenu.tsx","webpack://element-web/./src/components/views/spaces/SpacePublicShare.tsx","webpack://element-web/./src/components/views/toasts/GenericToast.tsx","webpack://element-web/./src/components/views/typography/Caption.tsx","webpack://element-web/./src/components/views/typography/Heading.tsx","webpack://element-web/./src/components/views/verification/VerificationShowSas.tsx","webpack://element-web/./src/components/views/voip/DialPad.tsx","webpack://element-web/./src/contexts/CurrentRightPanelPhaseContext.tsx","webpack://element-web/./src/hooks/right-panel/useCurrentPhase.ts","webpack://element-web/./src/contexts/LocalDeviceVerificationStateContext.ts","webpack://element-web/./src/contexts/MatrixClientContext.tsx","webpack://element-web/./src/contexts/RoomContext.ts","webpack://element-web/./src/stores/MemberListStore.ts","webpack://element-web/./src/stores/RoomViewStore.tsx","webpack://element-web/./src/stores/TypingStore.ts","webpack://element-web/./src/utils/LruCache.ts","webpack://element-web/./src/stores/UserProfilesStore.ts","webpack://element-web/./src/stores/oidc/OidcClientStore.ts","webpack://element-web/./src/utils/ResizeNotifier.ts","webpack://element-web/./src/stores/MultiRoomViewStore.ts","webpack://element-web/./src/contexts/SDKContext.ts","webpack://element-web/./src/contexts/ScopedRoomContext.tsx","webpack://element-web/./src/createRoom.ts","webpack://element-web/./src/customisations/Alias.ts","webpack://element-web/./src/customisations/ChatExport.ts","webpack://element-web/./src/customisations/ComponentVisibility.ts","webpack://element-web/./src/customisations/Directory.ts","webpack://element-web/./src/customisations/Lifecycle.ts","webpack://element-web/./src/customisations/Media.ts","webpack://element-web/./src/customisations/models/IMediaEventContent.ts","webpack://element-web/./src/customisations/RoomList.ts","webpack://element-web/./src/customisations/UserIdentifier.ts","webpack://element-web/./src/customisations/WidgetPermissions.ts","webpack://element-web/./src/customisations/WidgetVariables.ts","webpack://element-web/./src/customisations/helpers/UIComponents.ts","webpack://element-web/./src/dispatcher/actions.ts","webpack://element-web/./src/dispatcher/dispatcher.ts","webpack://element-web/./src/dispatcher/payloads.ts","webpack://element-web/./src/dispatcher/payloads/ComposerInsertPayload.ts","webpack://element-web/./src/editor/commands.tsx","webpack://element-web/./src/editor/deserialize.ts","webpack://element-web/./src/editor/dom.ts","webpack://element-web/./src/editor/diff.ts","webpack://element-web/./src/editor/model.ts","webpack://element-web/./src/editor/offset.ts","webpack://element-web/./src/editor/autocomplete.ts","webpack://element-web/./src/editor/parts.ts","webpack://element-web/./src/editor/position.ts","webpack://element-web/./src/editor/range.ts","webpack://element-web/./src/editor/render.ts","webpack://element-web/./src/editor/serialize.ts","webpack://element-web/./src/effects/index.ts","webpack://element-web/./src/effects/utils.ts","webpack://element-web/./src/email.ts","webpack://element-web/./src/emojipicker/recent.ts","webpack://element-web/./src/components/views/voip/CallDuration.tsx","webpack://element-web/./src/components/views/messages/CallEvent.tsx","webpack://element-web/./src/components/views/messages/RoomPredecessorTile.tsx","webpack://element-web/./src/components/views/messages/RoomAvatarEvent.tsx","webpack://element-web/./src/components/views/messages/MKeyVerificationRequest.tsx","webpack://element-web/./src/components/views/messages/MJitsiWidgetEvent.tsx","webpack://element-web/./src/components/views/messages/HiddenBody.tsx","webpack://element-web/./src/components/views/messages/ViewSourceEvent.tsx","webpack://element-web/./src/viewmodels/event-tiles/TextualEventViewModel.ts","webpack://element-web/./src/events/EventTileFactory.tsx","webpack://element-web/./src/utils/beacon/timeline.ts","webpack://element-web/./src/events/forward/getForwardableEvent.ts","webpack://element-web/./src/events/location/getShareableLocationEvent.ts","webpack://element-web/./src/favicon.ts","webpack://element-web/./src/hooks/room/useRoomMemberProfile.ts","webpack://element-web/./src/hooks/useAsyncMemo.ts","webpack://element-web/./src/hooks/useCall.ts","webpack://element-web/./src/hooks/useDispatcher.ts","webpack://element-web/./src/hooks/useDownloadMedia.ts","webpack://element-web/./src/hooks/useEventEmitter.ts","webpack://element-web/./src/hooks/useFocus.ts","webpack://element-web/./src/hooks/useIsEncrypted.ts","webpack://element-web/./src/hooks/useLocalEcho.ts","webpack://element-web/./src/hooks/useMediaVisible.ts","webpack://element-web/./src/hooks/useRoomNotificationState.ts","webpack://element-web/./src/hooks/useRoomState.ts","webpack://element-web/./src/hooks/useSettings.ts","webpack://element-web/./src/hooks/useStateToggle.ts","webpack://element-web/./src/hooks/useTimeout.ts","webpack://element-web/./src/hooks/useUnreadNotifications.ts","webpack://element-web/./src/ScalarAuthClient.ts","webpack://element-web/./src/components/views/settings/IntegrationManager.tsx","webpack://element-web/./src/integrations/IntegrationManagerInstance.ts","webpack://element-web/./src/components/views/dialogs/IntegrationsImpossibleDialog.tsx","webpack://element-web/./src/components/views/dialogs/IntegrationsDisabledDialog.tsx","webpack://element-web/./src/integrations/IntegrationManagers.ts","webpack://element-web/./src/languageHandler.tsx","webpack://element-web/./src/linkify-matrix.ts","webpack://element-web/./src/utils/MatrixGlob.ts","webpack://element-web/./src/mjolnir/ListRule.ts","webpack://element-web/./src/mjolnir/BanList.ts","webpack://element-web/./src/mjolnir/Mjolnir.ts","webpack://element-web/./src/models/Call.ts","webpack://element-web/./src/models/LocalRoom.ts","webpack://element-web/./src/modules/ConfigApi.ts","webpack://element-web/./src/modules/customComponentApi.ts","webpack://element-web/./src/modules/Profile.ts","webpack://element-web/./src/modules/Navigation.ts","webpack://element-web/./src/modules/Dialog.tsx","webpack://element-web/./src/modules/Auth.ts","webpack://element-web/./src/modules/BuiltinsApi.tsx","webpack://element-web/./src/modules/models/Room.ts","webpack://element-web/./src/modules/AccountDataApi.ts","webpack://element-web/./src/modules/ClientApi.ts","webpack://element-web/./src/modules/StoresApi.ts","webpack://element-web/./src/modules/Api.ts","webpack://element-web/./src/modules/ExtrasApi.ts","webpack://element-web/./src/components/views/dialogs/ModuleUiDialog.tsx","webpack://element-web/./src/modules/ProxiedModuleApi.ts","webpack://element-web/./src/modules/AppModule.ts","webpack://element-web/./src/modules/ModuleComponents.tsx","webpack://element-web/./src/modules/ModuleRunner.ts","webpack://element-web/./src/utils/JSON.ts","webpack://element-web/./src/rageshake/rageshake.ts","webpack://element-web/./src/rageshake/submit-rageshake.ts","webpack://element-web/./src/sentry.ts","webpack://element-web/./src/settings/SettingLevel.ts","webpack://element-web/./src/settings/controllers/ThemeController.ts","webpack://element-web/./src/settings/controllers/FontSizeController.ts","webpack://element-web/./src/settings/controllers/SystemFontController.ts","webpack://element-web/./src/settings/controllers/UIFeatureController.ts","webpack://element-web/./src/settings/controllers/ReducedMotionController.ts","webpack://element-web/./src/settings/controllers/IncompatibleController.ts","webpack://element-web/./src/settings/controllers/SlidingSyncController.ts","webpack://element-web/./src/settings/controllers/ServerSupportUnstableFeatureController.ts","webpack://element-web/./src/settings/controllers/AnalyticsController.ts","webpack://element-web/./src/settings/controllers/FallbackIceServerController.ts","webpack://element-web/./src/settings/controllers/MediaPreviewConfigController.ts","webpack://element-web/./src/@types/invite-rules.ts","webpack://element-web/./src/settings/controllers/InviteRulesConfigController.ts","webpack://element-web/./src/settings/Settings.tsx","webpack://element-web/./src/settings/WatchManager.ts","webpack://element-web/./src/settings/controllers/BlockInvitesConfigController.ts","webpack://element-web/./src/settings/handlers/AbstractLocalStorageSettingsHandler.ts","webpack://element-web/./src/settings/handlers/DefaultSettingsHandler.ts","webpack://element-web/./src/settings/handlers/RoomAccountSettingsHandler.ts","webpack://element-web/./src/settings/handlers/AccountSettingsHandler.ts","webpack://element-web/./src/settings/handlers/RoomSettingsHandler.ts","webpack://element-web/./src/settings/handlers/ConfigSettingsHandler.ts","webpack://element-web/./src/settings/handlers/LocalEchoWrapper.ts","webpack://element-web/./src/settings/handlers/PlatformSettingsHandler.ts","webpack://element-web/./src/settings/SettingsStore.ts","webpack://element-web/./src/settings/handlers/DeviceSettingsHandler.ts","webpack://element-web/./src/settings/handlers/RoomDeviceSettingsHandler.ts","webpack://element-web/./src/settings/UIFeature.ts","webpack://element-web/./src/settings/controllers/DeviceIsolationModeController.ts","webpack://element-web/./src/settings/controllers/MatrixClientBackedController.ts","webpack://element-web/./src/settings/controllers/NotificationControllers.ts","webpack://element-web/./src/settings/controllers/ReloadOnChangeController.ts","webpack://element-web/./src/settings/controllers/SettingController.ts","webpack://element-web/./src/settings/enums/ImageSize.ts","webpack://element-web/./src/settings/enums/Layout.ts","webpack://element-web/./src/settings/handlers/MatrixClientBackedSettingsHandler.ts","webpack://element-web/./src/settings/handlers/SettingsHandler.ts","webpack://element-web/./src/settings/watchers/FontWatcher.ts","webpack://element-web/./src/settings/watchers/ThemeWatcher.ts","webpack://element-web/./src/shouldHideEvent.ts","webpack://element-web/./src/components/views/dialogs/SlashCommandHelpDialog.tsx","webpack://element-web/./src/slash-commands/utils.ts","webpack://element-web/./src/slash-commands/interface.ts","webpack://element-web/./src/slash-commands/command.ts","webpack://element-web/./src/slash-commands/op.ts","webpack://element-web/./src/slash-commands/join.ts","webpack://element-web/./src/slash-commands/upgraderoom/upgraderoom.ts","webpack://element-web/./src/slash-commands/upgraderoom/runUpgradeRoomCommand.ts","webpack://element-web/./src/slash-commands/upgraderoom/parseUpgradeRoomArgs.ts","webpack://element-web/./src/slash-commands/emoticon.ts","webpack://element-web/./src/slash-commands/SlashCommands.tsx","webpack://element-web/./src/stores/ActiveWidgetStore.ts","webpack://element-web/./src/stores/AsyncStore.ts","webpack://element-web/./src/stores/AsyncStoreWithClient.ts","webpack://element-web/./src/stores/BreadcrumbsStore.ts","webpack://element-web/./src/stores/CallStore.ts","webpack://element-web/./src/stores/NonUrgentToastStore.ts","webpack://element-web/./src/stores/OwnBeaconStore.ts","webpack://element-web/./src/stores/OwnProfileStore.ts","webpack://element-web/./src/stores/ReadyWatchingStore.ts","webpack://element-web/./src/stores/ToastStore.ts","webpack://element-web/./src/stores/UIStore.ts","webpack://element-web/./src/stores/WidgetEchoStore.ts","webpack://element-web/./src/stores/WidgetStore.ts","webpack://element-web/./src/stores/local-echo/EchoContext.ts","webpack://element-web/./src/stores/local-echo/RoomEchoContext.ts","webpack://element-web/./src/components/views/dialogs/ServerOfflineDialog.tsx","webpack://element-web/./src/components/views/toasts/NonUrgentEchoFailureToast.tsx","webpack://element-web/./src/stores/local-echo/EchoStore.ts","webpack://element-web/./src/stores/local-echo/EchoChamber.ts","webpack://element-web/./src/stores/local-echo/EchoTransaction.ts","webpack://element-web/./src/stores/local-echo/GenericEchoChamber.ts","webpack://element-web/./src/stores/local-echo/RoomEchoChamber.ts","webpack://element-web/./src/stores/notifications/NotificationLevel.ts","webpack://element-web/./src/stores/notifications/NotificationState.ts","webpack://element-web/./src/stores/notifications/ListNotificationState.ts","webpack://element-web/./src/stores/notifications/RoomNotificationState.ts","webpack://element-web/./src/stores/notifications/SummarizedNotificationState.ts","webpack://element-web/./src/stores/notifications/RoomNotificationStateStore.ts","webpack://element-web/./src/stores/right-panel/RightPanelStoreIPanelState.ts","webpack://element-web/./src/stores/right-panel/RightPanelStore.ts","webpack://element-web/./src/stores/right-panel/RightPanelStorePhases.ts","webpack://element-web/./src/stores/room-list-v3/skip-list/sorters/index.ts","webpack://element-web/./src/stores/room-list/previews/utils.ts","webpack://element-web/./src/stores/room-list/previews/PollStartEventPreview.ts","webpack://element-web/./src/stores/room-list/MessagePreviewStore.ts","webpack://element-web/./src/stores/room-list/previews/MessageEventPreview.ts","webpack://element-web/./src/stores/room-list/previews/LegacyCallInviteEventPreview.ts","webpack://element-web/./src/stores/room-list/previews/LegacyCallAnswerEventPreview.ts","webpack://element-web/./src/stores/room-list/previews/LegacyCallHangupEvent.ts","webpack://element-web/./src/stores/room-list/previews/StickerEventPreview.ts","webpack://element-web/./src/stores/room-list/previews/ReactionEventPreview.ts","webpack://element-web/./src/stores/room-list/ListLayout.ts","webpack://element-web/./src/stores/room-list/RoomListLayoutStore.ts","webpack://element-web/./src/stores/room-list/filters/IFilterCondition.ts","webpack://element-web/./src/stores/room-list/algorithms/tag-sorting/index.ts","webpack://element-web/./src/stores/room-list/algorithms/tag-sorting/AlphabeticAlgorithm.ts","webpack://element-web/./src/stores/room-list/algorithms/tag-sorting/ManualAlgorithm.ts","webpack://element-web/./src/stores/room-list/algorithms/list-ordering/OrderingAlgorithm.ts","webpack://element-web/./src/stores/room-list/algorithms/list-ordering/ImportanceAlgorithm.ts","webpack://element-web/./src/stores/room-list/algorithms/list-ordering/NaturalAlgorithm.ts","webpack://element-web/./src/stores/room-list/algorithms/list-ordering/index.ts","webpack://element-web/./src/stores/room-list/algorithms/Algorithm.ts","webpack://element-web/./src/stores/room-list/filters/SpaceFilterCondition.ts","webpack://element-web/./src/stores/room-list/SpaceWatcher.ts","webpack://element-web/./src/stores/room-list/Interface.ts","webpack://element-web/./src/stores/room-list/RoomListStore.ts","webpack://element-web/./src/stores/room-list/algorithms/models.ts","webpack://element-web/./src/stores/room-list/algorithms/tag-sorting/RecentAlgorithm.ts","webpack://element-web/./src/stores/room-list/filters/VisibilityProvider.ts","webpack://element-web/./src/stores/room-list/models.ts","webpack://element-web/./src/stores/room-list/utils/roomMute.ts","webpack://element-web/./src/stores/notifications/SpaceNotificationState.ts","webpack://element-web/./src/utils/stringOrderField.ts","webpack://element-web/./src/stores/spaces/flattenSpaceHierarchy.ts","webpack://element-web/./src/stores/spaces/SpaceStore.ts","webpack://element-web/./src/stores/spaces/index.ts","webpack://element-web/./src/stores/widgets/ElementWidgetActions.ts","webpack://element-web/./src/stores/widgets/ElementWidgetCapabilities.ts","webpack://element-web/./src/stores/widgets/WidgetLayoutStore.ts","webpack://element-web/./src/components/views/dialogs/WidgetOpenIDPermissionsDialog.tsx","webpack://element-web/./src/widgets/CapabilityText.tsx","webpack://element-web/./src/components/views/dialogs/WidgetCapabilitiesPromptDialog.tsx","webpack://element-web/./src/stores/widgets/ElementWidgetDriver.ts","webpack://element-web/./src/utils/iterables.ts","webpack://element-web/./src/identifiers.ts","webpack://element-web/./src/components/views/dialogs/ModalWidgetDialog.tsx","webpack://element-web/./src/stores/ModalWidgetStore.ts","webpack://element-web/./src/stores/widgets/WidgetMessaging.ts","webpack://element-web/./src/stores/widgets/WidgetMessagingStore.ts","webpack://element-web/./src/stores/widgets/WidgetPermissionStore.ts","webpack://element-web/./src/stores/widgets/types.ts","webpack://element-web/./src/theme.ts","webpack://element-web/./src/toasts/DesktopNotificationsToast.ts","webpack://element-web/./src/components/views/dialogs/ChangelogDialog.tsx","webpack://element-web/./src/toasts/UpdateToast.tsx","webpack://element-web/./src/utils/BrowserWorkarounds.ts","webpack://element-web/./src/utils/DMRoomMap.ts","webpack://element-web/./src/utils/DecryptFile.ts","webpack://element-web/./src/utils/EventUtils.ts","webpack://element-web/./src/utils/Feedback.ts","webpack://element-web/./src/utils/FileDownloader.ts","webpack://element-web/./src/utils/FileUtils.ts","webpack://element-web/./src/utils/FormattingUtils.ts","webpack://element-web/./src/utils/IdentityServerUtils.ts","webpack://element-web/./src/utils/Image.ts","webpack://element-web/./src/utils/KeyVerificationStateObserver.ts","webpack://element-web/./src/utils/MarkedExecution.ts","webpack://element-web/./src/utils/LazyValue.ts","webpack://element-web/./src/utils/MediaEventHelper.ts","webpack://element-web/./src/components/views/dialogs/InviteProgressDialog.tsx","webpack://element-web/./src/utils/MultiInviter.ts","webpack://element-web/./src/utils/NativeEventUtils.ts","webpack://element-web/./src/utils/PinningUtils.ts","webpack://element-web/./src/utils/PreferredRoomVersions.ts","webpack://element-web/./src/utils/ReactUtils.tsx","webpack://element-web/./src/utils/Reply.ts","webpack://element-web/./src/utils/RoomUpgrade.ts","webpack://element-web/./src/utils/ShieldUtils.ts","webpack://element-web/./src/utils/Singleflight.ts","webpack://element-web/./src/utils/SnakedObject.ts","webpack://element-web/./src/utils/SortMembers.ts","webpack://element-web/./src/utils/StorageAccess.ts","webpack://element-web/./src/utils/StorageManager.ts","webpack://element-web/./src/utils/Timer.ts","webpack://element-web/./src/utils/UrlUtils.ts","webpack://element-web/./src/utils/WellKnownUtils.ts","webpack://element-web/./src/utils/Whenable.ts","webpack://element-web/./src/utils/WidgetUtils.ts","webpack://element-web/./src/utils/arrays.ts","webpack://element-web/./src/utils/beacon/getShareableLocation.ts","webpack://element-web/./src/utils/beacon/duration.ts","webpack://element-web/./src/utils/beacon/geolocation.ts","webpack://element-web/./src/utils/beacon/useBeacon.ts","webpack://element-web/./src/utils/beacon/useOwnLiveBeacons.ts","webpack://element-web/./src/utils/blobs.ts","webpack://element-web/./src/utils/colour.ts","webpack://element-web/./src/utils/connection.ts","webpack://element-web/./src/workers/indexeddbWorkerFactory.ts","webpack://element-web/./src/utils/createMatrixClient.ts","webpack://element-web/./src/utils/crypto/deviceInfo.ts","webpack://element-web/./src/utils/crypto/index.ts","webpack://element-web/./src/utils/crypto/shouldForceDisableEncryption.ts","webpack://element-web/./src/utils/device/dehydration.ts","webpack://element-web/./src/utils/device/parseUserAgent.ts","webpack://element-web/./src/utils/dm/startDm.ts","webpack://element-web/./src/utils/threepids.ts","webpack://element-web/./src/utils/direct-messages.ts","webpack://element-web/./src/utils/dm/findDMRoom.ts","webpack://element-web/./src/utils/dm/createDmLocalRoom.ts","webpack://element-web/./src/utils/dm/filterValidMDirect.ts","webpack://element-web/./src/utils/dm/findDMForUser.ts","webpack://element-web/./src/BlurhashEncoder.ts","webpack://element-web/./src/workers/blurhashWorkerFactory.ts","webpack://element-web/./src/utils/image-media.ts","webpack://element-web/./src/components/views/dialogs/LeaveSpaceDialog.tsx","webpack://element-web/./src/utils/leave-behaviour.ts","webpack://element-web/./src/utils/localRoom/isRoomReady.ts","webpack://element-web/./src/utils/local-room.ts","webpack://element-web/./src/utils/localRoom/isLocalRoom.ts","webpack://element-web/./src/utils/location/LocationShareErrors.ts","webpack://element-web/./src/utils/location/findMapStyleUrl.ts","webpack://element-web/./src/utils/location/isSelfLocation.ts","webpack://element-web/./src/utils/location/locationEventGeoUri.ts","webpack://element-web/./src/utils/location/parseGeoUri.ts","webpack://element-web/./src/utils/location/links.ts","webpack://element-web/./src/utils/location/positionFailureMessage.ts","webpack://element-web/./src/utils/maps.ts","webpack://element-web/./src/utils/membership.ts","webpack://element-web/./src/utils/messages.ts","webpack://element-web/./src/utils/notifications.ts","webpack://element-web/./src/utils/objects.ts","webpack://element-web/./src/utils/oidc/persistOidcSettings.ts","webpack://element-web/./src/utils/permalinks/MatrixToPermalinkConstructor.ts","webpack://element-web/./src/utils/permalinks/PermalinkConstructor.ts","webpack://element-web/./src/utils/permalinks/ElementPermalinkConstructor.ts","webpack://element-web/./src/utils/permalinks/MatrixSchemePermalinkConstructor.ts","webpack://element-web/./src/utils/permalinks/Permalinks.ts","webpack://element-web/./src/utils/permalinks/navigator.ts","webpack://element-web/./src/utils/presence.ts","webpack://element-web/./src/utils/promise.ts","webpack://element-web/./src/utils/read-receipts.ts","webpack://element-web/./src/utils/room/getFunctionalMembers.ts","webpack://element-web/./src/utils/room/getJoinedNonFunctionalMembers.ts","webpack://element-web/./src/utils/rooms.ts","webpack://element-web/./src/utils/sets.ts","webpack://element-web/./src/components/views/dialogs/CreateSubspaceDialog.tsx","webpack://element-web/./src/components/views/dialogs/AddExistingSubspaceDialog.tsx","webpack://element-web/./src/utils/space.tsx","webpack://element-web/./src/utils/strings.ts","webpack://element-web/./src/utils/units.ts","webpack://element-web/./src/utils/video-rooms.ts","webpack://element-web/./src/components/views/toasts/GenericExpiringToast.tsx","webpack://element-web/./src/components/views/elements/DesktopCapturerSourcePicker.tsx","webpack://element-web/./src/indexing/BaseEventIndexManager.ts","webpack://element-web/./src/vector/platform/IPCManager.ts","webpack://element-web/./src/vector/platform/SeshatIndexManager.ts","webpack://element-web/./src/vector/platform/ElectronPlatform.tsx","webpack://element-web/./src/utils/SessionLock.ts","webpack://element-web/./src/vector/platform/WebPlatform.ts","webpack://element-web/./src/vector/platform/PWAPlatform.ts","webpack://element-web/./src/vector/rageshakesetup.ts","webpack://element-web/./src/vector/init.tsx","webpack://element-web/./src/verification.ts","webpack://element-web/./src/viewmodels/message-body/DecryptionFailureBodyViewModel.ts","webpack://element-web/./src/widgets/Jitsi.ts","webpack://element-web/./src/widgets/ManagedHybrid.ts","webpack://element-web/./src/widgets/WidgetType.ts","webpack://element-web/./res/img/betas/video_rooms.png","webpack://element-web/./res/img/social/email-1.png","webpack://element-web/./res/img/social/facebook.png","webpack://element-web/./res/img/social/linkedin.png","webpack://element-web/./res/img/social/reddit.png","webpack://element-web/./res/img/social/twitter-2.png","webpack://element-web/./packages/shared-components/dist/element-web-shared-components.js"],"sourcesContent":["var _rect, _g, _path, _g2, _defs;\nfunction _extends() { return _extends = Object.assign ? Object.assign.bind() : function (n) { for (var e = 1; e < arguments.length; e++) { var t = arguments[e]; for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]); } return n; }, _extends.apply(null, arguments); }\nimport * as React from \"react\";\nimport { forwardRef } from \"react\";\nvar SvgElementDesktopLogo = function SvgElementDesktopLogo(props, ref) {\n  return /*#__PURE__*/React.createElement(\"svg\", _extends({\n    xmlns: \"http://www.w3.org/2000/svg\",\n    fill: \"none\",\n    viewBox: \"0 0 1024 1024\",\n    role: \"presentation\",\n    \"aria-hidden\": true,\n    ref: ref\n  }, props), /*#__PURE__*/React.createElement(\"g\", {\n    clipPath: \"url(#element-desktop-logo_svg__a)\"\n  }, /*#__PURE__*/React.createElement(\"mask\", {\n    id: \"element-desktop-logo_svg__b\",\n    width: 1024,\n    height: 1025,\n    x: 0,\n    y: -1,\n    maskUnits: \"userSpaceOnUse\",\n    style: {\n      maskType: \"alpha\"\n    }\n  }, _rect || (_rect = /*#__PURE__*/React.createElement(\"rect\", {\n    width: 1023,\n    height: 1023,\n    x: 0.5,\n    y: 0.5,\n    fill: \"#fff\",\n    stroke: \"#8D8D8D\",\n    rx: 265.5\n  }))), _g || (_g = /*#__PURE__*/React.createElement(\"g\", {\n    mask: \"url(#element-desktop-logo_svg__b)\"\n  }, /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"#fff\",\n    d: \"M0 0h1024v1024H0z\"\n  }), /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"url(#element-desktop-logo_svg__c)\",\n    d: \"M0 0h1024v1024H0z\"\n  }))), /*#__PURE__*/React.createElement(\"g\", {\n    filter: \"url(#element-desktop-logo_svg__d)\"\n  }, _path || (_path = /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"url(#element-desktop-logo_svg__e)\",\n    d: \"M512 106c224.228 0 406 181.772 406 406S736.228 918 512 918 106 736.228 106 512s181.772-406 406-406\"\n  })), /*#__PURE__*/React.createElement(\"path\", {\n    stroke: \"url(#element-desktop-logo_svg__f)\",\n    strokeWidth: 8,\n    d: \"M512 106c224.228 0 406 181.772 406 406S736.228 918 512 918 106 736.228 106 512s181.772-406 406-406Z\",\n    style: {\n      mixBlendMode: \"color-burn\"\n    }\n  }), _g2 || (_g2 = /*#__PURE__*/React.createElement(\"g\", {\n    fill: \"#fff\",\n    fillRule: \"evenodd\",\n    clipRule: \"evenodd\",\n    filter: \"url(#element-desktop-logo_svg__g)\"\n  }, /*#__PURE__*/React.createElement(\"path\", {\n    d: \"M437.051 293.072c0-16.547 13.442-29.961 30.024-29.961 112.383 0 203.489 90.916 203.489 203.067 0 16.547-13.442 29.961-30.024 29.961-16.581 0-30.023-13.414-30.023-29.961 0-79.057-64.221-143.145-143.442-143.145-16.582 0-30.024-13.414-30.024-29.961\"\n  }), /*#__PURE__*/React.createElement(\"path\", {\n    d: \"M730.866 436.217c16.581 0 30.023 13.414 30.023 29.961 0 112.15-91.105 203.066-203.489 203.066-16.581 0-30.023-13.414-30.023-29.961s13.442-29.96 30.023-29.96c79.221 0 143.443-64.089 143.443-143.145 0-16.547 13.442-29.961 30.023-29.961\"\n  }), /*#__PURE__*/React.createElement(\"path\", {\n    d: \"M587.421 730.924c0 16.547-13.442 29.96-30.023 29.96-112.384 0-203.489-90.916-203.489-203.066 0-16.547 13.442-29.961 30.023-29.961s30.023 13.414 30.023 29.961c0 79.057 64.221 143.145 143.443 143.145 16.581 0 30.023 13.414 30.023 29.961\"\n  }), /*#__PURE__*/React.createElement(\"path\", {\n    d: \"M293.134 587.779c-16.581 0-30.023-13.414-30.023-29.961 0-112.15 91.105-203.067 203.489-203.067 16.582 0 30.023 13.414 30.023 29.961s-13.441 29.961-30.023 29.961c-79.221 0-143.442 64.088-143.442 143.145 0 16.547-13.442 29.961-30.024 29.961\"\n  }))))), _defs || (_defs = /*#__PURE__*/React.createElement(\"defs\", null, /*#__PURE__*/React.createElement(\"linearGradient\", {\n    id: \"element-desktop-logo_svg__c\",\n    x1: 512,\n    x2: 512,\n    y1: 1024,\n    y2: 0,\n    gradientUnits: \"userSpaceOnUse\"\n  }, /*#__PURE__*/React.createElement(\"stop\", {\n    stopColor: \"#04B96A\",\n    stopOpacity: 0.41\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 0.2,\n    stopColor: \"#07B661\",\n    stopOpacity: 0.23\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 0.4,\n    stopColor: \"#00B85C\",\n    stopOpacity: 0.11\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 0.6,\n    stopColor: \"#16BB69\",\n    stopOpacity: 0.06\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 0.8,\n    stopColor: \"#16BB79\",\n    stopOpacity: 0.03\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 1,\n    stopColor: \"#fff\",\n    stopOpacity: 0\n  })), /*#__PURE__*/React.createElement(\"linearGradient\", {\n    id: \"element-desktop-logo_svg__e\",\n    x1: 512,\n    x2: 512,\n    y1: 102,\n    y2: 922,\n    gradientUnits: \"userSpaceOnUse\"\n  }, /*#__PURE__*/React.createElement(\"stop\", {\n    stopColor: \"#98E1C1\"\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 0.33,\n    stopColor: \"#0BC491\"\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 0.66,\n    stopColor: \"#007A61\"\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 1,\n    stopColor: \"#005C45\"\n  })), /*#__PURE__*/React.createElement(\"linearGradient\", {\n    id: \"element-desktop-logo_svg__f\",\n    x1: 512,\n    x2: 512,\n    y1: 102,\n    y2: 922,\n    gradientUnits: \"userSpaceOnUse\"\n  }, /*#__PURE__*/React.createElement(\"stop\", {\n    stopColor: \"#16BB79\",\n    stopOpacity: 0.03\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 0.25,\n    stopColor: \"#16BB69\",\n    stopOpacity: 0.06\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 0.5,\n    stopColor: \"#00B85C\",\n    stopOpacity: 0.11\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 0.75,\n    stopColor: \"#07B661\",\n    stopOpacity: 0.23\n  }), /*#__PURE__*/React.createElement(\"stop\", {\n    offset: 1,\n    stopColor: \"#04B96A\",\n    stopOpacity: 0.41\n  })), /*#__PURE__*/React.createElement(\"filter\", {\n    id: \"element-desktop-logo_svg__d\",\n    width: 1060,\n    height: 1266,\n    x: -18,\n    y: 78,\n    colorInterpolationFilters: \"sRGB\",\n    filterUnits: \"userSpaceOnUse\"\n  }, /*#__PURE__*/React.createElement(\"feFlood\", {\n    floodOpacity: 0,\n    result: \"BackgroundImageFix\"\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    \"in\": \"SourceAlpha\",\n    result: \"hardAlpha\",\n    values: \"0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 127 0\"\n  }), /*#__PURE__*/React.createElement(\"feOffset\", {\n    dy: 18\n  }), /*#__PURE__*/React.createElement(\"feGaussianBlur\", {\n    stdDeviation: 21\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    values: \"0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.1 0\"\n  }), /*#__PURE__*/React.createElement(\"feBlend\", {\n    in2: \"BackgroundImageFix\",\n    result: \"effect1_dropShadow_178_1078\"\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    \"in\": \"SourceAlpha\",\n    result: \"hardAlpha\",\n    values: \"0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 127 0\"\n  }), /*#__PURE__*/React.createElement(\"feOffset\", {\n    dy: 76\n  }), /*#__PURE__*/React.createElement(\"feGaussianBlur\", {\n    stdDeviation: 38\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    values: \"0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.08 0\"\n  }), /*#__PURE__*/React.createElement(\"feBlend\", {\n    in2: \"effect1_dropShadow_178_1078\",\n    result: \"effect2_dropShadow_178_1078\"\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    \"in\": \"SourceAlpha\",\n    result: \"hardAlpha\",\n    values: \"0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 127 0\"\n  }), /*#__PURE__*/React.createElement(\"feOffset\", {\n    dy: 170\n  }), /*#__PURE__*/React.createElement(\"feGaussianBlur\", {\n    stdDeviation: 51\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    values: \"0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.05 0\"\n  }), /*#__PURE__*/React.createElement(\"feBlend\", {\n    in2: \"effect2_dropShadow_178_1078\",\n    result: \"effect3_dropShadow_178_1078\"\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    \"in\": \"SourceAlpha\",\n    result: \"hardAlpha\",\n    values: \"0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 127 0\"\n  }), /*#__PURE__*/React.createElement(\"feOffset\", {\n    dy: 302\n  }), /*#__PURE__*/React.createElement(\"feGaussianBlur\", {\n    stdDeviation: 60\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    values: \"0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.01 0\"\n  }), /*#__PURE__*/React.createElement(\"feBlend\", {\n    in2: \"effect3_dropShadow_178_1078\",\n    result: \"effect4_dropShadow_178_1078\"\n  }), /*#__PURE__*/React.createElement(\"feBlend\", {\n    \"in\": \"SourceGraphic\",\n    in2: \"effect4_dropShadow_178_1078\",\n    result: \"shape\"\n  })), /*#__PURE__*/React.createElement(\"filter\", {\n    id: \"element-desktop-logo_svg__g\",\n    width: 537.778,\n    height: 537.773,\n    x: 243.111,\n    y: 247.111,\n    colorInterpolationFilters: \"sRGB\",\n    filterUnits: \"userSpaceOnUse\"\n  }, /*#__PURE__*/React.createElement(\"feFlood\", {\n    floodOpacity: 0,\n    result: \"BackgroundImageFix\"\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    \"in\": \"SourceAlpha\",\n    result: \"hardAlpha\",\n    values: \"0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 127 0\"\n  }), /*#__PURE__*/React.createElement(\"feOffset\", {\n    dy: 4\n  }), /*#__PURE__*/React.createElement(\"feGaussianBlur\", {\n    stdDeviation: 10\n  }), /*#__PURE__*/React.createElement(\"feComposite\", {\n    in2: \"hardAlpha\",\n    operator: \"out\"\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    values: \"0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0.25 0\"\n  }), /*#__PURE__*/React.createElement(\"feBlend\", {\n    in2: \"BackgroundImageFix\",\n    result: \"effect1_dropShadow_178_1078\"\n  }), /*#__PURE__*/React.createElement(\"feBlend\", {\n    \"in\": \"SourceGraphic\",\n    in2: \"effect1_dropShadow_178_1078\",\n    result: \"shape\"\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    \"in\": \"SourceAlpha\",\n    result: \"hardAlpha\",\n    values: \"0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 127 0\"\n  }), /*#__PURE__*/React.createElement(\"feOffset\", {\n    dy: -16\n  }), /*#__PURE__*/React.createElement(\"feGaussianBlur\", {\n    stdDeviation: 11\n  }), /*#__PURE__*/React.createElement(\"feComposite\", {\n    in2: \"hardAlpha\",\n    k2: -1,\n    k3: 1,\n    operator: \"arithmetic\"\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    values: \"0 0 0 0 0.596078 0 0 0 0 0.882353 0 0 0 0 0.756863 0 0 0 1 0\"\n  }), /*#__PURE__*/React.createElement(\"feBlend\", {\n    in2: \"shape\",\n    result: \"effect2_innerShadow_178_1078\"\n  })), /*#__PURE__*/React.createElement(\"clipPath\", {\n    id: \"element-desktop-logo_svg__a\"\n  }, /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"#fff\",\n    d: \"M0 0h1024v1024H0z\"\n  })))));\n};\nvar ForwardRef = /*#__PURE__*/forwardRef(SvgElementDesktopLogo);\nexport { ForwardRef as Icon };\nexport default \"img/element-desktop-logo.f4b4c62.svg\";","var _path, _path2, _path3, _path4;\nfunction _extends() { return _extends = Object.assign ? Object.assign.bind() : function (n) { for (var e = 1; e < arguments.length; e++) { var t = arguments[e]; for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]); } return n; }, _extends.apply(null, arguments); }\nimport * as React from \"react\";\nimport { forwardRef } from \"react\";\nvar SvgEmailPrompt = function SvgEmailPrompt(props, ref) {\n  return /*#__PURE__*/React.createElement(\"svg\", _extends({\n    xmlns: \"http://www.w3.org/2000/svg\",\n    viewBox: \"0 0 57 46\",\n    role: \"presentation\",\n    \"aria-hidden\": true,\n    ref: ref\n  }, props), _path || (_path = /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"#737d8c\",\n    d: \"M4 17c-.5 0-.975.096-1.416.264L20 34.68l17.416-17.416A4 4 0 0 0 36 17ZM.264 19.584A4 4 0 0 0 0 21v21a4 4 0 0 0 4 4h32a4 4 0 0 0 4-4V21c0-.5-.096-.975-.264-1.416L21.16 38.16a1.6 1.6 0 0 1-.533.356 1.6 1.6 0 0 1-.627.125 1.6 1.6 0 0 1-.627-.125 1.6 1.6 0 0 1-.533-.356z\"\n  })), _path2 || (_path2 = /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"#0dbd8b\",\n    fillOpacity: 0.1,\n    d: \"M57 16a16 16 0 0 1-16 16 16 16 0 0 1-16-16A16 16 0 0 1 41 0a16 16 0 0 1 16 16\"\n  })), _path3 || (_path3 = /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"#fff\",\n    d: \"M53 16a12 12 0 0 1-12 12 12 12 0 0 1-12-12A12 12 0 0 1 41 4a12 12 0 0 1 12 12\"\n  })), _path4 || (_path4 = /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"#0dbd8b\",\n    d: \"M49 16a8 8 0 0 1-8 8 8 8 0 0 1-8-8 8 8 0 0 1 8-8 8 8 0 0 1 8 8\"\n  })));\n};\nvar ForwardRef = /*#__PURE__*/forwardRef(SvgEmailPrompt);\nexport { ForwardRef as Icon };\nexport default \"img/element-icons/email-prompt.67a8ba4.svg\";","var _defs, _g;\nfunction _extends() { return _extends = Object.assign ? Object.assign.bind() : function (n) { for (var e = 1; e < arguments.length; e++) { var t = arguments[e]; for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]); } return n; }, _extends.apply(null, arguments); }\nimport * as React from \"react\";\nimport { forwardRef } from \"react\";\nvar SvgIconEmailPillAvatar = function SvgIconEmailPillAvatar(props, ref) {\n  return /*#__PURE__*/React.createElement(\"svg\", _extends({\n    xmlns: \"http://www.w3.org/2000/svg\",\n    viewBox: \"0 0 65.631 67.981\",\n    role: \"presentation\",\n    \"aria-hidden\": true,\n    ref: ref\n  }, props), _defs || (_defs = /*#__PURE__*/React.createElement(\"defs\", null, /*#__PURE__*/React.createElement(\"filter\", {\n    id: \"icon-email-pill-avatar_svg__a\",\n    width: 1.118,\n    height: 1.158,\n    x: -0.059,\n    y: -0.079,\n    filterUnits: \"objectBoundingBox\"\n  }, /*#__PURE__*/React.createElement(\"feOffset\", {\n    dy: 2,\n    \"in\": \"SourceAlpha\",\n    result: \"shadowOffsetOuter1\"\n  }), /*#__PURE__*/React.createElement(\"feGaussianBlur\", {\n    \"in\": \"shadowOffsetOuter1\",\n    result: \"shadowBlurOuter1\",\n    stdDeviation: 16\n  }), /*#__PURE__*/React.createElement(\"feColorMatrix\", {\n    \"in\": \"shadowBlurOuter1\",\n    result: \"shadowMatrixOuter1\",\n    values: \"0 0 0 0 0 0 0 0 0 0.473684211 0 0 0 0 1 0 0 0 0.241258741 0\"\n  }), /*#__PURE__*/React.createElement(\"feMerge\", null, /*#__PURE__*/React.createElement(\"feMergeNode\", {\n    \"in\": \"shadowMatrixOuter1\"\n  }), /*#__PURE__*/React.createElement(\"feMergeNode\", {\n    \"in\": \"SourceGraphic\"\n  }))))), _g || (_g = /*#__PURE__*/React.createElement(\"g\", {\n    fill: \"none\",\n    fillRule: \"evenodd\",\n    stroke: \"#368bd6\",\n    strokeLinecap: \"round\",\n    strokeLinejoin: \"round\",\n    filter: \"url(#icon-email-pill-avatar_svg__a)\",\n    transform: \"translate(-1493.716 -795.144)scale(3.40907)\"\n  }, /*#__PURE__*/React.createElement(\"g\", {\n    transform: \"translate(441.5 237.5)\"\n  }, /*#__PURE__*/React.createElement(\"circle\", {\n    cx: 6.286,\n    cy: 5.714,\n    r: 2.286\n  }), /*#__PURE__*/React.createElement(\"path\", {\n    d: \"M8.571 3.429v2.857a1.714 1.714 0 1 0 3.429 0v-.572a5.714 5.714 0 1 0-2.24 4.537\"\n  })))));\n};\nvar ForwardRef = /*#__PURE__*/forwardRef(SvgIconEmailPillAvatar);\nexport { ForwardRef as Icon };\nexport default \"img/icon-email-pill-avatar.a6d2e88.svg\";","var _path;\nfunction _extends() { return _extends = Object.assign ? Object.assign.bind() : function (n) { for (var e = 1; e < arguments.length; e++) { var t = arguments[e]; for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]); } return n; }, _extends.apply(null, arguments); }\nimport * as React from \"react\";\nimport { forwardRef } from \"react\";\nvar SvgLiveLocation = function SvgLiveLocation(props, ref) {\n  return /*#__PURE__*/React.createElement(\"svg\", _extends({\n    xmlns: \"http://www.w3.org/2000/svg\",\n    fill: \"none\",\n    viewBox: \"0 0 26 14\",\n    role: \"presentation\",\n    \"aria-hidden\": true,\n    ref: ref\n  }, props), _path || (_path = /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"currentColor\",\n    fillRule: \"evenodd\",\n    d: \"M3.654 13.153a.87.87 0 0 0 .063-1.173c-2.41-2.93-2.41-7.185-.007-10.121A.885.885 0 0 0 3.654.673a.89.89 0 0 0-1.318.063c-2.93 3.582-2.93 8.765 0 12.354a.885.885 0 0 0 1.318.063m2.529-2.529a.885.885 0 0 0 .081-1.148 4.43 4.43 0 0 1 0-5.12.89.89 0 0 0-.081-1.148l-.007-.006c-.376-.377-1.016-.352-1.324.081a6.22 6.22 0 0 0 0 7.266c.314.433.948.458 1.33.075m7.132-9.585c-2.429 0-4.392 2.018-4.392 4.512 0 2.688 2.773 6.394 3.915 7.805.25.31.709.31.96 0 1.136-1.411 3.909-5.117 3.909-7.805 0-2.494-1.964-4.512-4.392-4.512m0 6.123c-.866 0-1.569-.722-1.569-1.611 0-.89.703-1.611 1.569-1.611s1.568.721 1.568 1.61-.702 1.612-1.568 1.612m8.994 4.818a.87.87 0 0 0 .063 1.173.885.885 0 0 0 1.318-.063c2.93-3.589 2.93-8.772 0-12.354a.89.89 0 0 0-1.318-.063.885.885 0 0 0-.056 1.186c2.403 2.936 2.403 7.19-.007 10.12m-2.547-2.504a.885.885 0 0 0 .081 1.148c.383.383 1.017.358 1.33-.075a6.22 6.22 0 0 0 0-7.266c-.307-.433-.947-.458-1.323-.081l-.007.006a.89.89 0 0 0-.081 1.148 4.43 4.43 0 0 1 0 5.12\",\n    clipRule: \"evenodd\"\n  })));\n};\nvar ForwardRef = /*#__PURE__*/forwardRef(SvgLiveLocation);\nexport { ForwardRef as Icon };\nexport default \"img/location/live-location.db24eab.svg\";","module.exports = __webpack_public_path__ + \"recorder.worklet.js\";","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport enum MediaPreviewValue {\n    /**\n     * Media previews should be enabled.\n     */\n    On = \"on\",\n    /**\n     * Media previews should only be enabled for rooms with non-public join rules.\n     */\n    Private = \"private\",\n    /**\n     * Media previews should be disabled.\n     */\n    Off = \"off\",\n}\n\nexport const MEDIA_PREVIEW_ACCOUNT_DATA_TYPE = \"io.element.msc4278.media_preview_config\";\nexport interface MediaPreviewConfig extends Record<string, unknown> {\n    /**\n     * Media preview setting for thumbnails of media in rooms.\n     */\n    media_previews: MediaPreviewValue;\n    /**\n     * Media preview settings for avatars of rooms we have been invited to.\n     */\n    invite_avatars: MediaPreviewValue.On | MediaPreviewValue.Off;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type RoomMember, type User, type Room, type ResizeMethod } from \"matrix-js-sdk/src/matrix\";\nimport { useIdColorHash } from \"@vector-im/compound-web\";\n\nimport DMRoomMap from \"./utils/DMRoomMap\";\nimport { mediaFromMxc } from \"./customisations/Media\";\nimport { isLocalRoom } from \"./utils/localRoom/isLocalRoom\";\nimport { getFirstGrapheme } from \"./utils/strings\";\nimport ThemeWatcher from \"./settings/watchers/ThemeWatcher\";\n\n/**\n * Hardcoded from the Compound colors.\n * Shade for background as defined in the compound web implementation\n * https://github.com/vector-im/compound-web/blob/main/src/components/Avatar\n */\nconst AVATAR_BG_LIGHT_COLORS = [\"#e0f8d9\", \"#e3f5f8\", \"#faeefb\", \"#f1efff\", \"#ffecf0\", \"#ffefe4\"];\nconst AVATAR_TEXT_LIGHT_COLORS = [\"#005f00\", \"#00548c\", \"#822198\", \"#5d26cd\", \"#9f0850\", \"#9b2200\"];\n\nconst AVATAR_BG_DARK_COLORS = [\"#002600\", \"#001b4e\", \"#37004e\", \"#22006a\", \"#450018\", \"#470000\"];\nconst AVATAR_TEXT_DARK_COLORS = [\"#56c02c\", \"#21bacd\", \"#d991de\", \"#ad9cfe\", \"#fe84a2\", \"#f6913d\"];\n\n// Not to be used for BaseAvatar urls as that has similar default avatar fallback already\nexport function avatarUrlForMember(\n    member: RoomMember | undefined,\n    width: number,\n    height: number,\n    resizeMethod: ResizeMethod,\n): string {\n    let url: string | null | undefined;\n    if (member?.getMxcAvatarUrl()) {\n        url = mediaFromMxc(member.getMxcAvatarUrl()).getThumbnailOfSourceHttp(width, height, resizeMethod);\n    }\n    if (!url) {\n        // member can be null here currently since on invites, the JS SDK\n        // does not have enough info to build a RoomMember object for\n        // the inviter.\n        url = defaultAvatarUrlForString(member ? member.userId : \"\");\n    }\n    return url;\n}\n\n/**\n * Determines if the current theme is dark\n */\nfunction isDarkTheme(): boolean {\n    return new ThemeWatcher().getEffectiveTheme() === \"dark\";\n}\n\n/**\n * Determines the HEX color to use in the avatar pills\n * @param id the user or room ID\n * @returns the text color to use on the avatar\n */\nexport function getAvatarTextColor(id: string): string {\n    // eslint-disable-next-line react-hooks/rules-of-hooks\n    const index = useIdColorHash(id);\n\n    // Use light colors by default\n    return isDarkTheme() ? AVATAR_TEXT_DARK_COLORS[index - 1] : AVATAR_TEXT_LIGHT_COLORS[index - 1];\n}\n\nexport function avatarUrlForUser(\n    user: Pick<User, \"avatarUrl\">,\n    width: number,\n    height: number,\n    resizeMethod?: ResizeMethod,\n): string | null {\n    if (!user.avatarUrl) return null;\n    return mediaFromMxc(user.avatarUrl).getThumbnailOfSourceHttp(width, height, resizeMethod);\n}\n\nfunction isValidHexColor(color: string): boolean {\n    return (\n        typeof color === \"string\" &&\n        (color.length === 7 || color.length === 9) &&\n        color.startsWith(\"#\") &&\n        !color\n            .slice(1)\n            .split(\"\")\n            .some((c) => isNaN(parseInt(c, 16)))\n    );\n}\n\nfunction urlForColor(color: string): string {\n    const size = 40;\n    const canvas = document.createElement(\"canvas\");\n    canvas.width = size;\n    canvas.height = size;\n    const ctx = canvas.getContext(\"2d\");\n    // bail out when using jsdom in unit tests\n    if (!ctx) {\n        return \"\";\n    }\n    ctx.fillStyle = color;\n    ctx.fillRect(0, 0, size, size);\n    return canvas.toDataURL();\n}\n\n// XXX: Ideally we'd clear this cache when the theme changes\n// but since this function is at global scope, it's a bit\n// hard to install a listener here, even if there were a clear event to listen to\nconst colorToDataURLCache = new Map<string, string>();\n\nexport function defaultAvatarUrlForString(s: string): string {\n    if (!s) return \"\"; // XXX: should never happen but empirically does by evidence of a rageshake\n    // eslint-disable-next-line react-hooks/rules-of-hooks\n    const colorIndex = useIdColorHash(s);\n    // overwritten color value in custom themes\n    const cssVariable = `--avatar-background-colors_${colorIndex}`;\n    const cssValue = getComputedStyle(document.body).getPropertyValue(cssVariable);\n    // Light colors are the default\n    const color =\n        cssValue || isDarkTheme() ? AVATAR_BG_DARK_COLORS[colorIndex - 1] : AVATAR_BG_LIGHT_COLORS[colorIndex - 1];\n\n    let dataUrl = colorToDataURLCache.get(color);\n    if (!dataUrl) {\n        // validate color as this can come from account_data\n        // with custom theming\n        if (isValidHexColor(color)) {\n            dataUrl = urlForColor(color);\n            colorToDataURLCache.set(color, dataUrl);\n        } else {\n            dataUrl = \"\";\n        }\n    }\n    return dataUrl;\n}\n\n/**\n * returns the first (non-sigil) character of 'name',\n * converted to uppercase\n * @param {string} name\n * @return {string} the first letter\n */\nexport function getInitialLetter(name: string): string | undefined {\n    if (!name) {\n        // XXX: We should find out what causes the name to sometimes be falsy.\n        console.trace(\"`name` argument to `getInitialLetter` not supplied\");\n        return undefined;\n    }\n    if (name.length < 1) {\n        return undefined;\n    }\n\n    const initial = name[0];\n    if ((initial === \"@\" || initial === \"#\" || initial === \"+\") && name[1]) {\n        name = name.substring(1);\n    }\n\n    return getFirstGrapheme(name).toUpperCase();\n}\n\nexport function avatarUrlForRoom(\n    room: Room | null,\n    width?: number,\n    height?: number,\n    resizeMethod?: ResizeMethod,\n    avatarMxcOverride?: string,\n): string | null {\n    if (!room) return null; // null-guard\n    const mxc = avatarMxcOverride ?? room.getMxcAvatarUrl();\n    if (mxc) {\n        const media = mediaFromMxc(mxc);\n        if (width !== undefined && height !== undefined) {\n            return media.getThumbnailOfSourceHttp(width, height, resizeMethod);\n        }\n        return media.srcHttp;\n    }\n\n    // space rooms cannot be DMs so skip the rest\n    if (room.isSpaceRoom()) return null;\n\n    // If the room is not a DM don't fallback to a member avatar\n    if (!DMRoomMap.shared().getUserIdForRoomId(room.roomId) && !isLocalRoom(room)) {\n        return null;\n    }\n\n    // If there are only two members in the DM use the avatar of the other member\n    const otherMember = room.getAvatarFallbackMember();\n    if (otherMember?.getMxcAvatarUrl()) {\n        const media = mediaFromMxc(otherMember.getMxcAvatarUrl());\n        if (width !== undefined && height !== undefined) {\n            return media.getThumbnailOfSourceHttp(width, height, resizeMethod);\n        }\n        return media.srcHttp;\n    }\n    return null;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2024 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2016 Aviral Dasgupta\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// Note: we don't import the base64 utils from `matrix-js-sdk/src/matrix` because this file\n// is used by Element Web's service worker, and importing `matrix` brings in ~1mb of stuff\n// we don't need. Instead, we ignore the import restriction and only bring in what we actually\n// need.\n// Note: `base64` is not public in the js-sdk, so if it changes/breaks, that's on us. We should\n// be okay with our frequent tests, locked versioning, etc though. We'll pick up problems well\n// before release.\n// eslint-disable-next-line no-restricted-imports\nimport { encodeUnpaddedBase64 } from \"matrix-js-sdk/src/base64\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\n/**\n * Encrypted format of a pickle key, as stored in IndexedDB.\n */\nexport interface EncryptedPickleKey {\n    /** The encrypted payload. */\n    encrypted?: BufferSource;\n\n    /** Initialisation vector for the encryption. */\n    iv?: BufferSource;\n\n    /** The encryption key which was used to encrypt the payload. */\n    cryptoKey?: CryptoKey;\n}\n\n/**\n * Calculates the `additionalData` for the AES-GCM key used by the pickling processes. This\n * additional data is *not* encrypted, but *is* authenticated. The additional data is constructed\n * from the user ID and device ID provided.\n *\n * The later-constructed pickle key is used to decrypt values, such as access tokens, from IndexedDB.\n *\n * See https://developer.mozilla.org/en-US/docs/Web/API/AesGcmParams for more information on\n * `additionalData`.\n *\n * @param {string} userId The user ID who owns the pickle key.\n * @param {string} deviceId The device ID which owns the pickle key.\n * @return {Uint8Array} The additional data as a Uint8Array.\n */\nexport function getPickleAdditionalData(userId: string, deviceId: string): Uint8Array<ArrayBuffer> {\n    const additionalData = new Uint8Array(userId.length + deviceId.length + 1);\n    for (let i = 0; i < userId.length; i++) {\n        additionalData[i] = userId.charCodeAt(i);\n    }\n    additionalData[userId.length] = 124; // \"|\"\n    for (let i = 0; i < deviceId.length; i++) {\n        additionalData[userId.length + 1 + i] = deviceId.charCodeAt(i);\n    }\n    return additionalData;\n}\n\n/**\n * Encrypt the given pickle key, ready for storage in the database.\n *\n * @param pickleKey - The key to be encrypted.\n * @param userId - The user ID the pickle key belongs to.\n * @param deviceId - The device ID the pickle key belongs to.\n *\n * @returns Data object ready for storing in indexeddb.\n */\nexport async function encryptPickleKey(\n    pickleKey: Uint8Array<ArrayBuffer>,\n    userId: string,\n    deviceId: string,\n): Promise<EncryptedPickleKey | undefined> {\n    if (!crypto?.subtle) {\n        return undefined;\n    }\n    const cryptoKey = await crypto.subtle.generateKey({ name: \"AES-GCM\", length: 256 }, false, [\"encrypt\", \"decrypt\"]);\n    const iv = new Uint8Array(32);\n    crypto.getRandomValues(iv);\n\n    const additionalData = getPickleAdditionalData(userId, deviceId);\n    const encrypted = await crypto.subtle.encrypt({ name: \"AES-GCM\", iv, additionalData }, cryptoKey, pickleKey);\n    return { encrypted, iv, cryptoKey };\n}\n\n/**\n * Decrypts the provided data into a pickle key and base64-encodes it ready for use elsewhere.\n *\n * If `data` is undefined in part or in full, returns undefined.\n *\n *  If crypto functions are not available, returns undefined regardless of input.\n *\n * @param data An object containing the encrypted pickle key data: encrypted payload, initialization vector (IV), and crypto key. Typically loaded from indexedDB.\n * @param userId The user ID the pickle key belongs to.\n * @param deviceId The device ID the pickle key belongs to.\n * @returns A promise that resolves to the encoded pickle key, or undefined if the key cannot be built and encoded.\n */\nexport async function buildAndEncodePickleKey(\n    data: EncryptedPickleKey | undefined,\n    userId: string,\n    deviceId: string,\n): Promise<string | undefined> {\n    if (!crypto?.subtle) {\n        return undefined;\n    }\n    if (!data || !data.encrypted || !data.iv || !data.cryptoKey) {\n        return undefined;\n    }\n\n    try {\n        const additionalData = getPickleAdditionalData(userId, deviceId);\n        const pickleKeyBuf = await crypto.subtle.decrypt(\n            { name: \"AES-GCM\", iv: data.iv, additionalData },\n            data.cryptoKey,\n            data.encrypted,\n        );\n        if (pickleKeyBuf) {\n            return encodeUnpaddedBase64(new Uint8Array(pickleKeyBuf));\n        }\n    } catch {\n        logger.error(\"Error decrypting pickle key\");\n    }\n\n    return undefined;\n}\n","/*\nCopyright 2018-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type { IConfigOptions } from \"../IConfigOptions\";\n\n// Load the config file. First try to load up a domain-specific config of the\n// form \"config.$domain.json\" and if that fails, fall back to config.json.\nexport async function getVectorConfig(relativeLocation = \"\"): Promise<IConfigOptions | undefined> {\n    if (relativeLocation !== \"\" && !relativeLocation.endsWith(\"/\")) relativeLocation += \"/\";\n\n    // Handle trailing dot FQDNs\n    let domain = window.location.hostname.trimEnd();\n    if (domain.endsWith(\".\")) {\n        domain = domain.slice(0, -1);\n    }\n\n    const specificConfigPromise = getConfig(`${relativeLocation}config.${domain}.json`);\n    const generalConfigPromise = getConfig(relativeLocation + \"config.json\");\n\n    try {\n        const configJson = await specificConfigPromise;\n        // 404s succeed with an empty json config, so check that there are keys\n        if (!configJson || Object.keys(configJson).length === 0) {\n            throw new Error(); // throw to enter the catch\n        }\n        return configJson;\n    } catch {\n        return generalConfigPromise;\n    }\n}\n\nasync function getConfig(configJsonFilename: string): Promise<IConfigOptions | undefined> {\n    const url = new URL(configJsonFilename, window.location.href);\n    url.searchParams.set(\"cachebuster\", Date.now().toString());\n    const res = await fetch(url, {\n        cache: \"no-cache\",\n        method: \"GET\",\n    });\n\n    if (res.status === 404 || res.status === 0) {\n        // Lack of a config isn't an error, we should just use the defaults.\n        // Also treat a blank config as no config, assuming the status code is 0, because we don't get 404s from file:\n        // URIs so this is the only way we can not fail if the file doesn't exist when loading from a file:// URI.\n        return {} as IConfigOptions;\n    }\n\n    if (res.ok) {\n        return res.json();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2016 Aviral Dasgupta\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type MatrixClient,\n    type MatrixEvent,\n    type Room,\n    type SSOAction,\n    encodeUnpaddedBase64,\n    type OidcRegistrationClientMetadata,\n    MatrixEventEvent,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport dis from \"./dispatcher/dispatcher\";\nimport type BaseEventIndexManager from \"./indexing/BaseEventIndexManager\";\nimport { type ActionPayload } from \"./dispatcher/payloads\";\nimport { type CheckUpdatesPayload } from \"./dispatcher/payloads/CheckUpdatesPayload\";\nimport { Action } from \"./dispatcher/actions\";\nimport { hideToast as hideUpdateToast } from \"./toasts/UpdateToast\";\nimport { MatrixClientPeg } from \"./MatrixClientPeg\";\nimport { idbLoad, idbSave, idbDelete } from \"./utils/StorageAccess\";\nimport { type ViewRoomPayload } from \"./dispatcher/payloads/ViewRoomPayload\";\nimport { type IConfigOptions } from \"./IConfigOptions\";\nimport SdkConfig from \"./SdkConfig\";\nimport { buildAndEncodePickleKey, encryptPickleKey } from \"./utils/tokens/pickling\";\nimport Favicon from \"./favicon.ts\";\nimport { getVectorConfig } from \"./vector/getconfig.ts\";\n\nexport const SSO_HOMESERVER_URL_KEY = \"mx_sso_hs_url\";\nexport const SSO_ID_SERVER_URL_KEY = \"mx_sso_is_url\";\nexport const SSO_IDP_ID_KEY = \"mx_sso_idp_id\";\n\nexport enum UpdateCheckStatus {\n    Checking = \"CHECKING\",\n    Error = \"ERROR\",\n    NotAvailable = \"NOTAVAILABLE\",\n    Downloading = \"DOWNLOADING\",\n    Ready = \"READY\",\n}\n\nexport interface UpdateStatus {\n    /**\n     * The current phase of the manual update check.\n     */\n    status: UpdateCheckStatus;\n    /**\n     * Detail string relating to the current status, typically for error details.\n     */\n    detail?: string;\n}\n\nconst UPDATE_DEFER_KEY = \"mx_defer_update\";\n\n/**\n * Base class for classes that provide platform-specific functionality\n * eg. Setting an application badge or displaying notifications\n *\n * Instances of this class are provided by the application.\n */\nexport default abstract class BasePlatform {\n    protected notificationCount = 0;\n    protected errorDidOccur = false;\n    protected _favicon?: Favicon;\n    public readonly initialised = Promise.resolve<void>(undefined);\n\n    protected constructor() {\n        dis.register(this.onAction.bind(this));\n        this.startUpdateCheck = this.startUpdateCheck.bind(this);\n    }\n\n    public async getConfig(): Promise<IConfigOptions | undefined> {\n        return getVectorConfig();\n    }\n\n    /**\n     * Get a sensible default display name for the device Element is running on\n     */\n    public abstract getDefaultDeviceDisplayName(): string;\n\n    protected onAction(payload: ActionPayload): void {\n        switch (payload.action) {\n            case Action.ClientNotViable:\n            case Action.OnLoggedOut:\n                this.setNotificationCount(0);\n                break;\n        }\n    }\n\n    // Used primarily for Analytics\n    public abstract getHumanReadableName(): string;\n\n    public setNotificationCount(count: number): void {\n        if (this.notificationCount === count) return;\n        this.notificationCount = count;\n        this.updateFavicon();\n    }\n\n    public setErrorStatus(errorDidOccur: boolean): void {\n        if (this.errorDidOccur === errorDidOccur) return;\n        this.errorDidOccur = errorDidOccur;\n        this.updateFavicon();\n    }\n\n    /**\n     * Whether we can call checkForUpdate on this platform build\n     */\n    public async canSelfUpdate(): Promise<boolean> {\n        return false;\n    }\n\n    public startUpdateCheck(): void {\n        hideUpdateToast();\n        localStorage.removeItem(UPDATE_DEFER_KEY);\n        dis.dispatch<CheckUpdatesPayload>({\n            action: Action.CheckUpdates,\n            status: UpdateCheckStatus.Checking,\n        });\n    }\n\n    /**\n     * Update the currently running app to the latest available version\n     * and replace this instance of the app with the new version.\n     */\n    public installUpdate(): void {}\n\n    /**\n     * Check if the version update has been deferred and that deferment is still in effect\n     * @param newVersion the version string to check\n     */\n    protected shouldShowUpdate(newVersion: string): boolean {\n        // If the user registered on this client in the last 24 hours then do not show them the update toast\n        if (MatrixClientPeg.userRegisteredWithinLastHours(24)) return false;\n\n        try {\n            const [version, deferUntil] = JSON.parse(localStorage.getItem(UPDATE_DEFER_KEY)!);\n            return newVersion !== version || Date.now() > deferUntil;\n        } catch {\n            return true;\n        }\n    }\n\n    /**\n     * Ignore the pending update and don't prompt about this version\n     * until the next morning (8am).\n     */\n    public deferUpdate(newVersion: string): void {\n        const date = new Date(Date.now() + 24 * 60 * 60 * 1000);\n        date.setHours(8, 0, 0, 0); // set to next 8am\n        localStorage.setItem(UPDATE_DEFER_KEY, JSON.stringify([newVersion, date.getTime()]));\n        hideUpdateToast();\n    }\n\n    /**\n     * Return true if platform supports multi-language\n     * spell-checking, otherwise false.\n     */\n    public supportsSpellCheckSettings(): boolean {\n        return false;\n    }\n\n    /**\n     * Returns true if platform allows overriding native context menus\n     */\n    public allowOverridingNativeContextMenus(): boolean {\n        return false;\n    }\n\n    /**\n     * Returns true if the platform supports displaying\n     * notifications, otherwise false.\n     * @returns {boolean} whether the platform supports displaying notifications\n     */\n    public supportsNotifications(): boolean {\n        return false;\n    }\n\n    /**\n     * Returns true if the application currently has permission\n     * to display notifications. Otherwise false.\n     * @returns {boolean} whether the application has permission to display notifications\n     */\n    public maySendNotifications(): boolean {\n        return false;\n    }\n\n    /**\n     * Requests permission to send notifications. Returns\n     * a promise that is resolved when the user has responded\n     * to the request. The promise has a single string argument\n     * that is 'granted' if the user allowed the request or\n     * 'denied' otherwise.\n     */\n    public abstract requestNotificationPermission(): Promise<string>;\n\n    public displayNotification(\n        title: string,\n        msg: string,\n        avatarUrl: string | null,\n        room: Room,\n        ev?: MatrixEvent,\n    ): Notification {\n        const notifBody: NotificationOptions = {\n            body: msg,\n            silent: true, // we play our own sounds\n        };\n        if (avatarUrl) notifBody[\"icon\"] = avatarUrl;\n        const notification = new window.Notification(title, notifBody);\n\n        notification.onclick = () => {\n            const payload: ViewRoomPayload = {\n                action: Action.ViewRoom,\n                room_id: room.roomId,\n                metricsTrigger: \"Notification\",\n            };\n\n            if (ev?.getThread()) {\n                payload.event_id = ev.getId();\n            }\n\n            dis.dispatch(payload);\n            window.focus();\n        };\n\n        const closeHandler = (): void => notification.close();\n\n        // Clear a notification from a redacted event.\n        if (ev) {\n            ev.once(MatrixEventEvent.BeforeRedaction, closeHandler);\n            notification.onclose = () => {\n                ev.off(MatrixEventEvent.BeforeRedaction, closeHandler);\n            };\n        }\n\n        return notification;\n    }\n\n    public loudNotification(ev: MatrixEvent, room: Room): void {}\n\n    public clearNotification(notif: Notification): void {\n        // Some browsers don't support this, e.g Safari on iOS\n        // https://developer.mozilla.org/en-US/docs/Web/API/Notification/close\n        if (notif.close) {\n            notif.close();\n        }\n    }\n\n    /**\n     * Returns true if the platform requires URL previews in tooltips, otherwise false.\n     * @returns {boolean} whether the platform requires URL previews in tooltips\n     */\n    public needsUrlTooltips(): boolean {\n        return false;\n    }\n\n    /**\n     * Returns a promise that resolves to a string representing the current version of the application.\n     */\n    public abstract getAppVersion(): Promise<string>;\n\n    /**\n     * Restarts the application, without necessarily reloading\n     * any application code\n     */\n    public abstract reload(): void;\n\n    public supportsSetting(settingName?: string): boolean {\n        return false;\n    }\n\n    public async getSettingValue(settingName: string): Promise<any> {\n        return undefined;\n    }\n\n    public setSettingValue(settingName: string, value: any): Promise<void> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Get our platform specific EventIndexManager.\n     *\n     * @return {BaseEventIndexManager} The EventIndex manager for our platform,\n     * can be null if the platform doesn't support event indexing.\n     */\n    public getEventIndexingManager(): BaseEventIndexManager | null {\n        return null;\n    }\n\n    public setLanguage(preferredLangs: string[]): void {}\n\n    public setSpellCheckEnabled(enabled: boolean): void {}\n\n    public async getSpellCheckEnabled(): Promise<boolean> {\n        return false;\n    }\n\n    public setSpellCheckLanguages(preferredLangs: string[]): void {}\n\n    public getSpellCheckLanguages(): Promise<string[]> | null {\n        return null;\n    }\n\n    public async getDesktopCapturerSources(options: GetSourcesOptions): Promise<Array<DesktopCapturerSource>> {\n        return [];\n    }\n\n    public supportsDesktopCapturer(): boolean {\n        return false;\n    }\n\n    public supportsJitsiScreensharing(): boolean {\n        return true;\n    }\n\n    public overrideBrowserShortcuts(): boolean {\n        return false;\n    }\n\n    public navigateForwardBack(back: boolean): void {}\n\n    public getAvailableSpellCheckLanguages(): Promise<string[]> | null {\n        return null;\n    }\n\n    /**\n     * The URL to return to after a successful SSO authentication\n     * @param fragmentAfterLogin optional fragment for specific view to return to\n     */\n    public getSSOCallbackUrl(fragmentAfterLogin = \"\"): URL {\n        const url = new URL(window.location.href);\n        url.hash = fragmentAfterLogin;\n        return url;\n    }\n\n    /**\n     * Begin Single Sign On flows.\n     * @param {MatrixClient} mxClient the matrix client using which we should start the flow\n     * @param {\"sso\"|\"cas\"} loginType the type of SSO it is, CAS/SSO.\n     * @param {string} fragmentAfterLogin the hash to pass to the app during sso callback.\n     * @param {SSOAction} action the SSO flow to indicate to the IdP, optional.\n     * @param {string} idpId The ID of the Identity Provider being targeted, optional.\n     */\n    public startSingleSignOn(\n        mxClient: MatrixClient,\n        loginType: \"sso\" | \"cas\",\n        fragmentAfterLogin?: string,\n        idpId?: string,\n        action?: SSOAction,\n    ): void {\n        // persist hs url and is url for when the user is returned to the app with the login token\n        localStorage.setItem(SSO_HOMESERVER_URL_KEY, mxClient.getHomeserverUrl());\n        if (mxClient.getIdentityServerUrl()) {\n            localStorage.setItem(SSO_ID_SERVER_URL_KEY, mxClient.getIdentityServerUrl()!);\n        }\n        if (idpId) {\n            localStorage.setItem(SSO_IDP_ID_KEY, idpId);\n        }\n        const callbackUrl = this.getSSOCallbackUrl(fragmentAfterLogin);\n        window.location.href = mxClient.getSsoLoginUrl(callbackUrl.toString(), loginType, idpId, action); // redirect to SSO\n    }\n\n    /**\n     * Get a previously stored pickle key.  The pickle key is used for\n     * encrypting libolm objects and react-sdk-crypto data.\n     * @param {string} userId the user ID for the user that the pickle key is for.\n     * @param {string} deviceId the device ID that the pickle key is for.\n     * @returns {string|null} the previously stored pickle key, or null if no\n     *     pickle key has been stored.\n     */\n    public async getPickleKey(userId: string, deviceId: string): Promise<string | null> {\n        let data: { encrypted?: BufferSource; iv?: BufferSource; cryptoKey?: CryptoKey } | undefined;\n        try {\n            data = await idbLoad(\"pickleKey\", [userId, deviceId]);\n        } catch (e) {\n            logger.error(\"idbLoad for pickleKey failed\", e);\n        }\n\n        return (await buildAndEncodePickleKey(data, userId, deviceId)) ?? null;\n    }\n\n    /**\n     * Create and store a pickle key for encrypting libolm objects.\n     * @param {string} userId the user ID for the user that the pickle key is for.\n     * @param {string} deviceId the device ID that the pickle key is for.\n     * @returns {string|null} the pickle key, or null if the platform does not\n     *     support storing pickle keys.\n     */\n    public async createPickleKey(userId: string, deviceId: string): Promise<string | null> {\n        const randomArray = new Uint8Array(32);\n        crypto.getRandomValues(randomArray);\n        const data = await encryptPickleKey(randomArray, userId, deviceId);\n        if (data === undefined) {\n            // no crypto support\n            return null;\n        }\n\n        try {\n            await idbSave(\"pickleKey\", [userId, deviceId], data);\n        } catch {\n            return null;\n        }\n        return encodeUnpaddedBase64(randomArray);\n    }\n\n    /**\n     * Delete a previously stored pickle key from storage.\n     * @param {string} userId the user ID for the user that the pickle key is for.\n     * @param {string} deviceId the device ID that the pickle key is for.\n     */\n    public async destroyPickleKey(userId: string, deviceId: string): Promise<void> {\n        try {\n            await idbDelete(\"pickleKey\", [userId, deviceId]);\n        } catch (e) {\n            logger.error(\"idbDelete failed in destroyPickleKey\", e);\n        }\n    }\n\n    /**\n     * Clear app storage, called when logging out to perform data clean up.\n     */\n    public async clearStorage(): Promise<void> {\n        window.sessionStorage.clear();\n        window.localStorage.clear();\n    }\n\n    /**\n     * Base URL to use when generating external links for this client, for platforms e.g. Desktop this will be a different instance\n     */\n    public get baseUrl(): string {\n        return window.location.origin + window.location.pathname;\n    }\n\n    /**\n     * Fallback Client URI to use for OIDC client registration for if one is not specified in config.json\n     */\n    public get defaultOidcClientUri(): string {\n        return window.location.origin;\n    }\n\n    /**\n     * Metadata to use for dynamic OIDC client registrations\n     */\n    public async getOidcClientMetadata(): Promise<OidcRegistrationClientMetadata> {\n        const config = SdkConfig.get();\n        return {\n            clientName: config.brand,\n            clientUri: config.oidc_metadata?.client_uri ?? this.defaultOidcClientUri,\n            redirectUris: [this.getOidcCallbackUrl().href],\n            logoUri: config.oidc_metadata?.logo_uri ?? new URL(\"vector-icons/1024.png\", this.baseUrl).href,\n            applicationType: \"web\",\n            contacts: config.oidc_metadata?.contacts,\n            tosUri: config.oidc_metadata?.tos_uri ?? config.terms_and_conditions_links?.[0]?.url,\n            policyUri: config.oidc_metadata?.policy_uri ?? config.privacy_policy_url,\n        };\n    }\n\n    /**\n     * Suffix to append to the `state` parameter of OIDC /auth calls. Will be round-tripped to the callback URI.\n     * Currently only required for ElectronPlatform for passing element-desktop-ssoid.\n     */\n    public getOidcClientState(): string {\n        return \"\";\n    }\n\n    /**\n     * The URL to return to after a successful OIDC authentication\n     */\n    public getOidcCallbackUrl(): URL {\n        const url = new URL(window.location.href);\n        // The redirect URL has to exactly match that registered at the OIDC server, so\n        // ensure that the fragment part of the URL is empty.\n        url.hash = \"\";\n        // Set no_universal_links=true to prevent the callback being handled by Element X installed on macOS Apple Silicon\n        url.searchParams.set(\"no_universal_links\", \"true\");\n        return url;\n    }\n\n    /**\n     * Delay creating the `Favicon` instance until first use (on the first notification) as\n     * it uses canvas, which can trigger a permission prompt in Firefox's resist fingerprinting mode.\n     * See https://github.com/element-hq/element-web/issues/9605.\n     */\n    public get favicon(): Favicon {\n        if (this._favicon) {\n            return this._favicon;\n        }\n        this._favicon = new Favicon();\n        return this._favicon;\n    }\n\n    private updateFavicon(): void {\n        const notif: string | number = this.notificationCount;\n\n        if (this.errorDidOccur) {\n            this.favicon.badge(notif || \"×\", { bgColor: \"#f00\" });\n        }\n        this.favicon.badge(notif);\n    }\n\n    /**\n     * Begin update polling, if applicable\n     */\n    public startUpdater(): void {}\n\n    /**\n     * Checks if the current session is lock-free, i.e., no other instance is holding the session lock.\n     * Platforms that support session locking should override this method.\n     * @returns {boolean} True if the session is lock-free, false otherwise.\n     */\n    public abstract checkSessionLockFree(): boolean;\n    /**\n     * Attempts to acquire a session lock for this instance.\n     * If another instance is detected, calls the provided callback.\n     * Platforms that support session locking should override this method.\n     * @param _onNewInstance Callback to invoke if a new instance is detected.\n     * @returns {Promise<boolean>} True if the lock was acquired, false otherwise.\n     */\n    public abstract getSessionLock(_onNewInstance: () => Promise<void>): Promise<boolean>;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\nCopyright 2017 Vector Creations Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { _t, getUserLanguage } from \"./languageHandler\";\nimport { getUserTimezone } from \"./TimezoneHandler\";\n\nexport { formatSeconds } from \"@element-hq/web-shared-components\";\n\nexport const MINUTE_MS = 60000;\nexport const HOUR_MS = MINUTE_MS * 60;\nexport const DAY_MS = HOUR_MS * 24;\n\n/**\n * Returns array of 7 weekday names, from Sunday to Saturday, internationalised to the user's language.\n * @param weekday - format desired \"short\" | \"long\" | \"narrow\"\n */\nexport function getDaysArray(weekday: Intl.DateTimeFormatOptions[\"weekday\"] = \"short\"): string[] {\n    const sunday = 1672574400000; // 2023-01-01 12:00 UTC\n    const { format } = new Intl.DateTimeFormat(getUserLanguage(), { weekday, timeZone: \"UTC\" });\n    return [...Array(7).keys()].map((day) => format(sunday + day * DAY_MS));\n}\n\n/**\n * Returns array of 12 month names, from January to December, internationalised to the user's language.\n * @param month - format desired \"numeric\" | \"2-digit\" | \"long\" | \"short\" | \"narrow\"\n */\nexport function getMonthsArray(month: Intl.DateTimeFormatOptions[\"month\"] = \"short\"): string[] {\n    const { format } = new Intl.DateTimeFormat(getUserLanguage(), { month, timeZone: \"UTC\" });\n    return [...Array(12).keys()].map((m) => format(Date.UTC(2021, m)));\n}\n\n// XXX: Ideally we could just specify `hour12: boolean` but it has issues on Chrome in the `en` locale\n// https://support.google.com/chrome/thread/29828561?hl=en\nexport function getTwelveHourOptions(showTwelveHour: boolean): Intl.DateTimeFormatOptions {\n    return {\n        hourCycle: showTwelveHour ? \"h12\" : \"h23\",\n    };\n}\n\n/**\n * Formats a given date to a date & time string.\n *\n * The output format depends on how far away the given date is from now.\n * Will use the browser's default time zone.\n * If the date is today it will return a time string excluding seconds. See {@formatTime}.\n * If the date is within the last 6 days it will return the name of the weekday along with the time string excluding seconds.\n * If the date is within the same year then it will return the weekday, month and day of the month along with the time string excluding seconds.\n * Otherwise, it will return a string representing the full date & time in a human friendly manner. See {@formatFullDate}.\n * @param date - date object to format\n * @param showTwelveHour - whether to use 12-hour rather than 24-hour time. Defaults to `false` (24 hour mode).\n *        Overrides the default from the locale, whether `true` or `false`.\n * @param locale - the locale string to use, in BCP 47 format, defaulting to user's selected application locale\n */\nexport function formatDate(date: Date, showTwelveHour = false, locale?: string): string {\n    const _locale = locale ?? getUserLanguage();\n    const now = new Date();\n    if (date.toDateString() === now.toDateString()) {\n        return formatTime(date, showTwelveHour, _locale);\n    } else if (now.getTime() - date.getTime() < 6 * DAY_MS) {\n        // Time is within the last 6 days (or in the future)\n        return new Intl.DateTimeFormat(_locale, {\n            ...getTwelveHourOptions(showTwelveHour),\n            weekday: \"short\",\n            hour: \"numeric\",\n            minute: \"2-digit\",\n            timeZone: getUserTimezone(),\n        }).format(date);\n    } else if (now.getFullYear() === date.getFullYear()) {\n        return new Intl.DateTimeFormat(_locale, {\n            ...getTwelveHourOptions(showTwelveHour),\n            weekday: \"short\",\n            month: \"short\",\n            day: \"numeric\",\n            hour: \"numeric\",\n            minute: \"2-digit\",\n            timeZone: getUserTimezone(),\n        }).format(date);\n    }\n    return formatFullDate(date, showTwelveHour, false, _locale);\n}\n\n/**\n * Formats a given date to a human-friendly string with short weekday.\n * Will use the browser's default time zone.\n * @example \"Thu, 17 Nov 2022\" in en-GB locale\n * @param date - date object to format\n * @param locale - the locale string to use, in BCP 47 format, defaulting to user's selected application locale\n */\nexport function formatFullDateNoTime(date: Date, locale?: string): string {\n    return new Intl.DateTimeFormat(locale ?? getUserLanguage(), {\n        weekday: \"short\",\n        month: \"short\",\n        day: \"numeric\",\n        year: \"numeric\",\n        timeZone: getUserTimezone(),\n    }).format(date);\n}\n\n/**\n * Formats a given date to a date & time string, optionally including seconds.\n * Will use the browser's default time zone.\n * @example \"Thu, 17 Nov 2022, 4:58:32 pm\" in en-GB locale with showTwelveHour=true and showSeconds=true\n * @param date - date object to format\n * @param showTwelveHour - whether to use 12-hour rather than 24-hour time. Defaults to `false` (24 hour mode).\n *        Overrides the default from the locale, whether `true` or `false`.\n * @param showSeconds - whether to include seconds in the time portion of the string\n * @param locale - the locale string to use, in BCP 47 format, defaulting to user's selected application locale\n */\nexport function formatFullDate(date: Date, showTwelveHour = false, showSeconds = true, locale?: string): string {\n    return new Intl.DateTimeFormat(locale ?? getUserLanguage(), {\n        ...getTwelveHourOptions(showTwelveHour),\n        weekday: \"short\",\n        month: \"short\",\n        day: \"numeric\",\n        year: \"numeric\",\n        hour: \"numeric\",\n        minute: \"2-digit\",\n        second: showSeconds ? \"2-digit\" : undefined,\n        timeZone: getUserTimezone(),\n    }).format(date);\n}\n\n/**\n * Formats dates to be compatible with attributes of a `<input type=\"date\">`. Dates\n * should be formatted like \"2020-06-23\" (formatted according to ISO8601).\n *\n * @param date The date to format.\n * @returns The date string in ISO8601 format ready to be used with an `<input>`\n */\nexport function formatDateForInput(date: Date): string {\n    const year = `${date.getFullYear()}`.padStart(4, \"0\");\n    const month = `${date.getMonth() + 1}`.padStart(2, \"0\");\n    const day = `${date.getDate()}`.padStart(2, \"0\");\n    return `${year}-${month}-${day}`;\n}\n\n/**\n * Formats a given date to a time string including seconds.\n * Will use the browser's default time zone.\n * @example \"4:58:32 PM\" in en-GB locale with showTwelveHour=true\n * @example \"16:58:32\" in en-GB locale with showTwelveHour=false\n * @param date - date object to format\n * @param showTwelveHour - whether to use 12-hour rather than 24-hour time. Defaults to `false` (24 hour mode).\n *        Overrides the default from the locale, whether `true` or `false`.\n * @param locale - the locale string to use, in BCP 47 format, defaulting to user's selected application locale\n */\nexport function formatFullTime(date: Date, showTwelveHour = false, locale?: string): string {\n    return new Intl.DateTimeFormat(locale ?? getUserLanguage(), {\n        ...getTwelveHourOptions(showTwelveHour),\n        hour: \"numeric\",\n        minute: \"2-digit\",\n        second: \"2-digit\",\n        timeZone: getUserTimezone(),\n    }).format(date);\n}\n\n/**\n * Formats a given date to a time string excluding seconds.\n * Will use the browser's default time zone.\n * @example \"4:58 PM\" in en-GB locale with showTwelveHour=true\n * @example \"16:58\" in en-GB locale with showTwelveHour=false\n * @param date - date object to format\n * @param showTwelveHour - whether to use 12-hour rather than 24-hour time. Defaults to `false` (24 hour mode).\n *        Overrides the default from the locale, whether `true` or `false`.\n * @param locale - the locale string to use, in BCP 47 format, defaulting to user's selected application locale\n */\nexport function formatTime(date: Date, showTwelveHour = false, locale?: string): string {\n    return new Intl.DateTimeFormat(locale ?? getUserLanguage(), {\n        ...getTwelveHourOptions(showTwelveHour),\n        hour: \"numeric\",\n        minute: \"2-digit\",\n        timeZone: getUserTimezone(),\n    }).format(date);\n}\n\nexport function formatTimeLeft(inSeconds: number): string {\n    const hours = Math.floor(inSeconds / (60 * 60)).toFixed(0);\n    const minutes = Math.floor((inSeconds % (60 * 60)) / 60).toFixed(0);\n    const seconds = Math.floor((inSeconds % (60 * 60)) % 60).toFixed(0);\n\n    if (hours !== \"0\") {\n        return _t(\"time|hours_minutes_seconds_left\", {\n            hours,\n            minutes,\n            seconds,\n        });\n    }\n\n    if (minutes !== \"0\") {\n        return _t(\"time|minutes_seconds_left\", {\n            minutes,\n            seconds,\n        });\n    }\n\n    return _t(\"time|seconds_left\", {\n        seconds,\n    });\n}\n\nfunction withinPast24Hours(prevDate: Date, nextDate: Date): boolean {\n    return Math.abs(prevDate.getTime() - nextDate.getTime()) <= DAY_MS;\n}\n\nfunction withinCurrentDay(prevDate: Date, nextDate: Date): boolean {\n    return withinPast24Hours(prevDate, nextDate) && prevDate.getDay() === nextDate.getDay();\n}\n\nfunction withinCurrentYear(prevDate: Date, nextDate: Date): boolean {\n    return prevDate.getFullYear() === nextDate.getFullYear();\n}\n\nexport function wantsDateSeparator(prevEventDate: Date | undefined, nextEventDate: Date | undefined): boolean {\n    if (!nextEventDate || !prevEventDate) {\n        return false;\n    }\n    // Return early for events that are > 24h apart\n    if (!withinPast24Hours(prevEventDate, nextEventDate)) {\n        return true;\n    }\n\n    // Compare weekdays\n    return prevEventDate.getDay() !== nextEventDate.getDay();\n}\n\nexport function formatFullDateNoDay(date: Date): string {\n    const locale = getUserLanguage();\n    return _t(\"time|date_at_time\", {\n        date: date.toLocaleDateString(locale).replace(/\\//g, \"-\"),\n        time: date.toLocaleTimeString(locale).replace(/:/g, \"-\"),\n    });\n}\n\n/**\n * Returns an ISO date string without textual description of the date (ie: no \"Wednesday\" or similar)\n * @param date The date to format.\n * @returns The date string in ISO format.\n */\nexport function formatFullDateNoDayISO(date: Date): string {\n    return date.toISOString();\n}\n\n/**\n * Formats a given date to a string.\n * Will use the browser's default time zone.\n * @example 17/11/2022 in en-GB locale\n * @param date - date object to format\n * @param locale - the locale string to use, in BCP 47 format, defaulting to user's selected application locale\n */\nexport function formatFullDateNoDayNoTime(date: Date, locale?: string): string {\n    return new Intl.DateTimeFormat(locale ?? getUserLanguage(), {\n        year: \"numeric\",\n        month: \"numeric\",\n        day: \"numeric\",\n        timeZone: getUserTimezone(),\n    }).format(date);\n}\n\nexport function formatRelativeTime(date: Date, showTwelveHour = false): string {\n    const now = new Date();\n    if (withinCurrentDay(date, now)) {\n        return formatTime(date, showTwelveHour);\n    } else {\n        const months = getMonthsArray();\n        let relativeDate = `${months[date.getMonth()]} ${date.getDate()}`;\n\n        if (!withinCurrentYear(date, now)) {\n            relativeDate += `, ${date.getFullYear()}`;\n        }\n        return relativeDate;\n    }\n}\n\n/**\n * Formats duration in ms to human-readable string\n * Returns value in the biggest possible unit (day, hour, min, second)\n * Rounds values up until unit threshold\n * i.e. 23:13:57 -> 23h, 24:13:57 -> 1d, 44:56:56 -> 2d\n */\nexport function formatDuration(durationMs: number): string {\n    if (durationMs >= DAY_MS) {\n        return _t(\"time|short_days\", { value: Math.round(durationMs / DAY_MS) });\n    }\n    if (durationMs >= HOUR_MS) {\n        return _t(\"time|short_hours\", { value: Math.round(durationMs / HOUR_MS) });\n    }\n    if (durationMs >= MINUTE_MS) {\n        return _t(\"time|short_minutes\", { value: Math.round(durationMs / MINUTE_MS) });\n    }\n    return _t(\"time|short_seconds\", { value: Math.round(durationMs / 1000) });\n}\n\n/**\n * Formats duration in ms to human-readable string\n * Returns precise value down to the nearest second\n * i.e. 23:13:57 -> 23h 13m 57s, 44:56:56 -> 1d 20h 56m 56s\n */\nexport function formatPreciseDuration(durationMs: number): string {\n    const days = Math.floor(durationMs / DAY_MS);\n    const hours = Math.floor((durationMs % DAY_MS) / HOUR_MS);\n    const minutes = Math.floor((durationMs % HOUR_MS) / MINUTE_MS);\n    const seconds = Math.floor((durationMs % MINUTE_MS) / 1000);\n\n    if (days > 0) {\n        return _t(\"time|short_days_hours_minutes_seconds\", { days, hours, minutes, seconds });\n    }\n    if (hours > 0) {\n        return _t(\"time|short_hours_minutes_seconds\", { hours, minutes, seconds });\n    }\n    if (minutes > 0) {\n        return _t(\"time|short_minutes_seconds\", { minutes, seconds });\n    }\n    return _t(\"time|short_seconds\", { value: seconds });\n}\n\n/**\n * Formats a timestamp to a short date\n * Similar to {@formatFullDateNoDayNoTime} but with 2-digit on day, month, year.\n * @example 25/12/22 in en-GB locale\n * @param timestamp - epoch timestamp\n * @param locale - the locale string to use, in BCP 47 format, defaulting to user's selected application locale\n * @returns {string} formattedDate\n */\nexport const formatLocalDateShort = (timestamp: number, locale?: string): string =>\n    new Intl.DateTimeFormat(locale ?? getUserLanguage(), {\n        day: \"2-digit\",\n        month: \"2-digit\",\n        year: \"2-digit\",\n        timeZone: getUserTimezone(),\n    }).format(timestamp);\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type TimelineRenderingType } from \"./contexts/RoomContext\";\n\nexport const editorRoomKey = (roomId: string, context: TimelineRenderingType): string =>\n    `mx_edit_room_${roomId}_${context}`;\nexport const editorStateKey = (eventId: string): string => `mx_edit_state_${eventId}`;\n","/*\nCopyright 2024, 2025 New Vector Ltd.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2017, 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type Key, type LegacyRef, type ReactNode } from \"react\";\nimport sanitizeHtml, { type IOptions } from \"sanitize-html\";\nimport classNames from \"classnames\";\nimport katex from \"katex\";\nimport { decode } from \"html-entities\";\nimport { type IContent } from \"matrix-js-sdk/src/matrix\";\nimport escapeHtml from \"escape-html\";\nimport { getEmojiFromUnicode } from \"@matrix-org/emojibase-bindings\";\n\nimport SettingsStore from \"./settings/SettingsStore\";\nimport { stripHTMLReply, stripPlainReply } from \"./utils/Reply\";\nimport { PERMITTED_URL_SCHEMES } from \"./utils/UrlUtils\";\nimport { linkifyHtml, sanitizeHtmlParams, transformTags } from \"./Linkify\";\nimport { graphemeSegmenter } from \"./utils/strings\";\n\nexport { Linkify, linkifyAndSanitizeHtml } from \"./Linkify\";\n\n// Anything outside the basic multilingual plane will be a surrogate pair\nconst SURROGATE_PAIR_PATTERN = /([\\ud800-\\udbff])([\\udc00-\\udfff])/;\n// And there a bunch more symbol characters that emojibase has within the\n// BMP, so this includes the ranges from 'letterlike symbols' to\n// 'miscellaneous symbols and arrows' which should catch all of them\n// (with plenty of false positives, but that's OK)\nconst SYMBOL_PATTERN = /([\\u2100-\\u2bff])/;\n\n// Regex pattern for non-emoji characters that can appear in an \"all-emoji\" message\n// (Zero-Width Space, other whitespace)\nconst EMOJI_SEPARATOR_REGEX = /[\\u200B\\s]/g;\n\n// Regex for emoji. This includes any RGI_Emoji sequence followed by an optional\n// emoji presentation VS (U+FE0F), but not those sequences that are followed by\n// a text presentation VS (U+FE0E). We also count lone regional indicators\n// (U+1F1E6-U+1F1FF). Technically this regex produces false negatives for emoji\n// followed by U+FE0E when the emoji doesn't have a text variant, but in\n// practice this doesn't matter.\nexport const EMOJI_REGEX = (() => {\n    try {\n        // Per our support policy, v mode is available to us, but we still don't\n        // want the app to completely crash on older platforms. We use the\n        // constructor here to avoid a syntax error on such platforms.\n        return new RegExp(\"\\\\p{RGI_Emoji}(?!\\\\uFE0E)(?:(?<!\\\\uFE0F)\\\\uFE0F)?|[\\\\u{1f1e6}-\\\\u{1f1ff}]\", \"v\");\n    } catch {\n        // v mode not supported; fall back to matching nothing\n        return /(?!)/;\n    }\n})();\n\nconst BIGEMOJI_REGEX = (() => {\n    try {\n        return new RegExp(`^(${EMOJI_REGEX.source})+$`, \"iv\");\n    } catch {\n        // Fall back, just like for EMOJI_REGEX\n        return /(?!)/;\n    }\n})();\n\n/*\n * Return true if the given string contains emoji\n * Uses a much, much simpler regex than emojibase's so will give false\n * positives, but useful for fast-path testing strings to see if they\n * need emojification.\n */\nfunction mightContainEmoji(str?: string): boolean {\n    return !!str && (SURROGATE_PAIR_PATTERN.test(str) || SYMBOL_PATTERN.test(str));\n}\n\n/**\n * Returns the shortcode for an emoji character.\n *\n * @param {String} char The emoji character\n * @return {String} The shortcode (such as :thumbup:)\n */\nexport function unicodeToShortcode(char: string): string {\n    const shortcodes = getEmojiFromUnicode(char)?.shortcodes;\n    return shortcodes?.length ? `:${shortcodes[0]}:` : \"\";\n}\n\n/*\n * Given an untrusted HTML string, return a React node with an sanitized version\n * of that HTML.\n */\nexport function sanitizedHtmlNode(insaneHtml: string): ReactNode {\n    const saneHtml = sanitizeHtml(insaneHtml, sanitizeHtmlParams);\n\n    return <div dangerouslySetInnerHTML={{ __html: saneHtml }} dir=\"auto\" />;\n}\n\nexport function getHtmlText(insaneHtml: string): string {\n    return sanitizeHtml(insaneHtml, {\n        allowedTags: [],\n        allowedAttributes: {},\n        selfClosing: [],\n        allowedSchemes: [],\n        disallowedTagsMode: \"discard\",\n    });\n}\n\n/**\n * Tests if a URL from an untrusted source may be safely put into the DOM\n * The biggest threat here is javascript: URIs.\n * Note that the HTML sanitiser library has its own internal logic for\n * doing this, to which we pass the same list of schemes. This is used in\n * other places we need to sanitise URLs.\n * @return true if permitted, otherwise false\n */\nexport function isUrlPermitted(inputUrl: string): boolean {\n    try {\n        // URL parser protocol includes the trailing colon\n        return PERMITTED_URL_SCHEMES.includes(new URL(inputUrl).protocol.slice(0, -1));\n    } catch {\n        return false;\n    }\n}\n\n// this is the same as the above except with less rewriting\nconst composerSanitizeHtmlParams: IOptions = {\n    ...sanitizeHtmlParams,\n    transformTags: {\n        \"code\": transformTags[\"code\"],\n        \"*\": transformTags[\"*\"],\n    },\n};\n\n// reduced set of allowed tags to avoid turning topics into Myspace\nconst topicSanitizeHtmlParams: IOptions = {\n    ...sanitizeHtmlParams,\n    allowedTags: [\n        \"font\", // custom to matrix for IRC-style font coloring\n        \"del\", // for markdown\n        \"s\",\n        \"a\",\n        \"sup\",\n        \"sub\",\n        \"b\",\n        \"i\",\n        \"u\",\n        \"strong\",\n        \"em\",\n        \"strike\",\n        \"br\",\n        \"div\",\n        \"span\",\n    ],\n};\n\nabstract class BaseHighlighter<T extends React.ReactNode> {\n    public constructor(\n        public highlightClass: string,\n        public highlightLink?: string,\n    ) {}\n\n    /**\n     * Apply the highlights to a section of text\n     *\n     * @param {string} safeSnippet The snippet of text to apply the highlights\n     *     to. This input must be sanitised as it will be treated as HTML.\n     * @param {string[]} safeHighlights A list of substrings to highlight,\n     *     sorted by descending length.\n     *\n     * returns a list of results (strings for HtmlHighligher, react nodes for\n     * TextHighlighter).\n     */\n    public applyHighlights(safeSnippet: string, safeHighlights: string[]): T[] {\n        let lastOffset = 0;\n        let offset: number;\n        let nodes: T[] = [];\n\n        const safeHighlight = safeHighlights[0];\n        while ((offset = safeSnippet.toLowerCase().indexOf(safeHighlight.toLowerCase(), lastOffset)) >= 0) {\n            // handle preamble\n            if (offset > lastOffset) {\n                const subSnippet = safeSnippet.substring(lastOffset, offset);\n                nodes = nodes.concat(this.applySubHighlights(subSnippet, safeHighlights));\n            }\n\n            // do highlight. use the original string rather than safeHighlight\n            // to preserve the original casing.\n            const endOffset = offset + safeHighlight.length;\n            nodes.push(this.processSnippet(safeSnippet.substring(offset, endOffset), true));\n\n            lastOffset = endOffset;\n        }\n\n        // handle postamble\n        if (lastOffset !== safeSnippet.length) {\n            const subSnippet = safeSnippet.substring(lastOffset, undefined);\n            nodes = nodes.concat(this.applySubHighlights(subSnippet, safeHighlights));\n        }\n        return nodes;\n    }\n\n    private applySubHighlights(safeSnippet: string, safeHighlights: string[]): T[] {\n        if (safeHighlights[1]) {\n            // recurse into this range to check for the next set of highlight matches\n            return this.applyHighlights(safeSnippet, safeHighlights.slice(1));\n        } else {\n            // no more highlights to be found, just return the unhighlighted string\n            return [this.processSnippet(safeSnippet, false)];\n        }\n    }\n\n    protected abstract processSnippet(snippet: string, highlight: boolean): T;\n}\n\nclass HtmlHighlighter extends BaseHighlighter<string> {\n    /* highlight the given snippet if required\n     *\n     * snippet: content of the span; must have been sanitised\n     * highlight: true to highlight as a search match\n     *\n     * returns an HTML string\n     */\n    protected processSnippet(snippet: string, highlight: boolean): string {\n        if (!highlight) {\n            // nothing required here\n            return snippet;\n        }\n\n        let span = `<span class=\"${this.highlightClass}\">${snippet}</span>`;\n\n        if (this.highlightLink) {\n            span = `<a href=\"${encodeURI(this.highlightLink)}\">${span}</a>`;\n        }\n        return span;\n    }\n}\n\nconst emojiToHtmlSpan = (emoji: string): string =>\n    `<span class='mx_Emoji' title='${unicodeToShortcode(emoji)}'>${emoji}</span>`;\nconst emojiToJsxSpan = (emoji: string, key: Key): JSX.Element => (\n    <span key={key} className=\"mx_Emoji\" title={unicodeToShortcode(emoji)}>\n        {emoji}\n    </span>\n);\n\n/**\n * Wraps emojis in <span> to style them separately from the rest of message. Consecutive emojis (and modifiers) are wrapped\n * in the same <span>.\n * @param {string} message the text to format\n * @param {boolean} isHtmlMessage whether the message contains HTML\n * @returns if isHtmlMessage is true, returns an array of strings, otherwise return an array of React Elements for emojis\n * and plain text for everything else\n */\nexport function formatEmojis(message: string | undefined, isHtmlMessage?: false): JSX.Element[];\nexport function formatEmojis(message: string | undefined, isHtmlMessage: true): string[];\nexport function formatEmojis(message: string | undefined, isHtmlMessage?: boolean): (JSX.Element | string)[] {\n    const emojiToSpan = isHtmlMessage ? emojiToHtmlSpan : emojiToJsxSpan;\n    const result: (JSX.Element | string)[] = [];\n    if (!message) return result;\n\n    let text = \"\";\n    let key = 0;\n\n    for (const data of graphemeSegmenter.segment(message)) {\n        if (EMOJI_REGEX.test(data.segment)) {\n            if (text) {\n                result.push(text);\n                text = \"\";\n            }\n            result.push(emojiToSpan(data.segment, key));\n            key++;\n        } else {\n            text += data.segment;\n        }\n    }\n    if (text) {\n        result.push(text);\n    }\n    return result;\n}\n\ninterface EventAnalysis {\n    bodyHasEmoji: boolean;\n    isHtmlMessage: boolean;\n    strippedBody: string;\n    safeBody?: string; // safe, sanitised HTML, preferred over `strippedBody` which is fully plaintext\n    isFormattedBody: boolean;\n}\n\nexport interface EventRenderOpts {\n    highlightLink?: string;\n    disableBigEmoji?: boolean;\n    stripReplyFallback?: boolean;\n    forComposerQuote?: boolean;\n    /**\n     * Should inline media be rendered?\n     */\n    mediaIsVisible?: boolean;\n    linkify?: boolean;\n}\n\nfunction analyseEvent(content: IContent, highlights?: string[], opts: EventRenderOpts = {}): EventAnalysis {\n    let sanitizeParams = sanitizeHtmlParams;\n    if (opts.forComposerQuote) {\n        sanitizeParams = composerSanitizeHtmlParams;\n    }\n\n    if (opts.mediaIsVisible === false && sanitizeParams.transformTags?.[\"img\"]) {\n        // Prevent mutating the source of sanitizeParams.\n        sanitizeParams = {\n            ...sanitizeParams,\n            transformTags: {\n                ...sanitizeParams.transformTags,\n                img: (tagName) => {\n                    // Remove element\n                    return { tagName, attribs: {} };\n                },\n            },\n        };\n    }\n\n    if (opts.linkify) {\n        // Prevent mutating the source of sanitizeParams.\n        sanitizeParams = { ...sanitizeParams };\n        sanitizeParams.allowedClasses ??= {};\n        if (typeof sanitizeParams.allowedClasses.a === \"boolean\") {\n            // All classes are already allowed for \"a\"\n        } else {\n            sanitizeParams.allowedClasses.a ??= [];\n            sanitizeParams.allowedClasses.a.push(\"linkified\");\n        }\n    }\n\n    try {\n        const isFormattedBody =\n            content.format === \"org.matrix.custom.html\" && typeof content.formatted_body === \"string\";\n        let bodyHasEmoji = false;\n        let isHtmlMessage = false;\n\n        let safeBody: string | undefined; // safe, sanitised HTML, preferred over `strippedBody` which is fully plaintext\n\n        // sanitizeHtml can hang if an unclosed HTML tag is thrown at it\n        // A search for `<foo` will make the browser crash an alternative would be to escape HTML special characters\n        // but that would bring no additional benefit as the highlighter does not work with those special chars\n        const safeHighlights = highlights\n            ?.filter((highlight: string): boolean => !highlight.includes(\"<\"))\n            .map((highlight: string): string => sanitizeHtml(highlight, sanitizeParams));\n\n        let formattedBody = typeof content.formatted_body === \"string\" ? content.formatted_body : null;\n        const plainBody = typeof content.body === \"string\" ? content.body : \"\";\n\n        if (opts.stripReplyFallback && formattedBody) formattedBody = stripHTMLReply(formattedBody);\n        const strippedBody = opts.stripReplyFallback ? stripPlainReply(plainBody) : plainBody;\n        bodyHasEmoji = mightContainEmoji(isFormattedBody ? formattedBody! : plainBody);\n\n        const highlighter = safeHighlights?.length\n            ? new HtmlHighlighter(\"mx_EventTile_searchHighlight\", opts.highlightLink)\n            : null;\n\n        if (highlighter) {\n            // XXX: We sanitize the HTML whilst also highlighting its text nodes, to avoid accidentally trying\n            // to highlight HTML tags themselves. However, this does mean that we don't highlight textnodes which\n            // are interrupted by HTML tags (not that we did before) - e.g. foo<span/>bar won't get highlighted\n            // by an attempt to search for 'foobar'.  Then again, the search query probably wouldn't work either\n            // XXX: hacky bodge to temporarily apply a textFilter to the sanitizeParams structure.\n            sanitizeParams.textFilter = function (safeText) {\n                return highlighter.applyHighlights(safeText, safeHighlights!).join(\"\");\n            };\n        }\n\n        if (isFormattedBody) {\n            let unsafeBody = formattedBody!;\n\n            if (opts.linkify) {\n                unsafeBody = linkifyHtml(unsafeBody);\n            }\n\n            safeBody = sanitizeHtml(unsafeBody, sanitizeParams);\n\n            const phtml = new DOMParser().parseFromString(safeBody, \"text/html\");\n            const isPlainText = phtml.body.innerHTML === phtml.body.textContent;\n            isHtmlMessage = !isPlainText;\n\n            if (isHtmlMessage && SettingsStore.getValue(\"feature_latex_maths\")) {\n                [...phtml.querySelectorAll<HTMLElement>(\"div[data-mx-maths], span[data-mx-maths]\")].forEach((e) => {\n                    e.outerHTML = katex.renderToString(decode(e.getAttribute(\"data-mx-maths\")), {\n                        throwOnError: false,\n                        displayMode: e.tagName == \"DIV\",\n                        output: \"htmlAndMathml\",\n                    });\n                });\n                safeBody = phtml.body.innerHTML;\n            }\n        } else if (opts.linkify) {\n            // If we are linkifying plain text, pass the result through sanitizeHtml so that the highlighter configured in sanitizeParams.textFilter gets applied.\n            safeBody = sanitizeHtml(linkifyHtml(escapeHtml(plainBody)), sanitizeParams);\n        } else if (highlighter) {\n            safeBody = highlighter.applyHighlights(escapeHtml(plainBody), safeHighlights!).join(\"\");\n        }\n\n        return { bodyHasEmoji, isHtmlMessage, strippedBody, safeBody, isFormattedBody };\n    } finally {\n        delete sanitizeParams.textFilter;\n    }\n}\n\ninterface BodyToNodeReturn {\n    strippedBody: string;\n    formattedBody?: string;\n    emojiBodyElements: JSX.Element[] | undefined;\n    className: string;\n}\n\nexport function bodyToNode(content: IContent, highlights?: string[], opts: EventRenderOpts = {}): BodyToNodeReturn {\n    const eventInfo = analyseEvent(content, highlights, opts);\n\n    let emojiBody = false;\n    if (!opts.disableBigEmoji && eventInfo.bodyHasEmoji) {\n        const contentBody = eventInfo.safeBody ?? eventInfo.strippedBody;\n        let contentBodyTrimmed = contentBody !== undefined ? contentBody.trim() : \"\";\n\n        // Remove zero width joiner, zero width spaces and other spaces in body\n        // text. This ensures that emojis with spaces in between or that are made\n        // up of multiple unicode characters are still counted as purely emoji\n        // messages.\n        contentBodyTrimmed = contentBodyTrimmed.replace(EMOJI_SEPARATOR_REGEX, \"\");\n\n        const match = BIGEMOJI_REGEX.exec(contentBodyTrimmed);\n        emojiBody =\n            match?.[0]?.length === contentBodyTrimmed.length &&\n            // Prevent user pills expanding for users with only emoji in\n            // their username. Permalinks (links in pills) can be any URL\n            // now, so we just check for an HTTP-looking thing.\n            (eventInfo.strippedBody === eventInfo.safeBody || // replies have the html fallbacks, account for that here\n                content.formatted_body === undefined ||\n                (!content.formatted_body.includes(\"http:\") && !content.formatted_body.includes(\"https:\")));\n    }\n\n    const className = classNames({\n        \"mx_EventTile_body\": true,\n        \"mx_EventTile_bigEmoji\": emojiBody,\n        \"markdown-body\": eventInfo.isHtmlMessage && !emojiBody,\n        // Override the global `notranslate` class set by the top-level `matrixchat` div.\n        \"translate\": true,\n    });\n\n    let formattedBody = eventInfo.safeBody;\n    let emojiBodyElements: JSX.Element[] | undefined;\n\n    if (eventInfo.bodyHasEmoji) {\n        if (eventInfo.safeBody) {\n            // This has to be done after the emojiBody check as to not break big emoji on replies\n            formattedBody = formatEmojis(eventInfo.safeBody, true).join(\"\");\n        } else {\n            emojiBodyElements = formatEmojis(eventInfo.strippedBody, false) as JSX.Element[];\n        }\n    }\n\n    return { strippedBody: eventInfo.strippedBody, formattedBody, emojiBodyElements, className };\n}\n\n/**\n * Turn a matrix event body into html\n *\n * content: 'content' of the MatrixEvent\n *\n * highlights: optional list of words to highlight, ordered by longest word first\n *\n * opts.highlightLink: optional href to add to highlighted words\n * opts.disableBigEmoji: optional argument to disable the big emoji class.\n * opts.stripReplyFallback: optional argument specifying the event is a reply and so fallback needs removing\n * opts.forComposerQuote: optional param to lessen the url rewriting done by sanitization, for quoting into composer\n * opts.ref: React ref to attach to any React components returned (not compatible with opts.returnString)\n */\nexport function bodyToHtml(content: IContent, highlights?: string[], opts: EventRenderOpts = {}): string {\n    const eventInfo = analyseEvent(content, highlights, opts);\n\n    let formattedBody = eventInfo.safeBody;\n    if (eventInfo.bodyHasEmoji && formattedBody) {\n        // This has to be done after the emojiBody check above as to not break big emoji on replies\n        formattedBody = formatEmojis(eventInfo.safeBody, true).join(\"\");\n    }\n\n    return formattedBody ?? eventInfo.strippedBody;\n}\n\n/**\n * Turn a room topic into html\n * @param topic plain text topic\n * @param htmlTopic optional html topic\n * @param ref React ref to attach to any React components returned\n * @param allowExtendedHtml whether to allow extended HTML tags such as headings and lists\n * @return The HTML-ified node.\n */\nexport function topicToHtml(\n    topic?: string,\n    htmlTopic?: string,\n    ref?: LegacyRef<HTMLSpanElement>,\n    allowExtendedHtml = false,\n): ReactNode {\n    let isFormattedTopic = !!htmlTopic;\n    let topicHasEmoji = false;\n    let safeTopic = \"\";\n\n    try {\n        topicHasEmoji = mightContainEmoji(isFormattedTopic ? htmlTopic! : topic);\n\n        if (isFormattedTopic) {\n            safeTopic = sanitizeHtml(htmlTopic!, allowExtendedHtml ? sanitizeHtmlParams : topicSanitizeHtmlParams);\n            if (topicHasEmoji) {\n                safeTopic = formatEmojis(safeTopic, true).join(\"\");\n            }\n        }\n    } catch {\n        isFormattedTopic = false; // Fall back to plain-text topic\n    }\n\n    let emojiBodyElements: JSX.Element[] | undefined;\n    if (!isFormattedTopic && topicHasEmoji) {\n        emojiBodyElements = formatEmojis(topic, false);\n    }\n\n    if (isFormattedTopic) {\n        if (!safeTopic) return null;\n        return <span ref={ref} dangerouslySetInnerHTML={{ __html: safeTopic }} dir=\"auto\" />;\n    }\n\n    if (!emojiBodyElements && !topic) return null;\n    return (\n        <span ref={ref} dir=\"auto\">\n            {emojiBodyElements || topic}\n        </span>\n    );\n}\n\n/**\n * Returns if a node is a block element or not.\n * Only takes html nodes into account that are allowed in matrix messages.\n *\n * @param {Node} node\n * @returns {bool}\n */\nexport function checkBlockNode(node: Node): boolean {\n    switch (node.nodeName) {\n        case \"H1\":\n        case \"H2\":\n        case \"H3\":\n        case \"H4\":\n        case \"H5\":\n        case \"H6\":\n        case \"PRE\":\n        case \"BLOCKQUOTE\":\n        case \"P\":\n        case \"UL\":\n        case \"OL\":\n        case \"LI\":\n        case \"HR\":\n        case \"TABLE\":\n        case \"THEAD\":\n        case \"TBODY\":\n        case \"TR\":\n        case \"TH\":\n        case \"TD\":\n            return true;\n        case \"DIV\":\n            // don't treat math nodes as block nodes for deserializing\n            return !(node as HTMLElement).hasAttribute(\"data-mx-maths\");\n        default:\n            return false;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2022 The Matrix.org Foundation C.I.C.\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type IClientWellKnown } from \"matrix-js-sdk/src/matrix\";\n\nimport { type ValidatedServerConfig } from \"./utils/ValidatedServerConfig\";\n\n// Convention decision: All config options are lower_snake_case\n// We use an isolated file for the interface so we can mess around with the eslint options.\n\n/* eslint-disable camelcase */\n/* eslint @typescript-eslint/naming-convention: [\"error\", { \"selector\": \"property\", \"format\": [\"snake_case\"] } ] */\n\n/**\n * Bug reports are enabled but must only be locally\n * downloadable.\n */\nexport const BugReportEndpointURLLocal = \"local\";\n\n// see element-web config.md for non-developer docs\nexport interface IConfigOptions {\n    // dev note: while true that this is arbitrary JSON, it's valuable to enforce that all\n    // config options are documented for \"find all usages\" sort of searching.\n    // [key: string]: any;\n\n    // Properties of this interface are roughly grouped by their subject matter, such as\n    // \"instance customisation\", \"login stuff\", \"branding\", etc. Use blank lines to denote\n    // a logical separation of properties, but keep similar ones near each other.\n\n    // Exactly one of the following must be supplied\n    default_server_config?: IClientWellKnown; // copy/paste of client well-known\n    default_server_name?: string; // domain to do well-known lookup on\n    default_hs_url?: string; // http url\n\n    default_is_url?: string; // used in combination with default_hs_url, but for the identity server\n\n    // This is intended to be overridden by app startup and not specified by the user\n    // This is also why it's allowed to have an interface that isn't snake_case\n    validated_server_config?: ValidatedServerConfig;\n\n    fallback_hs_url?: string;\n\n    disable_custom_urls?: boolean;\n    disable_guests?: boolean;\n    disable_login_language_selector?: boolean;\n    disable_3pid_login?: boolean;\n\n    brand: string;\n    branding?: {\n        welcome_background_url?: string | string[]; // chosen at random if array\n        auth_header_logo_url?: string;\n        auth_footer_links?: { text: string; url: string }[];\n    };\n\n    force_verification?: boolean; // if true, users must verify new logins\n\n    map_style_url?: string; // for location-shared maps\n\n    embedded_pages?: {\n        welcome_url?: string;\n        home_url?: string;\n        login_for_welcome?: boolean;\n    };\n\n    permalink_prefix?: string;\n\n    update_base_url?: string;\n    desktop_builds: {\n        available: boolean;\n        logo: string; // url\n        url: string; // download url\n        url_macos?: string;\n        url_win64?: string;\n        url_win64arm?: string;\n        url_linux?: string;\n    };\n    mobile_builds: {\n        ios: string | null; // download url\n        android: string | null; // download url\n        fdroid: string | null; // download url\n    };\n\n    mobile_guide_toast?: boolean;\n    mobile_guide_app_variant?: \"element\" | \"element-classic\" | \"element-pro\";\n\n    default_theme?: \"light\" | \"dark\" | string; // custom themes are strings\n    default_country_code?: string; // ISO 3166 alpha2 country code\n    default_federate?: boolean;\n    default_device_display_name?: string; // for device naming on login+registration\n\n    setting_defaults?: Record<string, any>; // <SettingName, Value>\n\n    integrations_ui_url?: string;\n    integrations_rest_url?: string;\n    integrations_widgets_urls?: string[];\n    default_widget_container_height?: number; // height in pixels\n\n    show_labs_settings: boolean;\n    features?: Record<string, boolean>; // <FeatureName, EnabledBool>\n\n    /**\n     * Bug report endpoint URL. \"local\" means the logs should not be uploaded.\n     */\n    bug_report_endpoint_url?: typeof BugReportEndpointURLLocal | string; // omission disables bug reporting\n    uisi_autorageshake_app?: string; // defaults to \"element-auto-uisi\"\n    sentry?: {\n        dsn: string;\n        environment?: string; // \"production\", etc\n    };\n\n    widget_build_url?: string; // url called to replace jitsi/call widget creation\n    widget_build_url_ignore_dm?: boolean;\n    audio_stream_url?: string;\n    jitsi?: {\n        preferred_domain: string;\n    };\n    jitsi_widget?: {\n        skip_built_in_welcome_screen?: boolean;\n    };\n    voip?: {\n        obey_asserted_identity?: boolean; // MSC3086\n    };\n    element_call: {\n        guest_spa_url?: string;\n        use_exclusively?: boolean;\n        brand?: string;\n    };\n\n    logout_redirect_url?: string;\n\n    // sso_immediate_redirect is deprecated in favour of sso_redirect_options.immediate\n    sso_immediate_redirect?: boolean;\n    sso_redirect_options?: ISsoRedirectOptions;\n\n    custom_translations_url?: string;\n\n    report_event?: {\n        admin_message_md: string; // message for how to contact the server owner when reporting an event\n    };\n\n    room_directory?: {\n        servers: string[];\n    };\n\n    posthog?: {\n        project_api_key: string;\n        api_host: string; // hostname\n    };\n    analytics_owner?: string; // defaults to `brand`\n    privacy_policy_url?: string; // location for cookie policy\n\n    enable_presence_by_hs_url?: Record<string, boolean>; // <HomeserverName, Enabled>\n\n    terms_and_conditions_links?: { url: string; text: string }[];\n    help_url: string;\n    help_encryption_url: string;\n    help_key_storage_url: string;\n\n    latex_maths_delims?: {\n        inline?: {\n            left?: string;\n            right?: string;\n            pattern?: {\n                tex?: string;\n                latex?: string;\n            };\n        };\n        display?: {\n            left?: string;\n            right?: string;\n            pattern?: {\n                tex?: string;\n                latex?: string;\n            };\n        };\n    };\n\n    sync_timeline_limit?: number;\n    dangerously_allow_unsafe_and_insecure_passwords?: boolean; // developer option\n\n    user_notice?: {\n        title: string;\n        description: string;\n        show_once?: boolean;\n    };\n\n    feedback: {\n        existing_issues_url: string;\n        new_issue_url: string;\n    };\n\n    /**\n     * Configuration for OIDC issuers where a static client_id has been issued for the app.\n     * Otherwise dynamic client registration is attempted.\n     * The issuer URL must have a trailing `/`.\n     * OPTIONAL\n     */\n    oidc_static_clients?: {\n        [issuer: string]: { client_id: string };\n    };\n\n    /**\n     * Configuration for OIDC dynamic registration where a static OIDC client is not configured.\n     */\n    oidc_metadata?: {\n        client_uri?: string;\n        logo_uri?: string;\n        tos_uri?: string;\n        policy_uri?: string;\n        contacts?: string[];\n    };\n\n    modules?: string[];\n}\n\nexport interface ISsoRedirectOptions {\n    immediate?: boolean;\n    on_welcome_page?: boolean;\n    on_login_page?: boolean;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { SERVICE_TYPES, createClient, type MatrixClient, MatrixError } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { MatrixClientPeg } from \"./MatrixClientPeg\";\nimport Modal from \"./Modal\";\nimport { _t } from \"./languageHandler\";\nimport { Service, startTermsFlow, TermsNotSignedError } from \"./Terms\";\nimport {\n    doesAccountDataHaveIdentityServer,\n    doesIdentityServerHaveTerms,\n    setToDefaultIdentityServer,\n} from \"./utils/IdentityServerUtils\";\nimport QuestionDialog from \"./components/views/dialogs/QuestionDialog\";\nimport { abbreviateUrl } from \"./utils/UrlUtils\";\n\nexport class AbortedIdentityActionError extends Error {}\n\nexport default class IdentityAuthClient {\n    private accessToken: string | null = null;\n    private tempClient?: MatrixClient;\n    private authEnabled = true;\n\n    /**\n     * Creates a new identity auth client\n     * @param {string} identityUrl The URL to contact the identity server with.\n     * When provided, this class will operate solely within memory, refusing to\n     * persist any information such as tokens. Default null (not provided).\n     */\n    public constructor(identityUrl?: string) {\n        if (identityUrl) {\n            // XXX: We shouldn't have to create a whole new MatrixClient just to\n            // do identity server auth. The functions don't take an identity URL\n            // though, and making all of them take one could lead to developer\n            // confusion about what the idBaseUrl does on a client. Therefore, we\n            // just make a new client and live with it.\n            this.tempClient = createClient({\n                baseUrl: \"\", // invalid by design\n                idBaseUrl: identityUrl,\n            });\n        }\n    }\n\n    // This client must not be used for general operations as it may not have a baseUrl or be running (tempClient).\n    private get identityClient(): MatrixClient {\n        return this.tempClient ?? this.matrixClient;\n    }\n\n    private get matrixClient(): MatrixClient {\n        return MatrixClientPeg.safeGet();\n    }\n\n    private writeToken(): void {\n        if (this.tempClient) return; // temporary client: ignore\n        if (this.accessToken) {\n            window.localStorage.setItem(\"mx_is_access_token\", this.accessToken);\n        } else {\n            window.localStorage.removeItem(\"mx_is_access_token\");\n        }\n    }\n\n    private readToken(): string | null {\n        if (this.tempClient) return null; // temporary client: ignore\n        return window.localStorage.getItem(\"mx_is_access_token\");\n    }\n\n    // Returns a promise that resolves to the access_token string from the IS\n    public async getAccessToken({ check = true } = {}): Promise<string | null> {\n        if (!this.authEnabled) {\n            // The current IS doesn't support authentication\n            return null;\n        }\n\n        let token: string | null = this.accessToken;\n        if (!token) {\n            token = this.readToken();\n        }\n\n        if (!token) {\n            token = await this.registerForToken(check);\n            if (token) {\n                this.accessToken = token;\n                this.writeToken();\n            }\n            return token;\n        }\n\n        if (check) {\n            try {\n                await this.checkToken(token);\n            } catch (e) {\n                if (e instanceof TermsNotSignedError || e instanceof AbortedIdentityActionError) {\n                    // Retrying won't help this\n                    throw e;\n                }\n                // Retry in case token expired\n                token = await this.registerForToken();\n                if (token) {\n                    this.accessToken = token;\n                    this.writeToken();\n                }\n            }\n        }\n\n        return token;\n    }\n\n    private async checkToken(token: string): Promise<void> {\n        const identityServerUrl = this.identityClient.getIdentityServerUrl()!;\n\n        try {\n            await this.identityClient.getIdentityAccount(token);\n        } catch (e) {\n            if (e instanceof MatrixError && e.errcode === \"M_TERMS_NOT_SIGNED\") {\n                logger.log(\"Identity server requires new terms to be agreed to\");\n                await startTermsFlow(this.matrixClient, [new Service(SERVICE_TYPES.IS, identityServerUrl, token)]);\n                return;\n            }\n            throw e;\n        }\n\n        if (\n            !this.tempClient &&\n            !doesAccountDataHaveIdentityServer(this.matrixClient) &&\n            !(await doesIdentityServerHaveTerms(this.matrixClient, identityServerUrl))\n        ) {\n            const { finished } = Modal.createDialog(QuestionDialog, {\n                title: _t(\"terms|identity_server_no_terms_title\"),\n                description: (\n                    <div>\n                        <p>\n                            {_t(\n                                \"terms|identity_server_no_terms_description_1\",\n                                {},\n                                {\n                                    server: () => <strong>{abbreviateUrl(identityServerUrl)}</strong>,\n                                },\n                            )}\n                        </p>\n                        <p>{_t(\"terms|identity_server_no_terms_description_2\")}</p>\n                    </div>\n                ),\n                button: _t(\"action|trust\"),\n            });\n            const [confirmed] = await finished;\n            if (confirmed) {\n                setToDefaultIdentityServer(this.matrixClient);\n            } else {\n                throw new AbortedIdentityActionError(\"User aborted identity server action without terms\");\n            }\n        }\n\n        // We should ensure the token in `localStorage` is cleared\n        // appropriately. We already clear storage on sign out, but we'll need\n        // additional clearing when changing ISes in settings as part of future\n        // privacy work.\n        // See also https://github.com/vector-im/element-web/issues/10455.\n    }\n\n    public async registerForToken(check = true): Promise<string> {\n        const hsOpenIdToken = await MatrixClientPeg.safeGet().getOpenIdToken();\n        // XXX: The spec is `token`, but we used `access_token` for a Sydent release.\n        const { access_token: accessToken, token } =\n            await this.identityClient.registerWithIdentityServer(hsOpenIdToken);\n        const identityAccessToken = token || accessToken;\n        if (check) await this.checkToken(identityAccessToken);\n        return identityAccessToken;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2021 Clemens Zeidler\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { IS_MAC, Key } from \"./Keyboard\";\nimport SettingsStore from \"./settings/SettingsStore\";\nimport SdkConfig from \"./SdkConfig\";\nimport { type IKeyBindingsProvider, type KeyBinding } from \"./KeyBindingsManager\";\nimport { CATEGORIES, CategoryName, KeyBindingAction } from \"./accessibility/KeyboardShortcuts\";\nimport { getKeyboardShortcuts } from \"./accessibility/KeyboardShortcutUtils\";\n\nexport const getBindingsByCategory = (category: CategoryName): KeyBinding[] => {\n    return CATEGORIES[category].settingNames.reduce<KeyBinding[]>((bindings, action) => {\n        const keyCombo = getKeyboardShortcuts()[action]?.default;\n        if (keyCombo) {\n            bindings.push({ action, keyCombo });\n        }\n        return bindings;\n    }, []);\n};\n\nconst messageComposerBindings = (): KeyBinding[] => {\n    const bindings = getBindingsByCategory(CategoryName.COMPOSER);\n\n    if (SettingsStore.getValue(\"MessageComposerInput.ctrlEnterToSend\")) {\n        bindings.push({\n            action: KeyBindingAction.SendMessage,\n            keyCombo: {\n                key: Key.ENTER,\n                ctrlOrCmdKey: true,\n            },\n        });\n        bindings.push({\n            action: KeyBindingAction.NewLine,\n            keyCombo: {\n                key: Key.ENTER,\n            },\n        });\n        bindings.push({\n            action: KeyBindingAction.NewLine,\n            keyCombo: {\n                key: Key.ENTER,\n                shiftKey: true,\n            },\n        });\n    } else {\n        bindings.push({\n            action: KeyBindingAction.SendMessage,\n            keyCombo: {\n                key: Key.ENTER,\n            },\n        });\n        bindings.push({\n            action: KeyBindingAction.NewLine,\n            keyCombo: {\n                key: Key.ENTER,\n                shiftKey: true,\n            },\n        });\n        if (IS_MAC) {\n            bindings.push({\n                action: KeyBindingAction.NewLine,\n                keyCombo: {\n                    key: Key.ENTER,\n                    altKey: true,\n                },\n            });\n        }\n    }\n\n    return bindings;\n};\n\nconst autocompleteBindings = (): KeyBinding[] => {\n    const bindings = getBindingsByCategory(CategoryName.AUTOCOMPLETE);\n\n    bindings.push({\n        action: KeyBindingAction.ForceCompleteAutocomplete,\n        keyCombo: {\n            key: Key.TAB,\n        },\n    });\n    bindings.push({\n        action: KeyBindingAction.ForceCompleteAutocomplete,\n        keyCombo: {\n            key: Key.TAB,\n            ctrlKey: true,\n        },\n    });\n    bindings.push({\n        action: KeyBindingAction.CompleteAutocomplete,\n        keyCombo: {\n            key: Key.ENTER,\n        },\n    });\n    bindings.push({\n        action: KeyBindingAction.CompleteAutocomplete,\n        keyCombo: {\n            key: Key.ENTER,\n            ctrlKey: true,\n        },\n    });\n\n    return bindings;\n};\n\nconst roomListBindings = (): KeyBinding[] => {\n    return getBindingsByCategory(CategoryName.ROOM_LIST);\n};\n\nconst roomBindings = (): KeyBinding[] => {\n    const bindings = getBindingsByCategory(CategoryName.ROOM);\n\n    if (SettingsStore.getValue(\"ctrlFForSearch\")) {\n        bindings.push({\n            action: KeyBindingAction.SearchInRoom,\n            keyCombo: {\n                key: Key.F,\n                ctrlOrCmdKey: true,\n            },\n        });\n    }\n\n    return bindings;\n};\n\nconst navigationBindings = (): KeyBinding[] => {\n    return getBindingsByCategory(CategoryName.NAVIGATION);\n};\n\nconst accessibilityBindings = (): KeyBinding[] => {\n    return getBindingsByCategory(CategoryName.ACCESSIBILITY);\n};\n\nconst callBindings = (): KeyBinding[] => {\n    return getBindingsByCategory(CategoryName.CALLS);\n};\n\nconst labsBindings = (): KeyBinding[] => {\n    if (!SdkConfig.get(\"show_labs_settings\")) return [];\n\n    return getBindingsByCategory(CategoryName.LABS);\n};\n\nexport const defaultBindingsProvider: IKeyBindingsProvider = {\n    getMessageComposerBindings: messageComposerBindings,\n    getAutocompleteBindings: autocompleteBindings,\n    getRoomListBindings: roomListBindings,\n    getRoomBindings: roomBindings,\n    getNavigationBindings: navigationBindings,\n    getAccessibilityBindings: accessibilityBindings,\n    getCallBindings: callBindings,\n    getLabsBindings: labsBindings,\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2021 Clemens Zeidler\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type KeyBindingAction } from \"./accessibility/KeyboardShortcuts\";\nimport { defaultBindingsProvider } from \"./KeyBindingsDefaults\";\nimport { IS_MAC } from \"./Keyboard\";\n\n/**\n * Represent a key combination.\n *\n * The combo is evaluated strictly, i.e. the KeyboardEvent must match exactly what is specified in the KeyCombo.\n */\nexport type KeyCombo = {\n    key: string;\n\n    /** On PC: ctrl is pressed; on Mac: meta is pressed */\n    ctrlOrCmdKey?: boolean;\n\n    altKey?: boolean;\n    ctrlKey?: boolean;\n    metaKey?: boolean;\n    shiftKey?: boolean;\n};\n\nexport type KeyBinding = {\n    action: KeyBindingAction;\n    keyCombo: KeyCombo;\n};\n\n/**\n * Helper method to check if a KeyboardEvent matches a KeyCombo\n *\n * Note, this method is only exported for testing.\n */\nexport function isKeyComboMatch(ev: KeyboardEvent | React.KeyboardEvent, combo: KeyCombo, onMac: boolean): boolean {\n    if (combo.key !== undefined) {\n        // When shift is pressed, letters are returned as upper case chars. In this case do a lower case comparison.\n        // This works for letter combos such as shift + U as well for none letter combos such as shift + Escape.\n        // If shift is not pressed, the toLowerCase conversion can be avoided.\n        if (ev.shiftKey) {\n            if (ev.key.toLowerCase() !== combo.key.toLowerCase()) {\n                return false;\n            }\n        } else if (ev.key !== combo.key) {\n            return false;\n        }\n    }\n\n    const comboCtrl = combo.ctrlKey ?? false;\n    const comboAlt = combo.altKey ?? false;\n    const comboShift = combo.shiftKey ?? false;\n    const comboMeta = combo.metaKey ?? false;\n    // Tests mock events may keep the modifiers undefined; convert them to booleans\n    const evCtrl = ev.ctrlKey ?? false;\n    const evAlt = ev.altKey ?? false;\n    const evShift = ev.shiftKey ?? false;\n    const evMeta = ev.metaKey ?? false;\n    // When ctrlOrCmd is set, the keys need do evaluated differently on PC and Mac\n    if (combo.ctrlOrCmdKey) {\n        if (onMac) {\n            if (!evMeta || evCtrl !== comboCtrl || evAlt !== comboAlt || evShift !== comboShift) {\n                return false;\n            }\n        } else {\n            if (!evCtrl || evMeta !== comboMeta || evAlt !== comboAlt || evShift !== comboShift) {\n                return false;\n            }\n        }\n        return true;\n    }\n\n    if (evMeta !== comboMeta || evCtrl !== comboCtrl || evAlt !== comboAlt || evShift !== comboShift) {\n        return false;\n    }\n\n    return true;\n}\n\nexport type KeyBindingGetter = () => KeyBinding[];\n\nexport interface IKeyBindingsProvider {\n    [key: string]: KeyBindingGetter;\n}\n\nexport class KeyBindingsManager {\n    /**\n     * List of key bindings providers.\n     *\n     * Key bindings from the first provider(s) in the list will have precedence over key bindings from later providers.\n     *\n     * To overwrite the default key bindings add a new providers before the default provider, e.g. a provider for\n     * customized key bindings.\n     */\n    public bindingsProviders: IKeyBindingsProvider[] = [defaultBindingsProvider];\n\n    /**\n     * Finds a matching KeyAction for a given KeyboardEvent\n     */\n    private getAction(\n        getters: KeyBindingGetter[],\n        ev: KeyboardEvent | React.KeyboardEvent,\n    ): KeyBindingAction | undefined {\n        for (const getter of getters) {\n            const bindings = getter();\n            const binding = bindings.find((it) => isKeyComboMatch(ev, it.keyCombo, IS_MAC));\n            if (binding) {\n                return binding.action;\n            }\n        }\n        return undefined;\n    }\n\n    public getMessageComposerAction(ev: KeyboardEvent | React.KeyboardEvent): KeyBindingAction | undefined {\n        return this.getAction(\n            this.bindingsProviders.map((it) => it.getMessageComposerBindings),\n            ev,\n        );\n    }\n\n    public getAutocompleteAction(ev: KeyboardEvent | React.KeyboardEvent): KeyBindingAction | undefined {\n        return this.getAction(\n            this.bindingsProviders.map((it) => it.getAutocompleteBindings),\n            ev,\n        );\n    }\n\n    public getRoomListAction(ev: KeyboardEvent | React.KeyboardEvent): KeyBindingAction | undefined {\n        return this.getAction(\n            this.bindingsProviders.map((it) => it.getRoomListBindings),\n            ev,\n        );\n    }\n\n    public getRoomAction(ev: KeyboardEvent | React.KeyboardEvent): KeyBindingAction | undefined {\n        return this.getAction(\n            this.bindingsProviders.map((it) => it.getRoomBindings),\n            ev,\n        );\n    }\n\n    public getNavigationAction(ev: KeyboardEvent | React.KeyboardEvent): KeyBindingAction | undefined {\n        return this.getAction(\n            this.bindingsProviders.map((it) => it.getNavigationBindings),\n            ev,\n        );\n    }\n\n    public getAccessibilityAction(ev: KeyboardEvent | React.KeyboardEvent): KeyBindingAction | undefined {\n        return this.getAction(\n            this.bindingsProviders.map((it) => it.getAccessibilityBindings),\n            ev,\n        );\n    }\n\n    public getCallAction(ev: KeyboardEvent | React.KeyboardEvent): KeyBindingAction | undefined {\n        return this.getAction(\n            this.bindingsProviders.map((it) => it.getCallBindings),\n            ev,\n        );\n    }\n\n    public getLabsAction(ev: KeyboardEvent | React.KeyboardEvent): KeyBindingAction | undefined {\n        return this.getAction(\n            this.bindingsProviders.map((it) => it.getLabsBindings),\n            ev,\n        );\n    }\n}\n\nconst manager = new KeyBindingsManager();\n\nexport function getKeyBindingsManager(): KeyBindingsManager {\n    return manager;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2017 New Vector Ltd\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type React from \"react\";\n\nexport const Key = {\n    HOME: \"Home\",\n    END: \"End\",\n    PAGE_UP: \"PageUp\",\n    PAGE_DOWN: \"PageDown\",\n    BACKSPACE: \"Backspace\",\n    DELETE: \"Delete\",\n    ARROW_UP: \"ArrowUp\",\n    ARROW_DOWN: \"ArrowDown\",\n    ARROW_LEFT: \"ArrowLeft\",\n    ARROW_RIGHT: \"ArrowRight\",\n    F6: \"F6\",\n    TAB: \"Tab\",\n    ESCAPE: \"Escape\",\n    ENTER: \"Enter\",\n    ALT: \"Alt\",\n    CONTROL: \"Control\",\n    META: \"Meta\",\n    SHIFT: \"Shift\",\n    CONTEXT_MENU: \"ContextMenu\",\n\n    COMMA: \",\",\n    PERIOD: \".\",\n    LESS_THAN: \"<\",\n    GREATER_THAN: \">\",\n    BACKTICK: \"`\",\n    SPACE: \" \",\n    SLASH: \"/\",\n    SQUARE_BRACKET_LEFT: \"[\",\n    SQUARE_BRACKET_RIGHT: \"]\",\n    SEMICOLON: \";\",\n    A: \"a\",\n    B: \"b\",\n    C: \"c\",\n    D: \"d\",\n    E: \"e\",\n    F: \"f\",\n    G: \"g\",\n    H: \"h\",\n    I: \"i\",\n    J: \"j\",\n    K: \"k\",\n    L: \"l\",\n    M: \"m\",\n    N: \"n\",\n    O: \"o\",\n    P: \"p\",\n    Q: \"q\",\n    R: \"r\",\n    S: \"s\",\n    T: \"t\",\n    U: \"u\",\n    V: \"v\",\n    W: \"w\",\n    X: \"x\",\n    Y: \"y\",\n    Z: \"z\",\n};\n\nexport const IS_MAC = navigator.platform.toUpperCase().includes(\"MAC\");\nexport const IS_ELECTRON = window.electron;\n\nexport function isOnlyCtrlOrCmdKeyEvent(ev: React.KeyboardEvent | KeyboardEvent): boolean {\n    if (IS_MAC) {\n        return ev.metaKey && !ev.altKey && !ev.ctrlKey && !ev.shiftKey;\n    } else {\n        return ev.ctrlKey && !ev.altKey && !ev.metaKey && !ev.shiftKey;\n    }\n}\n\n/**\n * Checks if the given keyboard event is a modified key event (i.e., if any modifier keys are active).\n * @param ev The keyboard event to check\n * @returns True if the event is a modified key event, false otherwise\n */\nexport function isModifiedKeyEvent(ev: React.KeyboardEvent | KeyboardEvent): boolean {\n    return ev.metaKey || ev.altKey || ev.ctrlKey || ev.shiftKey;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { CallType, type MatrixCall } from \"matrix-js-sdk/src/webrtc/call\";\nimport {\n    EndCallIcon,\n    VideoCallSolidIcon,\n    VoiceCallSolidIcon,\n    VolumeOffSolidIcon,\n    VolumeOnSolidIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport LegacyCallHandler, { LegacyCallHandlerEvent } from \"../LegacyCallHandler\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { _t } from \"../languageHandler\";\nimport RoomAvatar from \"../components/views/avatars/RoomAvatar\";\nimport AccessibleButton, { type ButtonEvent } from \"../components/views/elements/AccessibleButton\";\nimport { getCallStateIcon } from \"../components/views/messages/LegacyCallEvent.tsx\";\n\nexport const getIncomingLegacyCallToastKey = (callId: string): string => `call_${callId}`;\n\ninterface IProps {\n    call: MatrixCall;\n}\n\ninterface IState {\n    silenced: boolean;\n}\n\nexport default class IncomingLegacyCallToast extends React.Component<IProps, IState> {\n    private readonly roomId: string;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        const roomId = LegacyCallHandler.instance.roomIdForCall(this.props.call);\n        if (!roomId) {\n            throw new Error(\"Unable to find room for incoming call\");\n        }\n        this.roomId = roomId;\n\n        this.state = {\n            silenced: LegacyCallHandler.instance.isCallSilenced(this.props.call.callId),\n        };\n    }\n\n    public componentDidMount = (): void => {\n        LegacyCallHandler.instance.addListener(\n            LegacyCallHandlerEvent.SilencedCallsChanged,\n            this.onSilencedCallsChanged,\n        );\n    };\n\n    public componentWillUnmount(): void {\n        LegacyCallHandler.instance.removeListener(\n            LegacyCallHandlerEvent.SilencedCallsChanged,\n            this.onSilencedCallsChanged,\n        );\n    }\n\n    private onSilencedCallsChanged = (): void => {\n        this.setState({ silenced: LegacyCallHandler.instance.isCallSilenced(this.props.call.callId) });\n    };\n\n    private onAnswerClick = (e: ButtonEvent): void => {\n        e.stopPropagation();\n        LegacyCallHandler.instance.answerCall(this.roomId);\n    };\n\n    private onRejectClick = (e: ButtonEvent): void => {\n        e.stopPropagation();\n        LegacyCallHandler.instance.hangupOrReject(this.roomId, true);\n    };\n\n    private onSilenceClick = (e: ButtonEvent): void => {\n        e.stopPropagation();\n        const callId = this.props.call.callId;\n        if (this.state.silenced) {\n            LegacyCallHandler.instance.unSilenceCall(callId);\n        } else {\n            LegacyCallHandler.instance.silenceCall(callId);\n        }\n    };\n\n    public render(): React.ReactNode {\n        const room = MatrixClientPeg.safeGet().getRoom(this.roomId);\n        const isVoice = this.props.call.type === CallType.Voice;\n        const callForcedSilent = LegacyCallHandler.instance.isForcedSilent();\n\n        let silenceButtonTooltip = this.state.silenced ? _t(\"voip|unsilence\") : _t(\"voip|silence\");\n        if (callForcedSilent) {\n            silenceButtonTooltip = _t(\"voip|silenced\");\n        }\n\n        return (\n            <React.Fragment>\n                <RoomAvatar room={room ?? undefined} size=\"32px\" />\n                <div className=\"mx_IncomingLegacyCallToast_content\">\n                    <span className=\"mx_LegacyCallEvent_caller\">{room ? room.name : _t(\"voip|unknown_caller\")}</span>\n                    <div className=\"mx_LegacyCallEvent_type\">\n                        {getCallStateIcon(isVoice, undefined)}\n                        {isVoice ? _t(\"voip|voice_call\") : _t(\"voip|video_call\")}\n                    </div>\n                    <div className=\"mx_IncomingLegacyCallToast_buttons\">\n                        <AccessibleButton\n                            className=\"mx_IncomingLegacyCallToast_button\"\n                            onClick={this.onRejectClick}\n                            kind=\"danger\"\n                        >\n                            <EndCallIcon />\n                            {_t(\"action|decline\")}\n                        </AccessibleButton>\n                        <AccessibleButton\n                            className=\"mx_IncomingLegacyCallToast_button\"\n                            onClick={this.onAnswerClick}\n                            kind=\"primary\"\n                        >\n                            {isVoice ? <VoiceCallSolidIcon /> : <VideoCallSolidIcon />}\n                            {_t(\"action|accept\")}\n                        </AccessibleButton>\n                    </div>\n                </div>\n                <AccessibleButton\n                    className=\"mx_IncomingLegacyCallToast_iconButton\"\n                    disabled={callForcedSilent}\n                    onClick={this.onSilenceClick}\n                    title={silenceButtonTooltip}\n                >\n                    {this.state.silenced ? <VolumeOffSolidIcon /> : <VolumeOnSolidIcon />}\n                </AccessibleButton>\n            </React.Fragment>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2022 The Matrix.org Foundation C.I.C.\nCopyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2017, 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { MatrixError, RuleId, TweakName, SyncState, TypedEventEmitter } from \"matrix-js-sdk/src/matrix\";\nimport {\n    type CallError,\n    CallErrorCode,\n    CallEvent,\n    CallParty,\n    CallState,\n    CallType,\n    FALLBACK_ICE_SERVER,\n    type MatrixCall,\n} from \"matrix-js-sdk/src/webrtc/call\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { CallEventHandlerEvent } from \"matrix-js-sdk/src/webrtc/callEventHandler\";\n\nimport { MatrixClientPeg } from \"./MatrixClientPeg\";\nimport Modal from \"./Modal\";\nimport { _t } from \"./languageHandler\";\nimport dis from \"./dispatcher/dispatcher\";\nimport WidgetUtils from \"./utils/WidgetUtils\";\nimport SettingsStore from \"./settings/SettingsStore\";\nimport { WidgetType } from \"./widgets/WidgetType\";\nimport { SettingLevel } from \"./settings/SettingLevel\";\nimport QuestionDialog from \"./components/views/dialogs/QuestionDialog\";\nimport ErrorDialog from \"./components/views/dialogs/ErrorDialog\";\nimport WidgetStore from \"./stores/WidgetStore\";\nimport { WidgetMessagingStore } from \"./stores/widgets/WidgetMessagingStore\";\nimport { ElementWidgetActions } from \"./stores/widgets/ElementWidgetActions\";\nimport { UIFeature } from \"./settings/UIFeature\";\nimport { Action } from \"./dispatcher/actions\";\nimport { addManagedHybridWidget, isManagedHybridWidgetEnabled } from \"./widgets/ManagedHybrid\";\nimport SdkConfig from \"./SdkConfig\";\nimport { ensureDMExists } from \"./createRoom\";\nimport { Container, WidgetLayoutStore } from \"./stores/widgets/WidgetLayoutStore\";\nimport IncomingLegacyCallToast, { getIncomingLegacyCallToastKey } from \"./toasts/IncomingLegacyCallToast\";\nimport ToastStore from \"./stores/ToastStore\";\nimport { type ViewRoomPayload } from \"./dispatcher/payloads/ViewRoomPayload\";\nimport { InviteKind } from \"./components/views/dialogs/InviteDialogTypes\";\nimport { type OpenInviteDialogPayload } from \"./dispatcher/payloads/OpenInviteDialogPayload\";\nimport { findDMForUser } from \"./utils/dm/findDMForUser\";\nimport { getJoinedNonFunctionalMembers } from \"./utils/room/getJoinedNonFunctionalMembers\";\nimport { localNotificationsAreSilenced } from \"./utils/notifications\";\nimport { isNotNull } from \"./Typeguards\";\nimport { BackgroundAudio } from \"./audio/BackgroundAudio\";\nimport { Jitsi } from \"./widgets/Jitsi.ts\";\n\nexport const PROTOCOL_PSTN = \"m.protocol.pstn\";\nexport const PROTOCOL_PSTN_PREFIXED = \"im.vector.protocol.pstn\";\n\nconst CHECK_PROTOCOLS_ATTEMPTS = 3;\n\ntype MediaEventType = keyof HTMLMediaElementEventMap;\nconst MEDIA_ERROR_EVENT_TYPES: MediaEventType[] = [\n    \"error\",\n    // The media has become empty; for example, this event is sent if the media has\n    // already been loaded (or partially loaded), and the HTMLMediaElement.load method\n    // is called to reload it.\n    \"emptied\",\n    // The user agent is trying to fetch media data, but data is unexpectedly not\n    // forthcoming.\n    \"stalled\",\n    // Media data loading has been suspended.\n    \"suspend\",\n    // Playback has stopped because of a temporary lack of data\n    \"waiting\",\n];\nconst MEDIA_DEBUG_EVENT_TYPES: MediaEventType[] = [\n    \"play\",\n    \"pause\",\n    \"playing\",\n    \"ended\",\n    \"loadeddata\",\n    \"loadedmetadata\",\n    \"canplay\",\n    \"canplaythrough\",\n    \"volumechange\",\n];\n\nconst MEDIA_EVENT_TYPES = [...MEDIA_ERROR_EVENT_TYPES, ...MEDIA_DEBUG_EVENT_TYPES];\n\nexport enum AudioID {\n    Ring = \"ringAudio\",\n    Ringback = \"ringbackAudio\",\n    CallEnd = \"callendAudio\",\n    Busy = \"busyAudio\",\n}\n\n/* istanbul ignore next */\nconst debuglog = (...args: any[]): void => {\n    if (SettingsStore.getValue(\"debug_legacy_call_handler\")) {\n        logger.log.call(console, \"LegacyCallHandler debuglog:\", ...args);\n    }\n};\n\ninterface ThirdpartyLookupResponse {\n    userid: string;\n    protocol: string;\n}\n\nexport enum LegacyCallHandlerEvent {\n    CallsChanged = \"calls_changed\",\n    CallChangeRoom = \"call_change_room\",\n    SilencedCallsChanged = \"silenced_calls_changed\",\n    ShownSidebarsChanged = \"shown_sidebars_changed\",\n    CallState = \"call_state\",\n    ProtocolSupport = \"protocol_support\",\n}\n\ntype EventEmitterMap = {\n    [LegacyCallHandlerEvent.CallsChanged]: (calls: Map<string, MatrixCall>) => void;\n    [LegacyCallHandlerEvent.CallChangeRoom]: (call: MatrixCall) => void;\n    [LegacyCallHandlerEvent.SilencedCallsChanged]: (calls: Set<string>) => void;\n    [LegacyCallHandlerEvent.ShownSidebarsChanged]: (sidebarsShown: Map<string, boolean>) => void;\n    [LegacyCallHandlerEvent.CallState]: (mappedRoomId: string | null, status: CallState) => void;\n    [LegacyCallHandlerEvent.ProtocolSupport]: () => void;\n};\n\n/**\n * LegacyCallHandler manages all currently active calls. It should be used for\n * placing, answering, rejecting and hanging up calls. It also handles ringing,\n * PSTN support and other things.\n */\nexport default class LegacyCallHandler extends TypedEventEmitter<LegacyCallHandlerEvent, EventEmitterMap> {\n    private calls = new Map<string, MatrixCall>(); // roomId -> call\n    // Calls started as an attended transfer, ie. with the intention of transferring another\n    // call with a different party to this one.\n    private transferees = new Map<string, MatrixCall>(); // callId (target) -> call (transferee)\n    private supportsPstnProtocol: boolean | null = null;\n    private pstnSupportPrefixed: boolean | null = null; // True if the server only support the prefixed pstn protocol\n\n    // Map of the asserted identity users after we've looked them up using the API.\n    // We need to be be able to determine the mapped room synchronously, so we\n    // do the async lookup when we get new information and then store these mappings here\n    private assertedIdentityNativeUsers = new Map<string, string>();\n\n    private silencedCalls = new Set<string>(); // callIds\n\n    private shownSidebars = new Map<string, boolean>(); // callId (call) -> sidebar show\n\n    private backgroundAudio = new BackgroundAudio();\n    private playingSources: Record<string, AudioBufferSourceNode> = {}; // Record them for stopping\n\n    public static get instance(): LegacyCallHandler {\n        if (!window.mxLegacyCallHandler) {\n            window.mxLegacyCallHandler = new LegacyCallHandler();\n        }\n\n        return window.mxLegacyCallHandler;\n    }\n\n    /*\n     * Gets the user-facing room associated with a call\n     */\n    public roomIdForCall(call?: MatrixCall): string | null {\n        if (!call) return null;\n\n        // check asserted identity: if we're not obeying asserted identity,\n        // this map will never be populated, but we check anyway for sanity\n        if (this.shouldObeyAssertedfIdentity()) {\n            const nativeUser = this.assertedIdentityNativeUsers.get(call.callId);\n            if (nativeUser) {\n                const room = findDMForUser(MatrixClientPeg.safeGet(), nativeUser);\n                if (room) return room.roomId;\n            }\n        }\n\n        return call.roomId ?? null;\n    }\n\n    public start(): void {\n        if (SettingsStore.getValue(UIFeature.Voip)) {\n            MatrixClientPeg.safeGet().on(CallEventHandlerEvent.Incoming, this.onCallIncoming);\n        }\n\n        this.checkProtocols(CHECK_PROTOCOLS_ATTEMPTS);\n    }\n\n    public stop(): void {\n        const cli = MatrixClientPeg.get();\n        if (cli) {\n            cli.removeListener(CallEventHandlerEvent.Incoming, this.onCallIncoming);\n        }\n    }\n\n    /* istanbul ignore next (remove if we start using this function for things other than debug logging) */\n    public handleEvent(e: Event): void {\n        const target = e.target as HTMLElement;\n        const audioId = target?.id;\n\n        if (MEDIA_ERROR_EVENT_TYPES.includes(e.type as MediaEventType)) {\n            logger.error(`LegacyCallHandler: encountered \"${e.type}\" event with <audio id=\"${audioId}\">`, e);\n        } else if (MEDIA_EVENT_TYPES.includes(e.type as MediaEventType)) {\n            debuglog(`encountered \"${e.type}\" event with <audio id=\"${audioId}\">`, e);\n        }\n    }\n\n    public isForcedSilent(): boolean {\n        const cli = MatrixClientPeg.safeGet();\n        return localNotificationsAreSilenced(cli);\n    }\n\n    public silenceCall(callId?: string): void {\n        if (!callId) return;\n        this.silencedCalls.add(callId);\n        this.emit(LegacyCallHandlerEvent.SilencedCallsChanged, this.silencedCalls);\n\n        // Don't pause audio if we have calls which are still ringing\n        if (this.areAnyCallsUnsilenced()) return;\n        this.pause(AudioID.Ring);\n    }\n\n    public unSilenceCall(callId?: string): void {\n        if (!callId || this.isForcedSilent()) return;\n        this.silencedCalls.delete(callId);\n        this.emit(LegacyCallHandlerEvent.SilencedCallsChanged, this.silencedCalls);\n        this.play(AudioID.Ring);\n    }\n\n    public isCallSilenced(callId?: string): boolean {\n        return this.isForcedSilent() || (!!callId && this.silencedCalls.has(callId));\n    }\n\n    /**\n     * Returns true if there is at least one unsilenced call\n     * @returns {boolean}\n     */\n    private areAnyCallsUnsilenced(): boolean {\n        for (const call of this.calls.values()) {\n            if (call.state === CallState.Ringing && !this.isCallSilenced(call.callId)) {\n                return true;\n            }\n        }\n        return false;\n    }\n\n    public setCallSidebarShown(callId: string, sidebarShown: boolean): void {\n        this.shownSidebars.set(callId, sidebarShown);\n        this.emit(LegacyCallHandlerEvent.ShownSidebarsChanged, this.shownSidebars);\n    }\n\n    public isCallSidebarShown(callId?: string): boolean {\n        return !!callId && (this.shownSidebars.get(callId) ?? true);\n    }\n\n    private async checkProtocols(maxTries: number): Promise<void> {\n        try {\n            const protocols = await MatrixClientPeg.safeGet().getThirdpartyProtocols();\n\n            if (protocols[PROTOCOL_PSTN] !== undefined) {\n                this.supportsPstnProtocol = Boolean(protocols[PROTOCOL_PSTN]);\n                if (this.supportsPstnProtocol) this.pstnSupportPrefixed = false;\n            } else if (protocols[PROTOCOL_PSTN_PREFIXED] !== undefined) {\n                this.supportsPstnProtocol = Boolean(protocols[PROTOCOL_PSTN_PREFIXED]);\n                if (this.supportsPstnProtocol) this.pstnSupportPrefixed = true;\n            } else {\n                this.supportsPstnProtocol = null;\n            }\n\n            this.emit(LegacyCallHandlerEvent.ProtocolSupport);\n        } catch (e) {\n            if (maxTries === 1) {\n                logger.log(\"Failed to check for protocol support and no retries remain: assuming no support\", e);\n            } else {\n                logger.log(\"Failed to check for protocol support: will retry\", e);\n                window.setTimeout(() => {\n                    this.checkProtocols(maxTries - 1);\n                }, 10000);\n            }\n        }\n    }\n\n    private shouldObeyAssertedfIdentity(): boolean {\n        return !!SdkConfig.getObject(\"voip\")?.get(\"obey_asserted_identity\");\n    }\n\n    public getSupportsPstnProtocol(): boolean {\n        return this.supportsPstnProtocol ?? false;\n    }\n\n    public async pstnLookup(phoneNumber: string): Promise<ThirdpartyLookupResponse[]> {\n        try {\n            return await MatrixClientPeg.safeGet().getThirdpartyUser(\n                this.pstnSupportPrefixed ? PROTOCOL_PSTN_PREFIXED : PROTOCOL_PSTN,\n                {\n                    \"m.id.phone\": phoneNumber,\n                },\n            );\n        } catch (e) {\n            logger.warn(\"Failed to lookup user from phone number\", e);\n            return Promise.resolve([]);\n        }\n    }\n\n    private onCallIncoming = (call: MatrixCall): void => {\n        // if the runtime env doesn't do VoIP, stop here.\n        if (!MatrixClientPeg.get()?.supportsVoip()) {\n            return;\n        }\n\n        const mappedRoomId = LegacyCallHandler.instance.roomIdForCall(call);\n        if (!mappedRoomId) return;\n        if (this.getCallForRoom(mappedRoomId)) {\n            logger.log(\n                \"Got incoming call for room \" + mappedRoomId + \" but there's already a call for this room: ignoring\",\n            );\n            return;\n        }\n\n        this.addCallForRoom(mappedRoomId, call);\n        this.setCallListeners(call);\n        // Explicitly handle first state change\n        this.onCallStateChanged(call.state, null, call);\n\n        // get ready to send encrypted events in the room, so if the user does answer\n        // the call, we'll be ready to send. NB. This is the protocol-level room ID not\n        // the mapped one: that's where we'll send the events.\n        const cli = MatrixClientPeg.safeGet();\n        const room = cli.getRoom(call.roomId);\n        if (room) cli.getCrypto()?.prepareToEncrypt(room);\n    };\n\n    public getCallById(callId: string): MatrixCall | null {\n        for (const call of this.calls.values()) {\n            if (call.callId === callId) return call;\n        }\n        return null;\n    }\n\n    public getCallForRoom(roomId: string): MatrixCall | null {\n        return this.calls.get(roomId) || null;\n    }\n\n    public getAllActiveCalls(): MatrixCall[] {\n        const activeCalls: MatrixCall[] = [];\n\n        for (const call of this.calls.values()) {\n            if (call.state !== CallState.Ended && call.state !== CallState.Ringing) {\n                activeCalls.push(call);\n            }\n        }\n        return activeCalls;\n    }\n\n    public getAllActiveCallsNotInRoom(notInThisRoomId: string): MatrixCall[] {\n        const callsNotInThatRoom: MatrixCall[] = [];\n\n        for (const [roomId, call] of this.calls.entries()) {\n            if (roomId !== notInThisRoomId && call.state !== CallState.Ended) {\n                callsNotInThatRoom.push(call);\n            }\n        }\n        return callsNotInThatRoom;\n    }\n\n    public getAllActiveCallsForPip(roomId: string): MatrixCall[] {\n        const room = MatrixClientPeg.safeGet().getRoom(roomId);\n        if (room && WidgetLayoutStore.instance.hasMaximisedWidget(room)) {\n            // This checks if there is space for the call view in the aux panel\n            // If there is no space any call should be displayed in PiP\n            return this.getAllActiveCalls();\n        }\n        return this.getAllActiveCallsNotInRoom(roomId);\n    }\n\n    public getTransfereeForCallId(callId: string): MatrixCall | undefined {\n        return this.transferees.get(callId);\n    }\n\n    public async play(audioId: AudioID): Promise<void> {\n        const logPrefix = `LegacyCallHandler.play(${audioId}):`;\n        logger.debug(`${logPrefix} beginning of function`);\n\n        const audioInfo: Record<AudioID, [prefix: string, loop: boolean]> = {\n            [AudioID.Ring]: [`./media/ring`, true],\n            [AudioID.Ringback]: [`./media/ringback`, true],\n            [AudioID.CallEnd]: [`./media/callend`, false],\n            [AudioID.Busy]: [`./media/busy`, false],\n        };\n\n        const [urlPrefix, loop] = audioInfo[audioId];\n        const source = await this.backgroundAudio.pickFormatAndPlay(urlPrefix, [\"mp3\", \"ogg\"], loop);\n        if (this.playingSources[audioId]) {\n            logger.warn(`${logPrefix} Already playing audio ${audioId}!`);\n        }\n        this.playingSources[audioId] = source;\n        logger.debug(`${logPrefix} playing audio successfully`);\n    }\n\n    public pause(audioId: AudioID): void {\n        const logPrefix = `LegacyCallHandler.pause(${audioId}):`;\n        logger.debug(`${logPrefix} beginning of function`);\n\n        const source = this.playingSources[audioId];\n        if (!source) {\n            logger.debug(`${logPrefix} audio not playing`);\n            return;\n        }\n\n        source.stop();\n        delete this.playingSources[audioId];\n\n        logger.debug(`${logPrefix} paused audio`);\n    }\n\n    /**\n     * Returns whether the given audio is currently playing\n     * Only supported for looping audio tracks\n     * @param audioId the ID of the audio to query for playing state\n     */\n    public isPlaying(audioId: AudioID.Ring | AudioID.Ringback): boolean {\n        return !!this.playingSources[audioId];\n    }\n\n    private matchesCallForThisRoom(call: MatrixCall): boolean {\n        // We don't allow placing more than one call per room, but that doesn't mean there\n        // can't be more than one, eg. in a glare situation. This checks that the given call\n        // is the call we consider 'the' call for its room.\n        const mappedRoomId = this.roomIdForCall(call);\n\n        const callForThisRoom = mappedRoomId ? this.getCallForRoom(mappedRoomId) : null;\n        return !!callForThisRoom && call.callId === callForThisRoom.callId;\n    }\n\n    private setCallListeners(call: MatrixCall): void {\n        let mappedRoomId = this.roomIdForCall(call);\n\n        call.on(CallEvent.Error, (err: CallError) => {\n            if (!this.matchesCallForThisRoom(call)) return;\n\n            logger.error(\"Call error:\", err);\n\n            if (err.code === CallErrorCode.NoUserMedia) {\n                this.showMediaCaptureError(call);\n                return;\n            }\n\n            if (\n                MatrixClientPeg.safeGet().getTurnServers().length === 0 &&\n                SettingsStore.getValue(\"fallbackICEServerAllowed\") === null\n            ) {\n                this.showICEFallbackPrompt();\n                return;\n            }\n\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"voip|call_failed\"),\n                description: err.message,\n            });\n        });\n        call.on(CallEvent.Hangup, () => {\n            if (!mappedRoomId || !this.matchesCallForThisRoom(call)) return;\n\n            if (isNotNull(mappedRoomId)) {\n                this.removeCallForRoom(mappedRoomId);\n            }\n        });\n        call.on(CallEvent.State, (newState: CallState, oldState: CallState) => {\n            this.onCallStateChanged(newState, oldState, call);\n        });\n        call.on(CallEvent.Replaced, (newCall: MatrixCall) => {\n            if (!mappedRoomId || !this.matchesCallForThisRoom(call)) return;\n\n            logger.log(`Call ID ${call.callId} is being replaced by call ID ${newCall.callId}`);\n\n            if (call.state === CallState.Ringing) {\n                this.pause(AudioID.Ring);\n            } else if (call.state === CallState.InviteSent) {\n                this.pause(AudioID.Ringback);\n            }\n\n            if (isNotNull(mappedRoomId)) {\n                this.removeCallForRoom(mappedRoomId);\n                this.addCallForRoom(mappedRoomId, newCall);\n            }\n            this.setCallListeners(newCall);\n            this.setCallState(newCall, newCall.state);\n        });\n        call.on(CallEvent.AssertedIdentityChanged, async (): Promise<void> => {\n            if (!mappedRoomId || !this.matchesCallForThisRoom(call)) return;\n\n            logger.log(`Call ID ${call.callId} got new asserted identity:`, call.getRemoteAssertedIdentity());\n\n            if (!this.shouldObeyAssertedfIdentity()) {\n                logger.log(\"asserted identity not enabled in config: ignoring\");\n                return;\n            }\n\n            const newAssertedIdentity = call.getRemoteAssertedIdentity()?.id;\n\n            if (newAssertedIdentity) {\n                this.assertedIdentityNativeUsers.set(call.callId, newAssertedIdentity);\n\n                // If we don't already have a room with this user, make one. This will be slightly odd\n                // if they called us because we'll be inviting them, but there's not much we can do about\n                // this if we want the actual, native room to exist (which we do). This is why it's\n                // important to only obey asserted identity in trusted environments, since anyone you're\n                // on a call with can cause you to send a room invite to someone.\n                await ensureDMExists(MatrixClientPeg.safeGet(), newAssertedIdentity);\n\n                const newMappedRoomId = this.roomIdForCall(call);\n                logger.log(`Old room ID: ${mappedRoomId}, new room ID: ${newMappedRoomId}`);\n                if (newMappedRoomId !== mappedRoomId && isNotNull(mappedRoomId) && isNotNull(newMappedRoomId)) {\n                    this.removeCallForRoom(mappedRoomId);\n                    mappedRoomId = newMappedRoomId;\n                    logger.log(\"Moving call to room \" + mappedRoomId);\n                    this.addCallForRoom(mappedRoomId, call, true);\n                }\n            }\n        });\n    }\n\n    private onCallStateChanged = (newState: CallState, oldState: CallState | null, call: MatrixCall): void => {\n        const mappedRoomId = this.roomIdForCall(call);\n        if (!mappedRoomId || !this.matchesCallForThisRoom(call)) return;\n\n        this.setCallState(call, newState);\n        // XXX: this is used by the IPC into Electron to keep device awake\n        dis.dispatch({\n            action: \"call_state\",\n            room_id: mappedRoomId,\n            state: newState,\n        });\n\n        switch (oldState) {\n            case CallState.Ringing:\n                this.pause(AudioID.Ring);\n                break;\n            case CallState.InviteSent:\n                this.pause(AudioID.Ringback);\n                break;\n        }\n\n        if (newState !== CallState.Ringing) {\n            this.silencedCalls.delete(call.callId);\n        }\n\n        switch (newState) {\n            case CallState.Ringing: {\n                const incomingCallPushRule = MatrixClientPeg.safeGet().pushProcessor.getPushRuleById(\n                    RuleId.IncomingCall,\n                );\n                const pushRuleEnabled = incomingCallPushRule?.enabled;\n                // actions can be either Tweaks | PushRuleActionName, ie an object or a string type enum\n                // and we want to only run this check on the Tweaks\n                const tweakSetToRing = incomingCallPushRule?.actions.some(\n                    (action) =>\n                        typeof action !== \"string\" && action.set_tweak === TweakName.Sound && action.value === \"ring\",\n                );\n\n                if (pushRuleEnabled && tweakSetToRing && !this.isForcedSilent()) {\n                    this.play(AudioID.Ring);\n                } else {\n                    this.silenceCall(call.callId);\n                }\n                break;\n            }\n            case CallState.InviteSent: {\n                this.play(AudioID.Ringback);\n                break;\n            }\n            case CallState.Ended: {\n                const hangupReason = call.hangupReason;\n                if (isNotNull(mappedRoomId)) {\n                    this.removeCallForRoom(mappedRoomId);\n                }\n\n                if (oldState === CallState.InviteSent && call.hangupParty === CallParty.Remote) {\n                    this.play(AudioID.Busy);\n\n                    // Don't show a modal when we got rejected/the call was hung up\n                    if (!hangupReason || [CallErrorCode.UserHangup, \"user hangup\"].includes(hangupReason)) break;\n\n                    let title: string;\n                    let description: string;\n                    // TODO: We should either do away with these or figure out a copy for each code (expect user_hangup...)\n                    if (call.hangupReason === CallErrorCode.UserBusy) {\n                        title = _t(\"voip|user_busy\");\n                        description = _t(\"voip|user_busy_description\");\n                    } else {\n                        title = _t(\"voip|call_failed\");\n                        description = _t(\"voip|call_failed_description\");\n                    }\n\n                    Modal.createDialog(ErrorDialog, {\n                        title,\n                        description,\n                    });\n                } else if (hangupReason === CallErrorCode.AnsweredElsewhere && oldState === CallState.Connecting) {\n                    Modal.createDialog(ErrorDialog, {\n                        title: _t(\"voip|answered_elsewhere\"),\n                        description: _t(\"voip|answered_elsewhere_description\"),\n                    });\n                } else if (oldState !== CallState.Fledgling && oldState !== CallState.Ringing) {\n                    // don't play the end-call sound for calls that never got off the ground\n                    this.play(AudioID.CallEnd);\n                }\n\n                if (isNotNull(mappedRoomId)) {\n                    this.logCallStats(call, mappedRoomId);\n                }\n                break;\n            }\n        }\n    };\n\n    private async logCallStats(call: MatrixCall, mappedRoomId: string): Promise<void> {\n        const stats = await call.getCurrentCallStats();\n        logger.debug(\n            `Call completed. Call ID: ${call.callId}, virtual room ID: ${call.roomId}, ` +\n                `user-facing room ID: ${mappedRoomId}, direction: ${call.direction}, ` +\n                `our Party ID: ${call.ourPartyId}, hangup party: ${call.hangupParty}, ` +\n                `hangup reason: ${call.hangupReason}`,\n        );\n        if (!stats) {\n            logger.debug(\n                \"Call statistics are undefined. The call has probably failed before a peerConn was established\",\n            );\n            return;\n        }\n        logger.debug(\"Local candidates:\");\n        for (const cand of stats.filter((item) => item.type === \"local-candidate\")) {\n            const address = cand.address || cand.ip; // firefox uses 'address', chrome uses 'ip'\n            logger.debug(\n                `${cand.id} - type: ${cand.candidateType}, address: ${address}, port: ${cand.port}, ` +\n                    `protocol: ${cand.protocol}, relay protocol: ${cand.relayProtocol}, network type: ${cand.networkType}`,\n            );\n        }\n        logger.debug(\"Remote candidates:\");\n        for (const cand of stats.filter((item) => item.type === \"remote-candidate\")) {\n            const address = cand.address || cand.ip; // firefox uses 'address', chrome uses 'ip'\n            logger.debug(\n                `${cand.id} - type: ${cand.candidateType}, address: ${address}, port: ${cand.port}, ` +\n                    `protocol: ${cand.protocol}`,\n            );\n        }\n        logger.debug(\"Candidate pairs:\");\n        for (const pair of stats.filter((item) => item.type === \"candidate-pair\")) {\n            logger.debug(\n                `${pair.localCandidateId} / ${pair.remoteCandidateId} - state: ${pair.state}, ` +\n                    `nominated: ${pair.nominated}, ` +\n                    `requests sent ${pair.requestsSent}, requests received  ${pair.requestsReceived},  ` +\n                    `responses received: ${pair.responsesReceived}, responses sent: ${pair.responsesSent}, ` +\n                    `bytes received: ${pair.bytesReceived}, bytes sent: ${pair.bytesSent}, `,\n            );\n        }\n\n        logger.debug(\"Outbound RTP:\");\n        for (const s of stats.filter((item) => item.type === \"outbound-rtp\")) {\n            logger.debug(s);\n        }\n\n        logger.debug(\"Inbound RTP:\");\n        for (const s of stats.filter((item) => item.type === \"inbound-rtp\")) {\n            logger.debug(s);\n        }\n    }\n\n    private setCallState(call: MatrixCall, status: CallState): void {\n        const mappedRoomId = LegacyCallHandler.instance.roomIdForCall(call);\n\n        logger.log(`Call state in ${mappedRoomId} changed to ${status}`);\n\n        const toastKey = getIncomingLegacyCallToastKey(call.callId);\n        if (status === CallState.Ringing) {\n            ToastStore.sharedInstance().addOrReplaceToast({\n                key: toastKey,\n                priority: 100,\n                component: IncomingLegacyCallToast,\n                bodyClassName: \"mx_IncomingLegacyCallToast\",\n                props: { call },\n            });\n        } else {\n            ToastStore.sharedInstance().dismissToast(toastKey);\n        }\n\n        this.emit(LegacyCallHandlerEvent.CallState, mappedRoomId, status);\n    }\n\n    private removeCallForRoom(roomId: string): void {\n        logger.log(\"Removing call for room \", roomId);\n        this.calls.delete(roomId);\n        this.emit(LegacyCallHandlerEvent.CallsChanged, this.calls);\n    }\n\n    private showICEFallbackPrompt(): void {\n        const cli = MatrixClientPeg.safeGet();\n        const { finished } = Modal.createDialog(\n            QuestionDialog,\n            {\n                title: _t(\"voip|misconfigured_server\"),\n                description: (\n                    <div>\n                        <p>\n                            {_t(\n                                \"voip|misconfigured_server_description\",\n                                { homeserverDomain: cli.getDomain() },\n                                { code: (sub: string) => <code>{sub}</code> },\n                            )}\n                        </p>\n                        <p>\n                            {_t(\"voip|misconfigured_server_fallback\", undefined, {\n                                server: () => <code>{new URL(FALLBACK_ICE_SERVER).pathname}</code>,\n                            })}\n                        </p>\n                    </div>\n                ),\n                button: _t(\"voip|misconfigured_server_fallback_accept\", {\n                    server: new URL(FALLBACK_ICE_SERVER).pathname,\n                }),\n                cancelButton: _t(\"action|ok\"),\n            },\n            undefined,\n            true,\n        );\n\n        finished.then(([allow]) => {\n            SettingsStore.setValue(\"fallbackICEServerAllowed\", null, SettingLevel.DEVICE, allow);\n        });\n    }\n\n    private showMediaCaptureError(call: MatrixCall): void {\n        let title;\n        let description;\n\n        if (call.type === CallType.Voice) {\n            title = _t(\"voip|unable_to_access_microphone\");\n            description = <div>{_t(\"voip|call_failed_microphone\")}</div>;\n        } else if (call.type === CallType.Video) {\n            title = _t(\"voip|unable_to_access_media\");\n            description = (\n                <div>\n                    {_t(\"voip|call_failed_media\")}\n                    <ul>\n                        <li>{_t(\"voip|call_failed_media_connected\")}</li>\n                        <li>{_t(\"voip|call_failed_media_permissions\")}</li>\n                        <li>{_t(\"voip|call_failed_media_applications\")}</li>\n                    </ul>\n                </div>\n            );\n        }\n\n        Modal.createDialog(\n            ErrorDialog,\n            {\n                title,\n                description,\n            },\n            undefined,\n            true,\n        );\n    }\n\n    private async placeMatrixCall(roomId: string, type: CallType, transferee?: MatrixCall): Promise<void> {\n        const cli = MatrixClientPeg.safeGet();\n\n        const timeUntilTurnCresExpire = cli.getTurnServersExpiry() - Date.now();\n        logger.log(\"Current turn creds expire in \" + timeUntilTurnCresExpire + \" ms\");\n        const call = cli.createCall(roomId)!;\n\n        try {\n            this.addCallForRoom(roomId, call);\n        } catch {\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"voip|already_in_call\"),\n                description: _t(\"voip|already_in_call_person\"),\n            });\n            return;\n        }\n        if (transferee) {\n            this.transferees.set(call.callId, transferee);\n        }\n\n        this.setCallListeners(call);\n\n        this.setActiveCallRoomId(roomId);\n\n        if (type === CallType.Voice) {\n            call.placeVoiceCall();\n        } else if (type === \"video\") {\n            call.placeVideoCall();\n        } else {\n            logger.error(\"Unknown conf call type: \" + type);\n        }\n    }\n\n    public async placeCall(roomId: string, type: CallType, transferee?: MatrixCall): Promise<void> {\n        const cli = MatrixClientPeg.safeGet();\n        const room = cli.getRoom(roomId);\n        if (!room) {\n            logger.error(`Room ${roomId} does not exist.`);\n            return;\n        }\n\n        // We might be using managed hybrid widgets\n        if (isManagedHybridWidgetEnabled(room)) {\n            await addManagedHybridWidget(room);\n            return;\n        }\n\n        // if the runtime env doesn't do VoIP, whine.\n        if (!cli.supportsVoip()) {\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"voip|unsupported\"),\n                description: _t(\"voip|unsupported_browser\"),\n            });\n            return;\n        }\n\n        if (cli.getSyncState() === SyncState.Error) {\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"voip|connection_lost\"),\n                description: _t(\"voip|connection_lost_description\"),\n            });\n            return;\n        }\n\n        // don't allow > 2 calls to be placed.\n        if (this.getAllActiveCalls().length > 1) {\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"voip|too_many_calls\"),\n                description: _t(\"voip|too_many_calls_description\"),\n            });\n            return;\n        }\n\n        // We leave the check for whether there's already a call in this room until later,\n        // otherwise it can race.\n\n        const members = getJoinedNonFunctionalMembers(room);\n        if (members.length <= 1) {\n            Modal.createDialog(ErrorDialog, {\n                description: _t(\"voip|cannot_call_yourself_description\"),\n            });\n        } else if (members.length === 2 && !Jitsi.getInstance().useFor1To1Calls) {\n            logger.info(`Place ${type} call in ${roomId}`);\n\n            await this.placeMatrixCall(roomId, type, transferee);\n        } else {\n            // > 2 || useFor1To1Calls\n            await this.placeJitsiCall(roomId, type);\n        }\n    }\n\n    public hangupAllCalls(): void {\n        for (const call of this.calls.values()) {\n            this.stopRingingIfPossible(call.callId);\n            call.hangup(CallErrorCode.UserHangup, false);\n        }\n    }\n\n    public hangupOrReject(roomId: string, reject?: boolean): void {\n        const call = this.calls.get(roomId);\n\n        // no call to hangup\n        if (!call) return;\n\n        this.stopRingingIfPossible(call.callId);\n\n        if (reject) {\n            call.reject();\n        } else {\n            call.hangup(CallErrorCode.UserHangup, false);\n        }\n        // don't remove the call yet: let the hangup event handler do it (otherwise it will throw\n        // the hangup event away)\n    }\n\n    public answerCall(roomId: string): void {\n        // no call to answer\n        if (!this.calls.has(roomId)) return;\n\n        const call = this.calls.get(roomId)!;\n        this.stopRingingIfPossible(call.callId);\n\n        if (this.getAllActiveCalls().length > 1) {\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"voip|too_many_calls\"),\n                description: _t(\"voip|too_many_calls_description\"),\n            });\n            return;\n        }\n\n        call.answer();\n        this.setActiveCallRoomId(roomId);\n        dis.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            room_id: roomId,\n            metricsTrigger: \"WebAcceptCall\",\n        });\n    }\n\n    private stopRingingIfPossible(callId: string): void {\n        this.silencedCalls.delete(callId);\n        if (this.areAnyCallsUnsilenced()) return;\n        this.pause(AudioID.Ring);\n    }\n\n    public async dialNumber(number: string, transferee?: MatrixCall): Promise<void> {\n        const results = await this.pstnLookup(number);\n        if (!results || results.length === 0 || !results[0].userid) {\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"voip|msisdn_lookup_failed\"),\n                description: _t(\"voip|msisdn_lookup_failed_description\"),\n            });\n            return;\n        }\n        const userId = results[0].userid;\n\n        const roomId = await ensureDMExists(MatrixClientPeg.safeGet(), userId);\n        if (!roomId) {\n            throw new Error(\"Failed to ensure DM exists for dialing number\");\n        }\n\n        dis.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            room_id: roomId,\n            metricsTrigger: \"WebDialPad\",\n        });\n\n        await this.placeMatrixCall(roomId, CallType.Voice, transferee);\n    }\n\n    public async startTransferToPhoneNumber(\n        call: MatrixCall,\n        destination: string,\n        consultFirst: boolean,\n    ): Promise<void> {\n        if (consultFirst) {\n            // if we're consulting, we just start by placing a call to the transfer\n            // target (passing the transferee so the actual transfer can happen later)\n            this.dialNumber(destination, call);\n            return;\n        }\n\n        const results = await this.pstnLookup(destination);\n        if (!results || results.length === 0 || !results[0].userid) {\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"voip|msisdn_transfer_failed\"),\n                description: _t(\"voip|msisdn_lookup_failed_description\"),\n            });\n            return;\n        }\n\n        await this.startTransferToMatrixID(call, results[0].userid, consultFirst);\n    }\n\n    public async startTransferToMatrixID(call: MatrixCall, destination: string, consultFirst: boolean): Promise<void> {\n        if (consultFirst) {\n            const dmRoomId = await ensureDMExists(MatrixClientPeg.safeGet(), destination);\n            if (!dmRoomId) {\n                logger.log(\"Failed to transfer call, could not ensure dm exists\");\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"voip|transfer_failed\"),\n                    description: _t(\"voip|transfer_failed_description\"),\n                });\n                return;\n            }\n\n            this.placeCall(dmRoomId, call.type, call);\n            dis.dispatch<ViewRoomPayload>({\n                action: Action.ViewRoom,\n                room_id: dmRoomId,\n                should_peek: false,\n                joining: false,\n                metricsTrigger: undefined, // other\n            });\n        } else {\n            try {\n                await call.transfer(destination);\n            } catch (e) {\n                logger.log(\"Failed to transfer call\", e);\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"voip|transfer_failed\"),\n                    description: _t(\"voip|transfer_failed_description\"),\n                });\n            }\n        }\n    }\n\n    public setActiveCallRoomId(activeCallRoomId: string): void {\n        logger.info(\"Setting call in room \" + activeCallRoomId + \" active\");\n\n        for (const [roomId, call] of this.calls.entries()) {\n            if (call.state === CallState.Ended) continue;\n\n            if (roomId === activeCallRoomId) {\n                call.setRemoteOnHold(false);\n            } else {\n                logger.info(\"Holding call in room \" + roomId + \" because another call is being set active\");\n                call.setRemoteOnHold(true);\n            }\n        }\n    }\n\n    /**\n     * @returns true if we are currently in any call where we haven't put the remote party on hold\n     */\n    public hasAnyUnheldCall(): boolean {\n        for (const call of this.calls.values()) {\n            if (call.state === CallState.Ended) continue;\n            if (!call.isRemoteOnHold()) return true;\n        }\n\n        return false;\n    }\n\n    private async placeJitsiCall(roomId: string, type: CallType): Promise<void> {\n        const client = MatrixClientPeg.safeGet();\n        logger.info(`Place conference call in ${roomId}`);\n\n        dis.dispatch({ action: \"appsDrawer\", show: true });\n\n        // Prevent double clicking the call button\n        const widget = WidgetStore.instance.getApps(roomId).find((app) => WidgetType.JITSI.matches(app.type));\n        if (widget) {\n            // If there already is a Jitsi widget, pin it\n            const room = client.getRoom(roomId);\n            if (isNotNull(room)) {\n                WidgetLayoutStore.instance.moveToContainer(room, widget, Container.Top);\n            }\n            return;\n        }\n\n        try {\n            await WidgetUtils.addJitsiWidget(client, roomId, type, \"Jitsi\", false);\n            logger.log(\"Jitsi widget added\");\n        } catch (e) {\n            if (e instanceof MatrixError && e.errcode === \"M_FORBIDDEN\") {\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"voip|no_permission_conference\"),\n                    description: _t(\"voip|no_permission_conference_description\"),\n                });\n            }\n            logger.error(e);\n        }\n    }\n\n    public hangupCallApp(roomId: string): void {\n        logger.info(\"Leaving conference call in \" + roomId);\n\n        const roomInfo = WidgetStore.instance.getRoom(roomId);\n        if (!roomInfo) return; // \"should never happen\" clauses go here\n\n        const jitsiWidgets = roomInfo.widgets.filter((w) => WidgetType.JITSI.matches(w.type));\n        jitsiWidgets.forEach((w) => {\n            const messaging = WidgetMessagingStore.instance.getMessagingForUid(WidgetUtils.getWidgetUid(w));\n            if (!messaging?.widgetApi) return; // more \"should never happen\" words\n\n            messaging.widgetApi.transport.send(ElementWidgetActions.HangupCall, {});\n        });\n    }\n\n    /*\n     * Shows the transfer dialog for a call, signalling to the other end that\n     * a transfer is about to happen\n     */\n    public showTransferDialog(call: MatrixCall): void {\n        call.setRemoteOnHold(true);\n        dis.dispatch<OpenInviteDialogPayload>({\n            action: Action.OpenInviteDialog,\n            kind: InviteKind.CallTransfer,\n            call,\n            analyticsName: \"Transfer Call\",\n            className: \"mx_InviteDialog_transferWrapper\",\n            onFinishedCallback: (results) => {\n                if (results.length === 0 || results[0] === false) {\n                    call.setRemoteOnHold(false);\n                }\n            },\n        });\n    }\n\n    private addCallForRoom(roomId: string, call: MatrixCall, changedRooms = false): void {\n        if (this.calls.has(roomId)) {\n            logger.log(`Couldn't add call to room ${roomId}: already have a call for this room`);\n            throw new Error(\"Already have a call for room \" + roomId);\n        }\n\n        logger.log(\"setting call for room \" + roomId);\n        this.calls.set(roomId, call);\n\n        // Should we always emit CallsChanged too?\n        if (changedRooms) {\n            this.emit(LegacyCallHandlerEvent.CallChangeRoom, call);\n        } else {\n            this.emit(LegacyCallHandlerEvent.CallsChanged, this.calls);\n        }\n    }\n}\n","/*\nCopyright 2024, 2025 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactElement } from \"react\";\nimport sanitizeHtml, { type IOptions } from \"sanitize-html\";\nimport { merge } from \"lodash\";\nimport _Linkify from \"linkify-react\";\n\nimport { _linkifyString, _linkifyHtml, ELEMENT_URL_PATTERN, options as linkifyMatrixOptions } from \"./linkify-matrix\";\nimport { tryTransformPermalinkToLocalHref } from \"./utils/permalinks/Permalinks\";\nimport { mediaFromMxc } from \"./customisations/Media\";\nimport { PERMITTED_URL_SCHEMES } from \"./utils/UrlUtils\";\n\nconst COLOR_REGEX = /^#[0-9a-fA-F]{6}$/;\nconst MEDIA_API_MXC_REGEX = /\\/_matrix\\/media\\/r0\\/(?:download|thumbnail)\\/(.+?)\\/(.+?)(?:[?/]|$)/;\n\nexport const transformTags: NonNullable<IOptions[\"transformTags\"]> = {\n    // custom to matrix\n    // add blank targets to all hyperlinks except vector URLs\n    \"a\": function (tagName: string, attribs: sanitizeHtml.Attributes) {\n        if (attribs.href) {\n            attribs.target = \"_blank\"; // by default\n\n            const transformed = tryTransformPermalinkToLocalHref(attribs.href); // only used to check if it is a link that can be handled locally\n            if (\n                transformed !== attribs.href || // it could be converted so handle locally symbols e.g. @user:server.tdl, matrix: and matrix.to\n                attribs.href.match(ELEMENT_URL_PATTERN) // for https links to Element domains\n            ) {\n                delete attribs.target;\n            }\n        } else {\n            // Delete the href attrib if it is falsy\n            delete attribs.href;\n        }\n\n        attribs.rel = \"noreferrer noopener\"; // https://mathiasbynens.github.io/rel-noopener/\n        return { tagName, attribs };\n    },\n    \"img\": function (tagName: string, attribs: sanitizeHtml.Attributes) {\n        let src = attribs.src;\n        // Strip out imgs that aren't `mxc` here instead of using allowedSchemesByTag\n        // because transformTags is used _before_ we filter by allowedSchemesByTag and\n        // we don't want to allow images with `https?` `src`s.\n        if (!src) {\n            return { tagName, attribs: {} };\n        }\n\n        if (!src.startsWith(\"mxc://\")) {\n            const match = MEDIA_API_MXC_REGEX.exec(src);\n            if (match) {\n                src = `mxc://${match[1]}/${match[2]}`;\n            }\n        }\n\n        if (!src.startsWith(\"mxc://\")) {\n            return { tagName, attribs: {} };\n        }\n\n        const requestedWidth = Number(attribs.width);\n        const requestedHeight = Number(attribs.height);\n        const width = Math.min(requestedWidth || 800, 800);\n        const height = Math.min(requestedHeight || 600, 600);\n        // specify width/height as max values instead of absolute ones to allow object-fit to do its thing\n        // we only allow our own styles for this tag so overwrite the attribute\n        attribs.style = `max-width: ${width}px; max-height: ${height}px;`;\n        if (requestedWidth) {\n            attribs.style += \"width: 100%;\";\n        }\n        if (requestedHeight) {\n            attribs.style += \"height: 100%;\";\n        }\n        attribs.src = mediaFromMxc(src).getThumbnailOfSourceHttp(width, height)!;\n        return { tagName, attribs };\n    },\n    \"code\": function (tagName: string, attribs: sanitizeHtml.Attributes) {\n        if (typeof attribs.class !== \"undefined\") {\n            // Filter out all classes other than ones starting with language- for syntax highlighting.\n            const classes = attribs.class.split(/\\s/).filter(function (cl) {\n                return cl.startsWith(\"language-\") && !cl.startsWith(\"language-_\");\n            });\n            attribs.class = classes.join(\" \");\n        }\n        return { tagName, attribs };\n    },\n    // eslint-disable-next-line @typescript-eslint/naming-convention\n    \"*\": function (tagName: string, attribs: sanitizeHtml.Attributes) {\n        // Delete any style previously assigned, style is an allowedTag for font, span & img,\n        // because attributes are stripped after transforming.\n        // For img this is trusted as it is generated wholly within the img transformation method.\n        if (tagName !== \"img\") {\n            delete attribs.style;\n        }\n\n        // Sanitise and transform data-mx-color and data-mx-bg-color to their CSS\n        // equivalents\n        const customCSSMapper: Record<string, string> = {\n            \"data-mx-color\": \"color\",\n            \"data-mx-bg-color\": \"background-color\",\n            // $customAttributeKey: $cssAttributeKey\n        };\n\n        let style = \"\";\n        Object.keys(customCSSMapper).forEach((customAttributeKey) => {\n            const cssAttributeKey = customCSSMapper[customAttributeKey];\n            const customAttributeValue = attribs[customAttributeKey];\n            if (\n                customAttributeValue &&\n                typeof customAttributeValue === \"string\" &&\n                COLOR_REGEX.test(customAttributeValue)\n            ) {\n                style += cssAttributeKey + \":\" + customAttributeValue + \";\";\n                delete attribs[customAttributeKey];\n            }\n        });\n\n        if (style) {\n            attribs.style = style + (attribs.style || \"\");\n        }\n\n        return { tagName, attribs };\n    },\n};\n\nexport const sanitizeHtmlParams: IOptions = {\n    allowedTags: [\n        // These tags are suggested by the spec https://spec.matrix.org/v1.10/client-server-api/#mroommessage-msgtypes\n        \"font\", // custom to matrix for IRC-style font coloring\n        \"del\", // for markdown\n        \"s\",\n        \"h1\",\n        \"h2\",\n        \"h3\",\n        \"h4\",\n        \"h5\",\n        \"h6\",\n        \"blockquote\",\n        \"p\",\n        \"a\",\n        \"ul\",\n        \"ol\",\n        \"sup\",\n        \"sub\",\n        \"nl\",\n        \"li\",\n        \"b\",\n        \"i\",\n        \"u\",\n        \"strong\",\n        \"em\",\n        \"strike\",\n        \"code\",\n        \"hr\",\n        \"br\",\n        \"div\",\n        \"table\",\n        \"thead\",\n        \"caption\",\n        \"tbody\",\n        \"tr\",\n        \"th\",\n        \"td\",\n        \"pre\",\n        \"span\",\n        \"img\",\n        \"details\",\n        \"summary\",\n    ],\n    allowedAttributes: {\n        // attribute sanitization happens after transformations, so we have to accept `style` for font, span & img\n        // but strip during the transformation.\n        // custom ones first:\n        font: [\"color\", \"data-mx-bg-color\", \"data-mx-color\", \"style\"], // custom to matrix\n        span: [\"data-mx-maths\", \"data-mx-bg-color\", \"data-mx-color\", \"data-mx-spoiler\", \"style\"], // custom to matrix\n        div: [\"data-mx-maths\"],\n        a: [\"href\", \"name\", \"target\", \"rel\"], // remote target: custom to matrix\n        // img tags also accept width/height, we just map those to max-width & max-height during transformation\n        img: [\"src\", \"alt\", \"title\", \"style\"],\n        ol: [\"start\"],\n        code: [\"class\"], // We don't actually allow all classes, we filter them in transformTags\n    },\n    // Lots of these won't come up by default because we don't allow them\n    selfClosing: [\"img\", \"br\", \"hr\", \"area\", \"base\", \"basefont\", \"input\", \"link\", \"meta\"],\n    // URL schemes we permit\n    allowedSchemes: PERMITTED_URL_SCHEMES,\n    allowProtocolRelative: false,\n    transformTags,\n    // 50 levels deep \"should be enough for anyone\"\n    nestingLimit: 50,\n};\n\n/* Wrapper around linkify-react merging in our default linkify options */\nexport function Linkify({ as, options, children }: React.ComponentProps<typeof _Linkify>): ReactElement {\n    return (\n        <_Linkify as={as} options={merge({}, linkifyMatrixOptions, options)}>\n            {children}\n        </_Linkify>\n    );\n}\n\n/**\n * Linkifies the given string. This is a wrapper around 'linkifyjs/string'.\n *\n * @param {string} str string to linkify\n * @param {object} [options] Options for linkifyString. Default: linkifyMatrixOptions\n * @returns {string} Linkified string\n */\nexport function linkifyString(str: string, options = linkifyMatrixOptions): string {\n    return _linkifyString(str, options);\n}\n\n/**\n * Linkifies the given HTML-formatted string. This is a wrapper around 'linkifyjs/html'.\n *\n * @param {string} str HTML string to linkify\n * @param {object} [options] Options for linkifyHtml. Default: linkifyMatrixOptions\n * @returns {string} Linkified string\n */\nexport function linkifyHtml(str: string, options = linkifyMatrixOptions): string {\n    return _linkifyHtml(str, options);\n}\n/**\n * Linkify the given string and sanitize the HTML afterwards.\n *\n * @param {string} dirtyHtml The HTML string to sanitize and linkify\n * @param {object} [options] Options for linkifyString. Default: linkifyMatrixOptions\n * @returns {string}\n */\nexport function linkifyAndSanitizeHtml(dirtyHtml: string, options = linkifyMatrixOptions): string {\n    return sanitizeHtml(linkifyString(dirtyHtml, options), sanitizeHtmlParams);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport \"./@types/commonmark\"; // import better types than @types/commonmark\nimport * as commonmark from \"commonmark\";\nimport { escape } from \"lodash\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { linkify } from \"./linkify-matrix\";\n\nconst ALLOWED_HTML_TAGS = [\"sub\", \"sup\", \"del\", \"s\", \"u\", \"br\", \"br/\"];\n\n// These types of node are definitely text\nconst TEXT_NODES = [\"text\", \"softbreak\", \"linebreak\", \"paragraph\", \"document\"];\n\nfunction isAllowedHtmlTag(node: commonmark.Node): boolean {\n    if (!node.literal) {\n        return false;\n    }\n\n    if (node.literal.match('^<((div|span) data-mx-maths=\"[^\"]*\"|/(div|span))>$') != null) {\n        return true;\n    }\n\n    // Regex won't work for tags with attrs, but the tags we allow\n    // shouldn't really have any anyway.\n    const matches = /^<\\/?(.*)>$/.exec(node.literal);\n    if (matches && matches.length == 2) {\n        const tag = matches[1];\n        return ALLOWED_HTML_TAGS.indexOf(tag) > -1;\n    }\n\n    return false;\n}\n\n/*\n * Returns true if the parse output containing the node\n * comprises multiple block level elements (ie. lines),\n * or false if it is only a single line.\n */\nfunction isMultiLine(node: commonmark.Node): boolean {\n    let par = node;\n    while (par.parent) {\n        par = par.parent;\n    }\n    return par.firstChild != par.lastChild;\n}\n\nfunction getTextUntilEndOrLinebreak(node: commonmark.Node): string {\n    let currentNode: commonmark.Node | null = node;\n    let text = \"\";\n    while (currentNode && currentNode.type !== \"softbreak\" && currentNode.type !== \"linebreak\") {\n        const { literal, type } = currentNode;\n        if (type === \"text\" && literal) {\n            let n = 0;\n            let char = literal[n];\n            while (char !== \" \" && char !== null && n <= literal.length) {\n                if (char === \" \") {\n                    break;\n                }\n                if (char) {\n                    text += char;\n                }\n                n += 1;\n                char = literal[n];\n            }\n            if (char === \" \") {\n                break;\n            }\n        }\n        currentNode = currentNode.next;\n    }\n    return text;\n}\n\nconst formattingChangesByNodeType = {\n    emph: \"_\",\n    strong: \"__\",\n};\n\n/**\n * Returns the literal of a node an all child nodes.\n */\nconst innerNodeLiteral = (node: commonmark.Node): string => {\n    let literal = \"\";\n\n    const walker = node.walker();\n    let step: commonmark.NodeWalkingStep | null;\n\n    while ((step = walker.next())) {\n        const currentNode = step.node;\n        const currentNodeLiteral = currentNode.literal;\n        if (step.entering && currentNode.type === \"text\" && currentNodeLiteral) {\n            literal += currentNodeLiteral;\n        }\n    }\n\n    return literal;\n};\n\nconst emptyItemWithNoSiblings = (node: commonmark.Node): boolean => {\n    return !node.prev && !node.next && !node.firstChild;\n};\n\n/**\n * Class that wraps commonmark, adding the ability to see whether\n * a given message actually uses any markdown syntax or whether\n * it's plain text.\n */\nexport default class Markdown {\n    private input: string;\n    private parsed: commonmark.Node;\n\n    public constructor(input: string) {\n        this.input = input;\n\n        const parser = new commonmark.Parser();\n        this.parsed = parser.parse(this.input);\n        this.parsed = this.repairLinks(this.parsed);\n    }\n\n    /**\n     * This method is modifying the parsed AST in such a way that links are always\n     * properly linkified instead of sometimes being wrongly emphasised in case\n     * if you were to write a link like the example below:\n     * https://my_weird-link_domain.domain.com\n     * ^ this link would be parsed to something like this:\n     * <a href=\"https://my\">https://my</a><b>weird-link</b><a href=\"https://domain.domain.com\">domain.domain.com</a>\n     * This method makes it so the link gets properly modified to a version where it is\n     * not emphasised until it actually ends.\n     * See: https://github.com/vector-im/element-web/issues/4674\n     * @param parsed\n     */\n    private repairLinks(parsed: commonmark.Node): commonmark.Node {\n        const walker = parsed.walker();\n        let event: commonmark.NodeWalkingStep | null = null;\n        let text = \"\";\n        let isInPara = false;\n        let previousNode: commonmark.Node | null = null;\n        let shouldUnlinkFormattingNode = false;\n        while ((event = walker.next())) {\n            const { node } = event;\n            if (node.type === \"paragraph\") {\n                if (event.entering) {\n                    isInPara = true;\n                } else {\n                    isInPara = false;\n                }\n            }\n            if (isInPara) {\n                // Clear saved string when line ends\n                if (\n                    node.type === \"softbreak\" ||\n                    node.type === \"linebreak\" ||\n                    // Also start calculating the text from the beginning on any spaces\n                    (node.type === \"text\" && node.literal === \" \")\n                ) {\n                    text = \"\";\n                    continue;\n                }\n\n                // Break up text nodes on spaces, so that we don't shoot past them without resetting\n                if (node.type === \"text\" && node.literal) {\n                    const [thisPart, ...nextParts] = node.literal.split(/( )/);\n                    node.literal = thisPart;\n                    text += thisPart;\n\n                    // Add the remaining parts as siblings\n                    nextParts.reverse().forEach((part) => {\n                        if (part) {\n                            const nextNode = new commonmark.Node(\"text\");\n                            nextNode.literal = part;\n                            node.insertAfter(nextNode);\n                            // Make the iterator aware of the newly inserted node\n                            walker.resumeAt(nextNode, true);\n                        }\n                    });\n                }\n\n                // We should not do this if previous node was not a textnode, as we can't combine it then.\n                if ((node.type === \"emph\" || node.type === \"strong\") && previousNode?.type === \"text\") {\n                    if (event.entering) {\n                        const foundLinks = linkify.find(text);\n                        for (const { value } of foundLinks) {\n                            if (node?.firstChild?.literal) {\n                                /**\n                                 * NOTE: This technically should unlink the emph node and create LINK nodes instead, adding all the next elements as siblings\n                                 * but this solution seems to work well and is hopefully slightly easier to understand too\n                                 */\n                                const format = formattingChangesByNodeType[node.type];\n                                const nonEmphasizedText = `${format}${innerNodeLiteral(node)}${format}`;\n                                const f = getTextUntilEndOrLinebreak(node);\n                                const newText = value + nonEmphasizedText + f;\n                                const newLinks = linkify.find(newText);\n                                // Should always find only one link here, if it finds more it means that the algorithm is broken\n                                if (newLinks.length === 1) {\n                                    const emphasisTextNode = new commonmark.Node(\"text\");\n                                    emphasisTextNode.literal = nonEmphasizedText;\n                                    previousNode.insertAfter(emphasisTextNode);\n                                    node.firstChild.literal = \"\";\n                                    event = node.walker().next();\n                                    if (event) {\n                                        // Remove `em` opening and closing nodes\n                                        node.unlink();\n                                        previousNode.insertAfter(event.node);\n                                        shouldUnlinkFormattingNode = true;\n                                    }\n                                } else {\n                                    logger.error(\n                                        \"Markdown links escaping found too many links for following text: \",\n                                        text,\n                                    );\n                                    logger.error(\n                                        \"Markdown links escaping found too many links for modified text: \",\n                                        newText,\n                                    );\n                                }\n                            }\n                        }\n                    } else {\n                        if (shouldUnlinkFormattingNode) {\n                            node.unlink();\n                            shouldUnlinkFormattingNode = false;\n                        }\n                    }\n                }\n            }\n            previousNode = node;\n        }\n        return parsed;\n    }\n\n    public isPlainText(): boolean {\n        const walker = this.parsed.walker();\n        let ev: commonmark.NodeWalkingStep | null;\n\n        while ((ev = walker.next())) {\n            const node = ev.node;\n\n            if (TEXT_NODES.indexOf(node.type) > -1) {\n                // definitely text\n                continue;\n            } else if (node.type == \"list\" || node.type == \"item\") {\n                // Special handling for inputs like `+`, `*`, `-` and `2021.` which\n                // would otherwise be treated as a list of a single empty item.\n                // See https://github.com/vector-im/element-web/issues/7631\n                if (node.type == \"list\" && node.firstChild && emptyItemWithNoSiblings(node.firstChild)) {\n                    // A list with a single empty item is treated as plain text.\n                    continue;\n                }\n\n                if (node.type == \"item\" && emptyItemWithNoSiblings(node)) {\n                    // An empty list item with no sibling items is treated as plain text.\n                    continue;\n                }\n\n                // Everything else is actual lists and therefore not plaintext.\n                return false;\n            } else if (node.type == \"html_inline\" || node.type == \"html_block\") {\n                // if it's an allowed html tag, we need to render it and therefore\n                // we will need to use HTML. If it's not allowed, it's not HTML since\n                // we'll just be treating it as text.\n                if (isAllowedHtmlTag(node)) {\n                    return false;\n                }\n            } else {\n                return false;\n            }\n        }\n        return true;\n    }\n\n    public toHTML({ externalLinks = false } = {}): string {\n        const renderer = new commonmark.HtmlRenderer({\n            safe: false,\n\n            // Set soft breaks to hard HTML breaks: commonmark\n            // puts softbreaks in for multiple lines in a blockquote,\n            // so if these are just newline characters then the\n            // block quote ends up all on one line\n            // (https://github.com/vector-im/element-web/issues/3154)\n            softbreak: \"<br />\",\n        });\n\n        // Trying to strip out the wrapping <p/> causes a lot more complication\n        // than it's worth, i think.  For instance, this code will go and strip\n        // out any <p/> tag (no matter where it is in the tree) which doesn't\n        // contain \\n's.\n        // On the flip side, <p/>s are quite opionated and restricted on where\n        // you can nest them.\n        //\n        // Let's try sending with <p/>s anyway for now, though.\n        const realParagraph = renderer.paragraph;\n        renderer.paragraph = function (node: commonmark.Node, entering: boolean) {\n            // If there is only one top level node, just return the\n            // bare text: it's a single line of text and so should be\n            // 'inline', rather than unnecessarily wrapped in its own\n            // p tag. If, however, we have multiple nodes, each gets\n            // its own p tag to keep them as separate paragraphs.\n            // However, if it's a blockquote, adds a p tag anyway\n            // in order to avoid deviation to commonmark and unexpected\n            // results when parsing the formatted HTML.\n            if (node.parent?.type === \"block_quote\" || isMultiLine(node)) {\n                realParagraph.call(this, node, entering);\n            }\n        };\n\n        renderer.link = function (node, entering) {\n            const attrs = this.attrs(node);\n            if (entering && node.destination) {\n                attrs.push([\"href\", this.esc(node.destination)]);\n                if (node.title) {\n                    attrs.push([\"title\", this.esc(node.title)]);\n                }\n                // Modified link behaviour to treat them all as external and\n                // thus opening in a new tab.\n                if (externalLinks) {\n                    attrs.push([\"target\", \"_blank\"]);\n                    attrs.push([\"rel\", \"noreferrer noopener\"]);\n                }\n                this.tag(\"a\", attrs);\n            } else {\n                this.tag(\"/a\");\n            }\n        };\n\n        renderer.html_inline = function (node: commonmark.Node) {\n            if (node.literal) {\n                if (isAllowedHtmlTag(node)) {\n                    this.lit(node.literal);\n                } else {\n                    this.lit(escape(node.literal));\n                }\n            }\n        };\n\n        renderer.html_block = function (node: commonmark.Node) {\n            /*\n            // as with `paragraph`, we only insert line breaks\n            // if there are multiple lines in the markdown.\n            const isMultiLine = is_multi_line(node);\n            if (isMultiLine) this.cr();\n            */\n            renderer.html_inline(node);\n            /*\n            if (isMultiLine) this.cr();\n            */\n        };\n\n        return renderer.render(this.parsed);\n    }\n\n    /*\n     * Render the markdown message to plain text. That is, essentially\n     * just remove any backslashes escaping what would otherwise be\n     * markdown syntax\n     * (to fix https://github.com/vector-im/element-web/issues/2870).\n     *\n     * N.B. this does **NOT** render arbitrary MD to plain text - only MD\n     * which has no formatting.  Otherwise it emits HTML(!).\n     */\n    public toPlaintext(): string {\n        const renderer = new commonmark.HtmlRenderer({ safe: false });\n\n        renderer.paragraph = function (node: commonmark.Node, entering: boolean) {\n            // as with toHTML, only append lines to paragraphs if there are\n            // multiple paragraphs\n            if (isMultiLine(node)) {\n                if (!entering && node.next) {\n                    this.lit(\"\\n\\n\");\n                }\n            }\n        };\n\n        renderer.html_block = function (node: commonmark.Node) {\n            if (node.literal) this.lit(node.literal);\n            if (isMultiLine(node) && node.next) this.lit(\"\\n\\n\");\n        };\n\n        // We inhibit the default escape function as we escape the entire output string to correctly handle backslashes\n        renderer.esc = (input: string) => input;\n\n        return escape(renderer.render(this.parsed));\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    ClientEvent,\n    type MatrixClient,\n    type MatrixEvent,\n    MatrixEventEvent,\n    type Room,\n    RoomEvent,\n    type IRoomTimelineData,\n    type RoomState,\n    RoomStateEvent,\n} from \"matrix-js-sdk/src/matrix\";\n\nimport dis from \"../dispatcher/dispatcher\";\nimport { type ActionPayload } from \"../dispatcher/payloads\";\n\n/**\n * Create a MatrixActions.sync action that represents a MatrixClient `sync` event,\n * each parameter mapping to a key-value in the action.\n *\n * @param {MatrixClient} matrixClient the matrix client\n * @param {string} state the current sync state.\n * @param {string} prevState the previous sync state.\n * @returns {Object} an action of type MatrixActions.sync.\n */\nfunction createSyncAction(matrixClient: MatrixClient, state: string, prevState: string): ActionPayload {\n    return {\n        action: \"MatrixActions.sync\",\n        state,\n        prevState,\n        matrixClient,\n    };\n}\n\n/**\n * @typedef AccountDataAction\n * @type {Object}\n * @property {string} action 'MatrixActions.accountData'.\n * @property {MatrixEvent} event the MatrixEvent that triggered the dispatch.\n * @property {string} event_type the type of the MatrixEvent, e.g. \"m.direct\".\n * @property {Object} event_content the content of the MatrixEvent.\n * @property {MatrixEvent} previousEvent the previous account data event of the same type, if present\n */\n\n/**\n * Create a MatrixActions.accountData action that represents a MatrixClient `accountData`\n * matrix event.\n *\n * @param {MatrixClient} matrixClient the matrix client.\n * @param {MatrixEvent} accountDataEvent the account data event.\n * @param {MatrixEvent | undefined} previousAccountDataEvent the previous account data event of the same type, if present\n * @returns {AccountDataAction} an action of type MatrixActions.accountData.\n */\nfunction createAccountDataAction(\n    matrixClient: MatrixClient,\n    accountDataEvent: MatrixEvent,\n    previousAccountDataEvent?: MatrixEvent,\n): ActionPayload {\n    return {\n        action: \"MatrixActions.accountData\",\n        event: accountDataEvent,\n        event_type: accountDataEvent.getType(),\n        event_content: accountDataEvent.getContent(),\n        previousEvent: previousAccountDataEvent,\n    };\n}\n\n/**\n * @typedef RoomAccountDataAction\n * @type {Object}\n * @property {string} action 'MatrixActions.Room.accountData'.\n * @property {MatrixEvent} event the MatrixEvent that triggered the dispatch.\n * @property {string} event_type the type of the MatrixEvent, e.g. \"m.direct\".\n * @property {Object} event_content the content of the MatrixEvent.\n * @property {Room} room the room where the account data was changed.\n */\n\n/**\n * Create a MatrixActions.Room.accountData action that represents a MatrixClient `Room.accountData`\n * matrix event.\n *\n * @param {MatrixClient} matrixClient the matrix client.\n * @param {MatrixEvent} accountDataEvent the account data event.\n * @param {Room} room the room where account data was changed\n * @returns {RoomAccountDataAction} an action of type MatrixActions.Room.accountData.\n */\nfunction createRoomAccountDataAction(\n    matrixClient: MatrixClient,\n    accountDataEvent: MatrixEvent,\n    room: Room,\n): ActionPayload {\n    return {\n        action: \"MatrixActions.Room.accountData\",\n        event: accountDataEvent,\n        event_type: accountDataEvent.getType(),\n        event_content: accountDataEvent.getContent(),\n        room: room,\n    };\n}\n\n/**\n * @typedef RoomAction\n * @type {Object}\n * @property {string} action 'MatrixActions.Room'.\n * @property {Room} room the Room that was stored.\n */\n\n/**\n * Create a MatrixActions.Room action that represents a MatrixClient `Room`\n * matrix event, emitted when a Room is stored in the client.\n *\n * @param {MatrixClient} matrixClient the matrix client.\n * @param {Room} room the Room that was stored.\n * @returns {RoomAction} an action of type `MatrixActions.Room`.\n */\nfunction createRoomAction(matrixClient: MatrixClient, room: Room): ActionPayload {\n    return { action: \"MatrixActions.Room\", room };\n}\n\n/**\n * @typedef RoomTagsAction\n * @type {Object}\n * @property {string} action 'MatrixActions.Room.tags'.\n * @property {Room} room the Room whose tags changed.\n */\n\n/**\n * Create a MatrixActions.Room.tags action that represents a MatrixClient\n * `Room.tags` matrix event, emitted when the m.tag room account data\n * event is updated.\n *\n * @param {MatrixClient} matrixClient the matrix client.\n * @param {MatrixEvent} roomTagsEvent the m.tag event.\n * @param {Room} room the Room whose tags were changed.\n * @returns {RoomTagsAction} an action of type `MatrixActions.Room.tags`.\n */\nfunction createRoomTagsAction(matrixClient: MatrixClient, roomTagsEvent: MatrixEvent, room: Room): ActionPayload {\n    return { action: \"MatrixActions.Room.tags\", room };\n}\n\n/**\n * Create a MatrixActions.Room.receipt action that represents a MatrixClient\n * `Room.receipt` event, each parameter mapping to a key-value in the action.\n *\n * @param {MatrixClient} matrixClient the matrix client\n * @param {MatrixEvent} event the receipt event.\n * @param {Room} room the room the receipt happened in.\n * @returns {Object} an action of type MatrixActions.Room.receipt.\n */\nfunction createRoomReceiptAction(matrixClient: MatrixClient, event: MatrixEvent, room: Room): ActionPayload {\n    return {\n        action: \"MatrixActions.Room.receipt\",\n        event,\n        room,\n        matrixClient,\n    };\n}\n\n/**\n * @typedef IRoomTimelineActionPayload\n * @type {Object}\n * @property {string} action 'MatrixActions.Room.timeline'.\n * @property {boolean} isLiveEvent whether the event was attached to a\n * live timeline.\n * @property {boolean} isLiveUnfilteredRoomTimelineEvent whether the\n * event was attached to a timeline in the set of unfiltered timelines.\n * @property {Room} room the Room whose tags changed.\n */\nexport interface IRoomTimelineActionPayload extends Pick<ActionPayload, \"action\"> {\n    action: \"MatrixActions.Room.timeline\";\n    event: MatrixEvent;\n    room: Room | null;\n    isLiveEvent?: boolean;\n    isLiveUnfilteredRoomTimelineEvent: boolean;\n}\n\n/**\n * @typedef IRoomStateEventsActionPayload\n * @type {Object}\n * @property {string} action 'MatrixActions.RoomState.events'.\n * @property {MatrixEvent} event the state event received\n * @property {RoomState} state the room state into which the event was applied\n * @property {MatrixEvent | null} lastStateEvent the previous value for this (event-type, state-key) tuple in room state\n */\nexport interface IRoomStateEventsActionPayload extends Pick<ActionPayload, \"action\"> {\n    action: \"MatrixActions.RoomState.events\";\n    event: MatrixEvent;\n    state: RoomState;\n    lastStateEvent: MatrixEvent | null;\n}\n\n/**\n * Create a MatrixActions.Room.timeline action that represents a\n * MatrixClient `Room.timeline` matrix event, emitted when an event\n * is added to or removed from a timeline of a room.\n *\n * @param {MatrixClient} matrixClient the matrix client.\n * @param {MatrixEvent} timelineEvent the event that was added/removed.\n * @param {?Room} room the Room that was stored.\n * @param {boolean} toStartOfTimeline whether the event is being added\n * to the start (and not the end) of the timeline.\n * @param {boolean} removed whether the event was removed from the\n * timeline.\n * @param {Object} data\n * @param {boolean} data.liveEvent whether the event is a live event,\n * belonging to a live timeline.\n * @param {EventTimeline} data.timeline the timeline being altered.\n * @returns {IRoomTimelineActionPayload} an action of type `MatrixActions.Room.timeline`.\n */\nfunction createRoomTimelineAction(\n    matrixClient: MatrixClient,\n    timelineEvent: MatrixEvent,\n    room: Room | null,\n    toStartOfTimeline: boolean,\n    removed: boolean,\n    data: IRoomTimelineData,\n): IRoomTimelineActionPayload {\n    return {\n        action: \"MatrixActions.Room.timeline\",\n        event: timelineEvent,\n        isLiveEvent: data.liveEvent,\n        isLiveUnfilteredRoomTimelineEvent: data.timeline.getTimelineSet() === room?.getUnfilteredTimelineSet(),\n        room,\n    };\n}\n\n/**\n * Create a MatrixActions.Room.timeline action that represents a\n * MatrixClient `Room.timeline` matrix event, emitted when an event\n * is added to or removed from a timeline of a room.\n *\n * @param {MatrixClient} matrixClient the matrix client.\n * @param {MatrixEvent} event the state event received\n * @param {RoomState} state the room state into which the event was applied\n * @param {MatrixEvent | null} lastStateEvent the previous value for this (event-type, state-key) tuple in room state\n * @returns {IRoomStateEventsActionPayload} an action of type `MatrixActions.RoomState.events`.\n */\nfunction createRoomStateEventsAction(\n    matrixClient: MatrixClient,\n    event: MatrixEvent,\n    state: RoomState,\n    lastStateEvent: MatrixEvent | null,\n): IRoomStateEventsActionPayload {\n    return {\n        action: \"MatrixActions.RoomState.events\",\n        event,\n        state,\n        lastStateEvent,\n    };\n}\n\n/**\n * @typedef RoomMembershipAction\n * @type {Object}\n * @property {string} action 'MatrixActions.Room.myMembership'.\n * @property {Room} room to room for which the self-membership changed.\n * @property {string} membership the new membership\n * @property {string} oldMembership the previous membership, can be null.\n */\n\n/**\n * Create a MatrixActions.Room.myMembership action that represents\n * a MatrixClient `Room.myMembership` event for the syncing user,\n * emitted when the syncing user's membership is updated for a room.\n *\n * @param {MatrixClient} matrixClient the matrix client.\n * @param {Room} room to room for which the self-membership changed.\n * @param {string} membership the new membership\n * @param {string} oldMembership the previous membership, can be null.\n * @returns {RoomMembershipAction} an action of type `MatrixActions.Room.myMembership`.\n */\nfunction createSelfMembershipAction(\n    matrixClient: MatrixClient,\n    room: Room,\n    membership: string,\n    oldMembership: string,\n): ActionPayload {\n    return { action: \"MatrixActions.Room.myMembership\", room, membership, oldMembership };\n}\n\n/**\n * @typedef EventDecryptedAction\n * @type {Object}\n * @property {string} action 'MatrixActions.Event.decrypted'.\n * @property {MatrixEvent} event the matrix event that was decrypted.\n */\n\n/**\n * Create a MatrixActions.Event.decrypted action that represents\n * a MatrixClient `Event.decrypted` matrix event, emitted when a\n * matrix event is decrypted.\n *\n * @param {MatrixClient} matrixClient the matrix client.\n * @param {MatrixEvent} event the matrix event that was decrypted.\n * @returns {EventDecryptedAction} an action of type `MatrixActions.Event.decrypted`.\n */\nfunction createEventDecryptedAction(matrixClient: MatrixClient, event: MatrixEvent): ActionPayload {\n    return { action: \"MatrixActions.Event.decrypted\", event };\n}\n\ntype Listener = () => void;\ntype ActionCreator = (matrixClient: MatrixClient, ...args: any) => ActionPayload;\n\n// A list of callbacks to call to unregister all listeners added\nlet matrixClientListenersStop: Listener[] = [];\n\n/**\n * Start listening to events of type eventName on matrixClient and when they are emitted,\n * dispatch an action created by the actionCreator function.\n * @param {MatrixClient} matrixClient a MatrixClient to register a listener with.\n * @param {string} eventName the event to listen to on MatrixClient.\n * @param {function} actionCreator a function that should return an action to dispatch\n *                                 when given the MatrixClient as an argument as well as\n *                                 arguments emitted in the MatrixClient event.\n */\nfunction addMatrixClientListener(\n    matrixClient: MatrixClient,\n    eventName: Parameters<MatrixClient[\"emit\"]>[0],\n    actionCreator: ActionCreator,\n): void {\n    const listener: Listener = (...args) => {\n        const payload = actionCreator(matrixClient, ...args);\n        if (payload) {\n            // Consumers shouldn't have to worry about calling js-sdk methods mid-dispatch, so make this dispatch async\n            dis.dispatch(payload, false);\n        }\n    };\n    matrixClient.on(eventName, listener);\n    matrixClientListenersStop.push(() => {\n        matrixClient.removeListener(eventName, listener);\n    });\n}\n\n/**\n * This object is responsible for dispatching actions when certain events are emitted by\n * the given MatrixClient.\n */\nexport default {\n    /**\n     * Start listening to certain events from the MatrixClient and dispatch actions when\n     * they are emitted.\n     * @param {MatrixClient} matrixClient the MatrixClient to listen to events from\n     */\n    start(matrixClient: MatrixClient) {\n        addMatrixClientListener(matrixClient, ClientEvent.Sync, createSyncAction);\n        addMatrixClientListener(matrixClient, ClientEvent.AccountData, createAccountDataAction);\n        addMatrixClientListener(matrixClient, RoomEvent.AccountData, createRoomAccountDataAction);\n        addMatrixClientListener(matrixClient, ClientEvent.Room, createRoomAction);\n        addMatrixClientListener(matrixClient, RoomEvent.Tags, createRoomTagsAction);\n        addMatrixClientListener(matrixClient, RoomEvent.Receipt, createRoomReceiptAction);\n        addMatrixClientListener(matrixClient, RoomEvent.Timeline, createRoomTimelineAction);\n        addMatrixClientListener(matrixClient, RoomEvent.MyMembership, createSelfMembershipAction);\n        addMatrixClientListener(matrixClient, MatrixEventEvent.Decrypted, createEventDecryptedAction);\n        addMatrixClientListener(matrixClient, RoomStateEvent.Events, createRoomStateEventsAction);\n    },\n\n    /**\n     * Stop listening to events.\n     */\n    stop() {\n        matrixClientListenersStop.forEach((stopListener) => stopListener());\n        matrixClientListenersStop = [];\n    },\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2023 The Matrix.org Foundation C.I.C.\nCopyright 2017, 2018 , 2019 New Vector Ltd\nCopyright 2017 Vector Creations Ltd.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    EventTimeline,\n    EventTimelineSet,\n    type ICreateClientOpts,\n    type IStartClientOpts,\n    type MatrixClient,\n    MemoryStore,\n    PendingEventOrdering,\n    type RoomNameState,\n    RoomNameType,\n    type TokenRefreshFunction,\n} from \"matrix-js-sdk/src/matrix\";\nimport { VerificationMethod } from \"matrix-js-sdk/src/types\";\nimport * as utils from \"matrix-js-sdk/src/utils\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport createMatrixClient from \"./utils/createMatrixClient\";\nimport SettingsStore from \"./settings/SettingsStore\";\nimport MatrixActionCreators from \"./actions/MatrixActionCreators\";\nimport Modal from \"./Modal\";\nimport MatrixClientBackedSettingsHandler from \"./settings/handlers/MatrixClientBackedSettingsHandler\";\nimport * as StorageManager from \"./utils/StorageManager\";\nimport IdentityAuthClient from \"./IdentityAuthClient\";\nimport { crossSigningCallbacks } from \"./SecurityManager\";\nimport { SlidingSyncManager } from \"./SlidingSyncManager\";\nimport { _t, UserFriendlyError } from \"./languageHandler\";\nimport MatrixClientBackedController from \"./settings/controllers/MatrixClientBackedController\";\nimport ErrorDialog from \"./components/views/dialogs/ErrorDialog\";\nimport PlatformPeg from \"./PlatformPeg\";\nimport { formatList } from \"./utils/FormattingUtils\";\nimport SdkConfig from \"./SdkConfig\";\nimport { setDeviceIsolationMode } from \"./settings/controllers/DeviceIsolationModeController.ts\";\nimport { initialiseDehydrationIfEnabled } from \"./utils/device/dehydration\";\n\nexport interface IMatrixClientCreds {\n    homeserverUrl: string;\n    identityServerUrl?: string;\n    userId: string;\n    deviceId?: string;\n    accessToken: string;\n    refreshToken?: string;\n    guest?: boolean;\n    pickleKey?: string;\n    freshLogin?: boolean;\n}\n\nexport interface MatrixClientPegAssignOpts {\n    /**\n     * If we are using Rust crypto, a key with which to encrypt the indexeddb.\n     *\n     * If provided, it must be exactly 32 bytes of data. If both this and\n     * {@link MatrixClientPegAssignOpts.rustCryptoStorePassword} are undefined,\n     * the store will be unencrypted.\n     */\n    rustCryptoStoreKey?: Uint8Array;\n\n    /**\n     * If we are using Rust crypto, a password which will be used to derive a key to encrypt the store with.\n     *\n     * An alternative to {@link MatrixClientPegAssignOpts.rustCryptoStoreKey}. Ignored if `rustCryptoStoreKey` is set.\n     *\n     * Deriving a key from a password is (deliberately) a slow operation, so prefer to pass a `rustCryptoStoreKey`\n     * directly where possible.\n     */\n    rustCryptoStorePassword?: string;\n}\n\n/**\n * Holds the current instance of the `MatrixClient` to use across the codebase.\n * Looking for an `MatrixClient`? Just look for the `MatrixClientPeg` on the peg\n * board. \"Peg\" is the literal meaning of something you hang something on. So\n * you'll find a `MatrixClient` hanging on the `MatrixClientPeg`.\n */\nexport interface IMatrixClientPeg {\n    /**\n     * The opts used to start the client\n     */\n    opts: IStartClientOpts;\n\n    /**\n     * Get the current MatrixClient, if any\n     */\n    get(): MatrixClient | null;\n\n    /**\n     * Get the current MatrixClient, throwing an error if there isn't one\n     */\n    safeGet(): MatrixClient;\n\n    /**\n     * Unset the current MatrixClient\n     */\n    unset(): void;\n\n    /**\n     * Prepare the MatrixClient for use, including initialising the store and crypto, but do not start it.\n     */\n    assign(opts?: MatrixClientPegAssignOpts): Promise<IStartClientOpts>;\n\n    /**\n     * Prepare the MatrixClient for use, including initialising the store and crypto, and start it.\n     */\n    start(opts?: MatrixClientPegAssignOpts): Promise<void>;\n\n    /**\n     * If we've registered a user ID we set this to the ID of the\n     * user we've just registered. If they then go & log in, we\n     * can send them to the welcome user (obviously this doesn't\n     * guarantee they'll get a chat with the welcome user).\n     *\n     * @param {string} uid The user ID of the user we've just registered\n     */\n    setJustRegisteredUserId(uid: string | null): void;\n\n    /**\n     * Returns true if the current user has just been registered by this\n     * client as determined by setJustRegisteredUserId()\n     *\n     * @returns {bool} True if user has just been registered\n     */\n    currentUserIsJustRegistered(): boolean;\n\n    /**\n     * If the current user has been registered by this device then this\n     * returns a boolean of whether it was within the last N hours given.\n     */\n    userRegisteredWithinLastHours(hours: number): boolean;\n\n    /**\n     * If the current user has been registered by this device then this\n     * returns a boolean of whether it was after a given timestamp.\n     */\n    userRegisteredAfter(date: Date): boolean;\n\n    /**\n     * Replace this MatrixClientPeg's client with a client instance that has\n     * homeserver / identity server URLs and active credentials\n     *\n     * @param {IMatrixClientCreds} creds The new credentials to use.\n     * @param {TokenRefreshFunction} tokenRefreshFunction OPTIONAL function used by MatrixClient to attempt token refresh\n     *          see {@link ICreateClientOpts.tokenRefreshFunction}\n     */\n    replaceUsingCreds(creds: IMatrixClientCreds, tokenRefreshFunction?: TokenRefreshFunction): void;\n}\n\n/**\n * Wrapper object for handling the js-sdk Matrix Client object in the react-sdk\n * Handles the creation/initialisation of client objects.\n * This module provides a singleton instance of this class so the 'current'\n * Matrix Client object is available easily.\n */\nclass MatrixClientPegClass implements IMatrixClientPeg {\n    // These are the default options used when when the\n    // client is started in 'start'. These can be altered\n    // at any time up to after the 'will_start_client'\n    // event is finished processing.\n    public opts: IStartClientOpts = {\n        initialSyncLimit: 20,\n    };\n\n    private matrixClient: MatrixClient | null = null;\n    private justRegisteredUserId: string | null = null;\n\n    public get(): MatrixClient | null {\n        return this.matrixClient;\n    }\n\n    public safeGet(): MatrixClient {\n        if (!this.matrixClient) {\n            throw new UserFriendlyError(\"error_user_not_logged_in\");\n        }\n        return this.matrixClient;\n    }\n\n    public unset(): void {\n        this.matrixClient = null;\n\n        MatrixActionCreators.stop();\n    }\n\n    public setJustRegisteredUserId(uid: string | null): void {\n        this.justRegisteredUserId = uid;\n        if (uid) {\n            const registrationTime = Date.now().toString();\n            window.localStorage.setItem(\"mx_registration_time\", registrationTime);\n        }\n    }\n\n    public currentUserIsJustRegistered(): boolean {\n        return !!this.matrixClient && this.matrixClient.credentials.userId === this.justRegisteredUserId;\n    }\n\n    public userRegisteredWithinLastHours(hours: number): boolean {\n        if (hours <= 0) {\n            return false;\n        }\n\n        try {\n            const registrationTime = parseInt(window.localStorage.getItem(\"mx_registration_time\")!, 10);\n            const diff = Date.now() - registrationTime;\n            return diff / 36e5 <= hours;\n        } catch {\n            return false;\n        }\n    }\n\n    public userRegisteredAfter(timestamp: Date): boolean {\n        try {\n            const registrationTime = parseInt(window.localStorage.getItem(\"mx_registration_time\")!, 10);\n            return timestamp.getTime() <= registrationTime;\n        } catch {\n            return false;\n        }\n    }\n\n    public replaceUsingCreds(creds: IMatrixClientCreds, tokenRefreshFunction?: TokenRefreshFunction): void {\n        this.createClient(creds, tokenRefreshFunction);\n    }\n\n    private onUnexpectedStoreClose = async (): Promise<void> => {\n        if (!this.matrixClient) return;\n        this.matrixClient.stopClient(); // stop the client as the database has failed\n        this.matrixClient.store.destroy();\n\n        if (!this.matrixClient.isGuest()) {\n            // If the user is not a guest then prompt them to reload rather than doing it for them\n            // For guests this is likely to happen during e-mail verification as part of registration\n\n            const brand = SdkConfig.get().brand;\n            const platform = PlatformPeg.get()?.getHumanReadableName();\n\n            // Determine the description based on the platform\n            const description =\n                platform === \"Web Platform\"\n                    ? _t(\"error_database_closed_description|for_web\", { brand })\n                    : _t(\"error_database_closed_description|for_desktop\");\n\n            const [reload] = await Modal.createDialog(ErrorDialog, {\n                title: _t(\"error_database_closed_title\", { brand }),\n                description,\n                button: _t(\"action|reload\"),\n            }).finished;\n\n            if (!reload) return;\n        }\n\n        PlatformPeg.get()?.reload();\n    };\n\n    /**\n     * Implementation of {@link IMatrixClientPeg.assign}.\n     */\n    public async assign(assignOpts: MatrixClientPegAssignOpts = {}): Promise<IStartClientOpts> {\n        if (!this.matrixClient) {\n            throw new Error(\"createClient must be called first\");\n        }\n\n        for (const dbType of [\"indexeddb\", \"memory\"]) {\n            try {\n                const promise = this.matrixClient.store.startup();\n                logger.log(\"MatrixClientPeg: waiting for MatrixClient store to initialise\");\n                await promise;\n                break;\n            } catch (err) {\n                if (dbType === \"indexeddb\") {\n                    logger.error(\"Error starting matrixclient store - falling back to memory store\", err);\n                    this.matrixClient.store = new MemoryStore({\n                        localStorage: localStorage,\n                    });\n                } else {\n                    logger.error(\"Failed to start memory store!\", err);\n                    throw err;\n                }\n            }\n        }\n        this.matrixClient.store.on?.(\"closed\", this.onUnexpectedStoreClose);\n\n        // try to initialise e2e on the new client\n        if (!SettingsStore.getValue(\"lowBandwidth\")) {\n            await this.initClientCrypto(assignOpts.rustCryptoStoreKey, assignOpts.rustCryptoStorePassword);\n        }\n\n        const opts = utils.deepCopy(this.opts);\n        // the react sdk doesn't work without this, so don't allow\n        opts.pendingEventOrdering = PendingEventOrdering.Detached;\n        opts.lazyLoadMembers = true;\n        opts.clientWellKnownPollPeriod = 2 * 60 * 60; // 2 hours\n        opts.threadSupport = true;\n\n        if (SettingsStore.getValue(\"feature_sliding_sync\")) {\n            throw new UserFriendlyError(\"sliding_sync_legacy_no_longer_supported\");\n        }\n\n        // If the user has enabled the labs feature for sliding sync, set it up\n        // otherwise check if the feature is supported\n        if (SettingsStore.getValue(\"feature_simplified_sliding_sync\")) {\n            opts.slidingSync = await SlidingSyncManager.instance.setup(this.matrixClient);\n        } else {\n            SlidingSyncManager.instance.checkSupport(this.matrixClient);\n        }\n\n        // Connect the matrix client to the dispatcher and setting handlers\n        MatrixActionCreators.start(this.matrixClient);\n        MatrixClientBackedSettingsHandler.matrixClient = this.matrixClient;\n        MatrixClientBackedController.matrixClient = this.matrixClient;\n\n        return opts;\n    }\n\n    /**\n     * Attempt to initialize the crypto layer on a newly-created MatrixClient\n     *\n     * @param rustCryptoStoreKey - A key with which to encrypt the rust crypto indexeddb.\n     *   If provided, it must be exactly 32 bytes of data. If both this and `rustCryptoStorePassword` are\n     *   undefined, the store will be unencrypted.\n     *\n     * @param rustCryptoStorePassword - An alternative to `rustCryptoStoreKey`. Ignored if `rustCryptoStoreKey` is set.\n     *    A password which will be used to derive a key to encrypt the store with. Deriving a key from a password is\n     *    (deliberately) a slow operation, so prefer to pass a `rustCryptoStoreKey` directly where possible.\n     */\n    private async initClientCrypto(rustCryptoStoreKey?: Uint8Array, rustCryptoStorePassword?: string): Promise<void> {\n        if (!this.matrixClient) {\n            throw new Error(\"createClient must be called first\");\n        }\n\n        if (!rustCryptoStoreKey && !rustCryptoStorePassword) {\n            logger.error(\"Warning! Not using an encryption key for rust crypto store.\");\n        }\n\n        await this.matrixClient.initRustCrypto({\n            storageKey: rustCryptoStoreKey,\n            storagePassword: rustCryptoStorePassword,\n        });\n\n        StorageManager.setCryptoInitialised(true);\n\n        setDeviceIsolationMode(this.matrixClient, SettingsStore.getValue(\"feature_exclude_insecure_devices\"));\n\n        // Start dehydration. This code is only for the case where the client\n        // gets restarted, so we only do this if we already have the dehydration\n        // key cached, and we don't have to try to rehydrate a device. If this\n        // is a new login, we will start dehydration after Secret Storage is\n        // unlocked.\n        try {\n            await initialiseDehydrationIfEnabled(this.matrixClient, { onlyIfKeyCached: true, rehydrate: false });\n        } catch (e) {\n            // We may get an error dehydrating, such as if cross-signing and\n            // SSSS are not set up yet.  Just log the error and continue.\n            // If SSSS gets set up later, we will re-try dehydration.\n            console.log(\"Error starting device dehydration\", e);\n        }\n\n        return;\n    }\n\n    /**\n     * Implementation of {@link IMatrixClientPeg.start}.\n     */\n    public async start(assignOpts?: MatrixClientPegAssignOpts): Promise<void> {\n        const opts = await this.assign(assignOpts);\n\n        logger.log(`MatrixClientPeg: really starting MatrixClient`);\n        await this.matrixClient!.startClient(opts);\n        logger.log(`MatrixClientPeg: MatrixClient started`);\n    }\n\n    private namesToRoomName(names: string[], count: number): string | undefined {\n        const countWithoutMe = count - 1;\n        if (!names.length) {\n            return _t(\"empty_room\");\n        }\n        if (names.length === 1 && countWithoutMe <= 1) {\n            return names[0];\n        }\n    }\n\n    private memberNamesToRoomName(names: string[], count: number): string {\n        const name = this.namesToRoomName(names, count);\n        if (name) return name;\n\n        if (names.length === 2 && count === 2) {\n            return formatList(names);\n        }\n        return formatList(names, 1);\n    }\n\n    private inviteeNamesToRoomName(names: string[], count: number): string {\n        const name = this.namesToRoomName(names, count);\n        if (name) return name;\n\n        if (names.length === 2 && count === 2) {\n            return _t(\"inviting_user1_and_user2\", {\n                user1: names[0],\n                user2: names[1],\n            });\n        }\n        return _t(\"inviting_user_and_n_others\", {\n            user: names[0],\n            count: count - 1,\n        });\n    }\n\n    private createClient(creds: IMatrixClientCreds, tokenRefreshFunction?: TokenRefreshFunction): void {\n        const opts: ICreateClientOpts = {\n            baseUrl: creds.homeserverUrl,\n            idBaseUrl: creds.identityServerUrl,\n            accessToken: creds.accessToken,\n            refreshToken: creds.refreshToken,\n            tokenRefreshFunction,\n            userId: creds.userId,\n            deviceId: creds.deviceId,\n            pickleKey: creds.pickleKey,\n            timelineSupport: true,\n            forceTURN: !SettingsStore.getValue(\"webRtcAllowPeerToPeer\"),\n            fallbackICEServerAllowed: !!SettingsStore.getValue(\"fallbackICEServerAllowed\"),\n            // Gather up to 20 ICE candidates when a call arrives: this should be more than we'd\n            // ever normally need, so effectively this should make all the gathering happen when\n            // the call arrives.\n            iceCandidatePoolSize: 20,\n            verificationMethods: [\n                VerificationMethod.Sas,\n                VerificationMethod.ShowQrCode,\n                VerificationMethod.Reciprocate,\n            ],\n            identityServer: new IdentityAuthClient(),\n            // These are always installed regardless of the labs flag so that cross-signing features\n            // can toggle on without reloading and also be accessed immediately after login.\n            cryptoCallbacks: { ...crossSigningCallbacks },\n            enableEncryptedStateEvents: SettingsStore.getValue(\"feature_msc4362_encrypted_state_events\"),\n            roomNameGenerator: (_: string, state: RoomNameState) => {\n                switch (state.type) {\n                    case RoomNameType.Generated:\n                        switch (state.subtype) {\n                            case \"Inviting\":\n                                return this.inviteeNamesToRoomName(state.names, state.count);\n                            default:\n                                return this.memberNamesToRoomName(state.names, state.count);\n                        }\n                    case RoomNameType.EmptyRoom:\n                        if (state.oldName) {\n                            return _t(\"empty_room_was_name\", {\n                                oldName: state.oldName,\n                            });\n                        } else {\n                            return _t(\"empty_room\");\n                        }\n                    default:\n                        return null;\n                }\n            },\n        };\n\n        this.matrixClient = createMatrixClient(opts);\n        this.matrixClient.setGuest(Boolean(creds.guest));\n\n        const notifTimelineSet = new EventTimelineSet(undefined, {\n            timelineSupport: true,\n            pendingEvents: false,\n        });\n        // XXX: what is our initial pagination token?! it somehow needs to be synchronised with /sync.\n        notifTimelineSet.getLiveTimeline().setPaginationToken(\"\", EventTimeline.BACKWARDS);\n        this.matrixClient.setNotifTimelineSet(notifTimelineSet);\n    }\n}\n\n/**\n * Note: You should be using a React context with access to a client rather than\n * using this, as in a multi-account world this will not exist!\n */\nexport const MatrixClientPeg: IMatrixClientPeg = new MatrixClientPegClass();\n\nif (!window.mxMatrixClientPeg) {\n    window.mxMatrixClientPeg = MatrixClientPeg;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2017 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport EventEmitter from \"events\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport SettingsStore from \"./settings/SettingsStore\";\nimport { SettingLevel } from \"./settings/SettingLevel\";\nimport { MatrixClientPeg } from \"./MatrixClientPeg\";\nimport { _t } from \"./languageHandler\";\n\n// XXX: MediaDeviceKind is a union type, so we make our own enum\nexport enum MediaDeviceKindEnum {\n    AudioOutput = \"audiooutput\",\n    AudioInput = \"audioinput\",\n    VideoInput = \"videoinput\",\n}\n\nexport type IMediaDevices = Record<MediaDeviceKindEnum, Array<MediaDeviceInfo>>;\n\nexport enum MediaDeviceHandlerEvent {\n    AudioOutputChanged = \"audio_output_changed\",\n}\n\nexport default class MediaDeviceHandler extends EventEmitter {\n    private static internalInstance?: MediaDeviceHandler;\n\n    public static get instance(): MediaDeviceHandler {\n        if (!MediaDeviceHandler.internalInstance) {\n            MediaDeviceHandler.internalInstance = new MediaDeviceHandler();\n        }\n        return MediaDeviceHandler.internalInstance;\n    }\n\n    public static async hasAnyLabeledDevices(): Promise<boolean> {\n        const devices = await navigator.mediaDevices.enumerateDevices();\n        return devices.some((d) => Boolean(d.label));\n    }\n\n    /**\n     * Gets the available audio input/output and video input devices\n     * from the browser: a thin wrapper around mediaDevices.enumerateDevices()\n     * that also returns results by type of devices. Note that this requires\n     * user media permissions and an active stream, otherwise you'll get blank\n     * device labels.\n     *\n     * Once the Permissions API\n     * (https://developer.mozilla.org/en-US/docs/Web/API/Permissions_API)\n     * is ready for primetime, it might help make this simpler.\n     *\n     * @return Promise<IMediaDevices> The available media devices\n     */\n    public static async getDevices(): Promise<IMediaDevices | undefined> {\n        try {\n            const devices = await navigator.mediaDevices.enumerateDevices();\n            const output: Record<MediaDeviceKindEnum, MediaDeviceInfo[]> = {\n                [MediaDeviceKindEnum.AudioOutput]: [],\n                [MediaDeviceKindEnum.AudioInput]: [],\n                [MediaDeviceKindEnum.VideoInput]: [],\n            };\n\n            devices.forEach((device) => output[device.kind].push(device));\n            return output;\n        } catch (error) {\n            logger.warn(\"Unable to refresh WebRTC Devices: \", error);\n        }\n    }\n\n    public static getDefaultDevice = (devices: Array<Partial<MediaDeviceInfo>>): string => {\n        // Note we're looking for a device with deviceId 'default' but adding a device\n        // with deviceId == the empty string: this is because Chrome gives us a device\n        // with deviceId 'default', so we're looking for this, not the one we are adding.\n        if (!devices.some((i) => i.deviceId === \"default\")) {\n            devices.unshift({ deviceId: \"\", label: _t(\"voip|default_device\") });\n            return \"\";\n        } else {\n            return \"default\";\n        }\n    };\n\n    /**\n     * Retrieves devices from the SettingsStore and tells the js-sdk to use them\n     */\n    public static async loadDevices(): Promise<void> {\n        const audioDeviceId = SettingsStore.getValue(\"webrtc_audioinput\");\n        const videoDeviceId = SettingsStore.getValue(\"webrtc_videoinput\");\n\n        await MatrixClientPeg.safeGet().getMediaHandler().setAudioInput(audioDeviceId);\n        await MatrixClientPeg.safeGet().getMediaHandler().setVideoInput(videoDeviceId);\n\n        await MediaDeviceHandler.updateAudioSettings();\n    }\n\n    private static async updateAudioSettings(): Promise<void> {\n        await MatrixClientPeg.safeGet().getMediaHandler().setAudioSettings({\n            autoGainControl: MediaDeviceHandler.getAudioAutoGainControl(),\n            echoCancellation: MediaDeviceHandler.getAudioEchoCancellation(),\n            noiseSuppression: MediaDeviceHandler.getAudioNoiseSuppression(),\n        });\n    }\n\n    public setAudioOutput(deviceId: string): void {\n        SettingsStore.setValue(\"webrtc_audiooutput\", null, SettingLevel.DEVICE, deviceId);\n        this.emit(MediaDeviceHandlerEvent.AudioOutputChanged, deviceId);\n    }\n\n    /**\n     * This will not change the device that a potential call uses. The call will\n     * need to be ended and started again for this change to take effect\n     * @param {string} deviceId\n     */\n    public async setAudioInput(deviceId: string): Promise<void> {\n        SettingsStore.setValue(\"webrtc_audioinput\", null, SettingLevel.DEVICE, deviceId);\n        return MatrixClientPeg.safeGet().getMediaHandler().setAudioInput(deviceId);\n    }\n\n    /**\n     * This will not change the device that a potential call uses. The call will\n     * need to be ended and started again for this change to take effect\n     * @param {string} deviceId\n     */\n    public async setVideoInput(deviceId: string): Promise<void> {\n        SettingsStore.setValue(\"webrtc_videoinput\", null, SettingLevel.DEVICE, deviceId);\n        return MatrixClientPeg.safeGet().getMediaHandler().setVideoInput(deviceId);\n    }\n\n    public async setDevice(deviceId: string, kind: MediaDeviceKindEnum): Promise<void> {\n        switch (kind) {\n            case MediaDeviceKindEnum.AudioOutput:\n                this.setAudioOutput(deviceId);\n                break;\n            case MediaDeviceKindEnum.AudioInput:\n                await this.setAudioInput(deviceId);\n                break;\n            case MediaDeviceKindEnum.VideoInput:\n                await this.setVideoInput(deviceId);\n                break;\n        }\n    }\n\n    public static async setAudioAutoGainControl(value: boolean): Promise<void> {\n        await SettingsStore.setValue(\"webrtc_audio_autoGainControl\", null, SettingLevel.DEVICE, value);\n        await MediaDeviceHandler.updateAudioSettings();\n    }\n\n    public static async setAudioEchoCancellation(value: boolean): Promise<void> {\n        await SettingsStore.setValue(\"webrtc_audio_echoCancellation\", null, SettingLevel.DEVICE, value);\n        await MediaDeviceHandler.updateAudioSettings();\n    }\n\n    public static async setAudioNoiseSuppression(value: boolean): Promise<void> {\n        await SettingsStore.setValue(\"webrtc_audio_noiseSuppression\", null, SettingLevel.DEVICE, value);\n        await MediaDeviceHandler.updateAudioSettings();\n    }\n\n    public static getAudioOutput(): string {\n        return SettingsStore.getValueAt(SettingLevel.DEVICE, \"webrtc_audiooutput\");\n    }\n\n    public static getAudioInput(): string {\n        return SettingsStore.getValueAt(SettingLevel.DEVICE, \"webrtc_audioinput\");\n    }\n\n    public static getVideoInput(): string {\n        return SettingsStore.getValueAt(SettingLevel.DEVICE, \"webrtc_videoinput\");\n    }\n\n    public static getAudioAutoGainControl(): boolean {\n        return SettingsStore.getValue(\"webrtc_audio_autoGainControl\");\n    }\n\n    public static getAudioEchoCancellation(): boolean {\n        return SettingsStore.getValue(\"webrtc_audio_echoCancellation\");\n    }\n\n    public static getAudioNoiseSuppression(): boolean {\n        return SettingsStore.getValue(\"webrtc_audio_noiseSuppression\");\n    }\n\n    /**\n     * Returns the current set deviceId for a device kind\n     * @param {MediaDeviceKindEnum} kind of the device that will be returned\n     * @returns {string} the deviceId\n     */\n    public static getDevice(kind: MediaDeviceKindEnum): string {\n        switch (kind) {\n            case MediaDeviceKindEnum.AudioOutput:\n                return this.getAudioOutput();\n            case MediaDeviceKindEnum.AudioInput:\n                return this.getAudioInput();\n            case MediaDeviceKindEnum.VideoInput:\n                return this.getVideoInput();\n        }\n    }\n\n    public static get startWithAudioMuted(): boolean {\n        return SettingsStore.getValue(\"audioInputMuted\");\n    }\n    public static set startWithAudioMuted(value: boolean) {\n        SettingsStore.setValue(\"audioInputMuted\", null, SettingLevel.DEVICE, value);\n    }\n\n    public static get startWithVideoMuted(): boolean {\n        return SettingsStore.getValue(\"videoInputMuted\");\n    }\n    public static set startWithVideoMuted(value: boolean) {\n        SettingsStore.setValue(\"videoInputMuted\", null, SettingLevel.DEVICE, value);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode, Suspense } from \"react\";\n\nimport { _t } from \"./languageHandler\";\nimport BaseDialog from \"./components/views/dialogs/BaseDialog\";\nimport DialogButtons from \"./components/views/elements/DialogButtons\";\nimport Spinner from \"./components/views/elements/Spinner\";\n\ninterface IProps {\n    onFinished(): void;\n    children: ReactNode;\n}\n\ninterface IState {\n    error?: Error;\n}\n\n/**\n * Wrap an asynchronous loader function with a react component which shows a\n * spinner until the real component loads.\n */\nexport default class AsyncWrapper extends React.Component<IProps, IState> {\n    public static getDerivedStateFromError(error: Error): IState {\n        return { error };\n    }\n\n    public state: IState = {};\n\n    public render(): React.ReactNode {\n        if (this.state.error) {\n            return (\n                <BaseDialog onFinished={this.props.onFinished} title={_t(\"common|error\")}>\n                    {_t(\"failed_load_async_component\")}\n                    <DialogButtons\n                        primaryButton={_t(\"action|dismiss\")}\n                        onPrimaryButtonClick={this.props.onFinished}\n                        hasCancel={false}\n                    />\n                </BaseDialog>\n            );\n        }\n\n        return <Suspense fallback={<Spinner />}>{this.props.children}</Suspense>;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { StrictMode } from \"react\";\nimport { createRoot, type Root } from \"react-dom/client\";\nimport classNames from \"classnames\";\nimport { TypedEventEmitter } from \"matrix-js-sdk/src/matrix\";\nimport { Glass, TooltipProvider } from \"@vector-im/compound-web\";\n\nimport defaultDispatcher from \"./dispatcher/dispatcher\";\nimport AsyncWrapper from \"./AsyncWrapper\";\nimport { type Defaultize } from \"./@types/common\";\nimport { type ActionPayload } from \"./dispatcher/payloads\";\nimport { filterBoolean } from \"./utils/arrays.ts\";\n\nconst DIALOG_CONTAINER_ID = \"mx_Dialog_Container\";\nconst STATIC_DIALOG_CONTAINER_ID = \"mx_Dialog_StaticContainer\";\n\n// Type which accepts a React Component which looks like a Modal (accepts an onFinished prop)\nexport type ComponentType =\n    | React.ComponentType<{\n          onFinished(...args: any): void;\n      }>\n    | React.ComponentType<any>;\n\n/**\n * The parameter types of the `onFinished` callback property exposed by the component which forms the\n * body of the dialog.\n *\n * @typeParam C - The type of the React component which forms the body of the dialog.\n */\ntype OnFinishedParams<C extends ComponentType> = Parameters<React.ComponentProps<C>[\"onFinished\"]>;\n\n/**\n * The properties exposed by the `props` argument to {@link Modal.createDialog}: the same as\n * those exposed by the underlying component, with the exception of `onFinished`, which is provided by\n * `createDialog`.\n *\n * @typeParam C - The type of the React component which forms the body of the dialog.\n */\nexport type ComponentProps<C extends ComponentType> = Defaultize<\n    Omit<React.ComponentProps<C>, \"onFinished\">,\n    C[\"defaultProps\"]\n>;\n\nexport interface IModal<C extends ComponentType> {\n    elem: React.ReactNode;\n    className?: string;\n    beforeClosePromise?: Promise<boolean>;\n    closeReason?: ModalCloseReason;\n    onBeforeClose?(reason?: ModalCloseReason): Promise<boolean>;\n\n    /**\n     * Run the {@link deferred} with the given arguments, and close this modal.\n     *\n     * This method is passed as the `onFinished` callback to the underlying component,\n     * as well as being returned by {@link Modal.createDialog} to the caller.\n     */\n    close(...args: OnFinishedParams<C> | []): void;\n\n    hidden?: boolean;\n\n    /** A deferred to resolve when the dialog closes, with the results as provided by\n     * the call to {@link close} (normally from the `onFinished` callback).\n     */\n    deferred?: PromiseWithResolvers<OnFinishedParams<C> | []>;\n}\n\n/** The result of {@link Modal.createDialog}.\n *\n * @typeParam C - The type of the React component which forms the body of the dialog.\n */\nexport interface IHandle<C extends ComponentType> {\n    /**\n     * A promise which will resolve when the dialog closes.\n     *\n     * If the dialog body component calls the `onFinished` property, or the caller calls {@link close},\n     * the promise resolves with an array holding the arguments to that call.\n     *\n     * If the dialog is closed by clicking in the background, the promise resolves with an empty array.\n     */\n    finished: Promise<OnFinishedParams<C> | []>;\n\n    /**\n     * A function which, if called, will close the dialog.\n     *\n     * @param args - Arguments to return to {@link finished}.\n     */\n    close(...args: OnFinishedParams<C>): void;\n}\n\ninterface IOptions<C extends ComponentType> {\n    onBeforeClose?: IModal<C>[\"onBeforeClose\"];\n}\n\nexport enum ModalManagerEvent {\n    Opened = \"opened\",\n    Closed = \"closed\",\n}\n\ntype HandlerMap = {\n    [ModalManagerEvent.Opened]: () => void;\n    [ModalManagerEvent.Closed]: () => void;\n};\n\ntype ModalCloseReason = \"backgroundClick\";\n\nfunction getOrCreateContainer(id: string): HTMLDivElement {\n    let container = document.getElementById(id) as HTMLDivElement | null;\n    if (!container) {\n        container = document.createElement(\"div\");\n        container.id = id;\n        document.body.appendChild(container);\n    }\n    return container;\n}\n\nexport class ModalManager extends TypedEventEmitter<ModalManagerEvent, HandlerMap> {\n    private counter = 0;\n    // The modal to prioritise over all others. If this is set, only show\n    // this modal. Remove all other modals from the stack when this modal\n    // is closed.\n    private priorityModal: IModal<any> | null = null;\n    // The modal to keep open underneath other modals if possible. Useful\n    // for cases like Settings where the modal should remain open while the\n    // user is prompted for more information/errors.\n    private staticModal: IModal<any> | null = null;\n    // A list of the modals we have stacked up, with the most recent at [0]\n    // Neither the static nor priority modal will be in this list.\n    private modals: IModal<any>[] = [];\n\n    private static root?: Root;\n    private static getOrCreateRoot(): Root {\n        if (!ModalManager.root) {\n            const container = getOrCreateContainer(DIALOG_CONTAINER_ID);\n            ModalManager.root = createRoot(container);\n        }\n        return ModalManager.root;\n    }\n\n    private static staticRoot?: Root;\n    private static getOrCreateStaticRoot(): Root {\n        if (!ModalManager.staticRoot) {\n            const container = getOrCreateContainer(STATIC_DIALOG_CONTAINER_ID);\n            ModalManager.staticRoot = createRoot(container);\n        }\n        return ModalManager.staticRoot;\n    }\n\n    public constructor() {\n        super();\n\n        // We never unregister this, but the Modal class is a singleton so there would\n        // never be an opportunity to do so anyway, except in the entirely theoretical\n        // scenario of instantiating a non-singleton instance of the Modal class.\n        defaultDispatcher.register(this.onAction);\n    }\n\n    private onAction = (payload: ActionPayload): void => {\n        if (payload.action === \"logout\") {\n            this.forceCloseAllModals();\n        }\n    };\n\n    public toggleCurrentDialogVisibility(): void {\n        const modal = this.getCurrentModal();\n        if (!modal) return;\n        modal.hidden = !modal.hidden;\n    }\n\n    public hasDialogs(): boolean {\n        return !!this.priorityModal || !!this.staticModal || this.modals.length > 0;\n    }\n\n    /**\n     * DEPRECATED.\n     * This is used only for tests. They should be using forceCloseAllModals but that\n     * caused a chunk of tests to fail, so for now they continue to use this.\n     *\n     * @param reason either \"backgroundClick\" or undefined\n     * @return whether a modal was closed\n     */\n    public closeCurrentModal(reason?: ModalCloseReason): boolean {\n        const modal = this.getCurrentModal();\n        if (!modal) {\n            return false;\n        }\n        modal.closeReason = reason;\n        modal.close();\n        return true;\n    }\n\n    /**\n     * Forces closes all open modals. The modals onBeforeClose function will not be\n     * run and the modal will not have a chance to prevent closing. Intended for\n     * situations like the user logging out of the app.\n     */\n    public forceCloseAllModals(): void {\n        const modals = filterBoolean([...this.modals, this.staticModal, this.priorityModal]);\n        for (const modal of modals) {\n            modal.deferred?.resolve([]);\n            this.emitClosed();\n        }\n\n        this.modals = [];\n        this.staticModal = null;\n        this.priorityModal = null;\n        this.reRender();\n    }\n\n    /**\n     * @typeParam C - the component type\n     */\n    private buildModal<C extends ComponentType>(\n        Component: C,\n        props?: ComponentProps<C>,\n        className?: string,\n        options?: IOptions<C>,\n    ): {\n        modal: IModal<C>;\n        closeDialog: IHandle<C>[\"close\"];\n        onFinishedProm: IHandle<C>[\"finished\"];\n    } {\n        const modal = {\n            onBeforeClose: options?.onBeforeClose,\n            className,\n\n            // these will be set below but we need an object reference to pass to getCloseFn before we can do that\n            elem: null,\n        } as IModal<C>;\n\n        const [closeDialog, onFinishedProm] = this.getCloseFn<C>(modal);\n\n        // don't attempt to reuse the same AsyncWrapper for different dialogs,\n        // otherwise we'll get confused.\n        const modalCount = this.counter++;\n\n        // Typescript doesn't like us passing props as any here, but we know that they are well typed due to the rigorous generics.\n        modal.elem = (\n            <AsyncWrapper key={modalCount} onFinished={closeDialog}>\n                <Component {...(props as any)} onFinished={closeDialog} />\n            </AsyncWrapper>\n        );\n        modal.close = closeDialog;\n\n        return { modal, closeDialog, onFinishedProm };\n    }\n\n    private getCloseFn<C extends ComponentType>(modal: IModal<C>): [IHandle<C>[\"close\"], IHandle<C>[\"finished\"]] {\n        modal.deferred = Promise.withResolvers<OnFinishedParams<C> | []>();\n        return [\n            async (...args: OnFinishedParams<C>): Promise<void> => {\n                if (modal.beforeClosePromise) {\n                    await modal.beforeClosePromise;\n                } else if (modal.onBeforeClose) {\n                    modal.beforeClosePromise = modal.onBeforeClose(modal.closeReason);\n                    const shouldClose = await modal.beforeClosePromise;\n                    modal.beforeClosePromise = undefined;\n                    if (!shouldClose) {\n                        return;\n                    }\n                }\n                modal.deferred?.resolve(args);\n                const i = this.modals.indexOf(modal);\n                if (i >= 0) {\n                    this.modals.splice(i, 1);\n                }\n\n                if (this.priorityModal === modal) {\n                    this.priorityModal = null;\n\n                    // XXX: This is destructive\n                    this.modals = [];\n                }\n\n                if (this.staticModal === modal) {\n                    this.staticModal = null;\n\n                    // XXX: This is destructive\n                    this.modals = [];\n                }\n\n                this.reRender();\n                this.emitClosed();\n            },\n            modal.deferred.promise,\n        ];\n    }\n\n    /**\n     * @callback onBeforeClose\n     * @param {string?} reason either \"backgroundClick\" or null\n     * @return {Promise<bool>} whether the dialog should close\n     */\n\n    /**\n     * Open a modal view.\n     *\n     * This can be used to display a react component which is loaded as an asynchronous\n     * webpack component. To do this, set 'loader' as:\n     *\n     *   (cb) => {\n     *       require(['<module>'], cb);\n     *   }\n     *\n     * @param component The component to render as a dialog. This component must accept an `onFinished` prop function as\n     *                  per the type {@link ComponentType}. If loading a component with esoteric dependencies consider\n     *                  using React.lazy to async load the component.\n     *                  e.g. `lazy(() => import('./MyComponent'))`\n     *\n     * @param props properties to pass to the displayed component. (We will also pass an `onFinished` property; when\n     *     called, that property will close the dialog and return the results to the caller via {@link IHandle.finished}.)\n     *\n     * @param className CSS class to apply to the modal wrapper\n     *\n     * @param isPriorityModal if true, this modal will be displayed regardless\n     *                                  of other modals that are currently in the stack.\n     *                                  Also, when closed, all modals will be removed\n     *                                  from the stack.\n     * @param isStaticModal if true, this modal will be displayed under other\n     *                                 modals in the stack. When closed, all modals will\n     *                                 also be removed from the stack. This is not compatible\n     *                                 with being a priority modal. Only one modal can be\n     *                                 static at a time.\n     * @param options? extra options for the dialog\n     * @param options.onBeforeClose a callback to decide whether to close the dialog\n     * @returns {@link IHandle} object.\n     */\n    public createDialog<C extends ComponentType>(\n        component: C,\n        props?: ComponentProps<C>,\n        className?: string,\n        isPriorityModal = false,\n        isStaticModal = false,\n        options: IOptions<C> = {},\n    ): IHandle<C> {\n        const beforeModal = this.getCurrentModal();\n        const { modal, closeDialog, onFinishedProm } = this.buildModal<C>(component, props, className, options);\n        if (isPriorityModal) {\n            // XXX: This is destructive\n            this.priorityModal = modal;\n        } else if (isStaticModal) {\n            // This is intentionally destructive\n            this.staticModal = modal;\n        } else {\n            this.modals.unshift(modal);\n        }\n\n        this.reRender();\n        this.emitIfChanged(beforeModal);\n\n        return {\n            close: closeDialog,\n            finished: onFinishedProm,\n        };\n    }\n\n    public appendDialog<C extends ComponentType>(\n        component: C,\n        props?: ComponentProps<C>,\n        className?: string,\n    ): IHandle<C> {\n        const beforeModal = this.getCurrentModal();\n        const { modal, closeDialog, onFinishedProm } = this.buildModal<C>(component, props, className, {});\n\n        this.modals.push(modal);\n\n        this.reRender();\n        this.emitIfChanged(beforeModal);\n\n        return {\n            close: closeDialog,\n            finished: onFinishedProm,\n        };\n    }\n\n    private emitIfChanged(beforeModal?: IModal<any>): void {\n        if (beforeModal !== this.getCurrentModal()) {\n            this.emit(ModalManagerEvent.Opened);\n        }\n    }\n\n    /**\n     * Emit the closed event\n     * @private\n     */\n    private emitClosed(): void {\n        this.emit(ModalManagerEvent.Closed);\n    }\n\n    private onBackgroundClick = (): void => {\n        const modal = this.getCurrentModal();\n        if (!modal) {\n            return;\n        }\n        // we want to pass a reason to the onBeforeClose\n        // callback, but close is currently defined to\n        // pass all number of arguments to the onFinished callback\n        // so, pass the reason to close through a member variable\n        modal.closeReason = \"backgroundClick\";\n        modal.close();\n        modal.closeReason = undefined;\n    };\n\n    private getCurrentModal(): IModal<any> {\n        return this.priorityModal ? this.priorityModal : this.modals[0] || this.staticModal;\n    }\n\n    private async reRender(): Promise<void> {\n        if (this.modals.length === 0 && !this.priorityModal && !this.staticModal) {\n            // If there is no modal to render, make all of Element available\n            // to screen reader users again\n            defaultDispatcher.dispatch({\n                action: \"aria_unhide_main_app\",\n            });\n            ModalManager.getOrCreateRoot().render(<></>);\n            ModalManager.getOrCreateStaticRoot().render(<></>);\n            return;\n        }\n\n        // Hide the content outside the modal to screen reader users\n        // so they won't be able to navigate into it and act on it using\n        // screen reader specific features\n        defaultDispatcher.dispatch({\n            action: \"aria_hide_main_app\",\n        });\n\n        if (this.staticModal) {\n            const classes = classNames(\"mx_Dialog_wrapper mx_Dialog_staticWrapper\", this.staticModal.className);\n\n            const staticDialog = (\n                <StrictMode>\n                    <TooltipProvider>\n                        <div className={classes}>\n                            <Glass className=\"mx_Dialog_border\">\n                                <div className=\"mx_Dialog\">{this.staticModal.elem}</div>\n                            </Glass>\n                            <div\n                                data-testid=\"dialog-background\"\n                                className=\"mx_Dialog_background mx_Dialog_staticBackground\"\n                                onClick={this.onBackgroundClick}\n                            />\n                        </div>\n                    </TooltipProvider>\n                </StrictMode>\n            );\n\n            ModalManager.getOrCreateStaticRoot().render(staticDialog);\n        } else {\n            // This is safe to call repeatedly if we happen to do that\n            ModalManager.getOrCreateStaticRoot().render(<></>);\n        }\n\n        const modal = this.getCurrentModal();\n        if (modal !== this.staticModal && !modal.hidden) {\n            const classes = classNames(\"mx_Dialog_wrapper\", modal.className, {\n                mx_Dialog_wrapperWithStaticUnder: this.staticModal,\n            });\n\n            const dialog = (\n                <StrictMode>\n                    <TooltipProvider>\n                        <div className={classes}>\n                            <Glass className=\"mx_Dialog_border\">\n                                <div className=\"mx_Dialog\">{modal.elem}</div>\n                            </Glass>\n                            <div\n                                data-testid=\"dialog-background\"\n                                className=\"mx_Dialog_background\"\n                                onClick={this.onBackgroundClick}\n                            />\n                        </div>\n                    </TooltipProvider>\n                </StrictMode>\n            );\n\n            ModalManager.getOrCreateRoot().render(dialog);\n        } else {\n            // This is safe to call repeatedly if we happen to do that\n            ModalManager.getOrCreateRoot().render(<></>);\n        }\n    }\n}\n\nif (!window.singletonModalManager) {\n    window.singletonModalManager = new ModalManager();\n}\nexport default window.singletonModalManager;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useCallback, useEffect, useRef, useState } from \"react\";\nimport {\n    type Room,\n    type MatrixEvent,\n    type RoomMember,\n    RoomEvent,\n    EventType,\n    MatrixEventEvent,\n} from \"matrix-js-sdk/src/matrix\";\nimport { Button, ToggleInput, Tooltip, TooltipProvider } from \"@vector-im/compound-web\";\nimport VideoCallIcon from \"@vector-im/compound-design-tokens/assets/web/icons/video-call-solid\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type IRTCNotificationContent } from \"matrix-js-sdk/src/matrixrtc\";\nimport { CheckIcon, VoiceCallIcon, CloseIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\nimport { AvatarWithDetails } from \"@element-hq/web-shared-components\";\n\nimport { _t } from \"../languageHandler\";\nimport RoomAvatar from \"../components/views/avatars/RoomAvatar\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport { type ViewRoomPayload } from \"../dispatcher/payloads/ViewRoomPayload\";\nimport { Action } from \"../dispatcher/actions\";\nimport ToastStore from \"../stores/ToastStore\";\nimport { LiveContentSummary, LiveContentType } from \"../components/views/rooms/LiveContentSummary\";\nimport { useCall, useParticipantCount } from \"../hooks/useCall\";\nimport AccessibleButton, { type ButtonEvent } from \"../components/views/elements/AccessibleButton\";\nimport { useDispatcher } from \"../hooks/useDispatcher\";\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport { type Call, CallEvent } from \"../models/Call\";\nimport LegacyCallHandler, { AudioID } from \"../LegacyCallHandler\";\nimport { useEventEmitter, useTypedEventEmitter } from \"../hooks/useEventEmitter\";\nimport { CallStore, CallStoreEvent } from \"../stores/CallStore\";\nimport DMRoomMap from \"../utils/DMRoomMap\";\n\n/**\n * Get the key for the incoming call toast. A combination of the call ID and room ID.\n * @param callId The ID of the call.\n * @param roomId The ID of the room.\n * @returns The key for the incoming call toast.\n */\nexport const getIncomingCallToastKey = (callId: string, roomId: string): string => `call_${callId}_${roomId}`;\n\n/**\n * Get the ts when the notification event was sent.\n * This can be either the origin_server_ts or a ts the sender of this event claims as\n * the time they sent it (sender_ts).\n * The origin_server_ts is the fallback if sender_ts seems wrong.\n * @param event The RTCNotification event.\n * @returns The timestamp to use as the expect start time to apply the `lifetime` to.\n */\nexport const getNotificationEventSendTs = (event: MatrixEvent): number => {\n    const content = event.getContent() as Partial<IRTCNotificationContent>;\n    const sendTs = content.sender_ts;\n    if (sendTs && Math.abs(sendTs - event.getTs()) >= 15000) {\n        logger.warn(\n            \"Received RTCNotification event. With large sender_ts origin_server_ts offset -> using origin_server_ts\",\n        );\n        return event.getTs();\n    }\n    return sendTs ?? event.getTs();\n};\nconst MAX_RING_TIME_MS = 90 * 1000;\n\ninterface JoinCallButtonWithCallProps {\n    onClick: (e: ButtonEvent) => void;\n    call: Call | null;\n    disabledTooltip: string | undefined;\n    isRinging: boolean;\n}\n\nfunction JoinCallButtonWithCall({ onClick, disabledTooltip, isRinging }: JoinCallButtonWithCallProps): JSX.Element {\n    return (\n        <Tooltip description={disabledTooltip ?? _t(\"voip|video_call\")}>\n            <Button\n                className=\"mx_IncomingCallToast_actionButton\"\n                onClick={onClick}\n                disabled={disabledTooltip != undefined}\n                kind=\"primary\"\n                Icon={CheckIcon}\n                size=\"sm\"\n            >\n                {isRinging ? _t(\"action|accept\") : _t(\"action|join\")}\n            </Button>\n        </Tooltip>\n    );\n}\n\ninterface DeclineCallButtonWithNotificationEventProps {\n    onDeclined: (e: ButtonEvent) => void;\n    notificationEvent: MatrixEvent;\n    room?: Room;\n}\n\nfunction DeclineCallButtonWithNotificationEvent({\n    notificationEvent,\n    room,\n    onDeclined,\n}: DeclineCallButtonWithNotificationEventProps): JSX.Element {\n    const [declining, setDeclining] = useState(false);\n    const onClick = useCallback(\n        async (e: ButtonEvent) => {\n            e.stopPropagation();\n            setDeclining(true);\n            await room?.client.sendRtcDecline(room.roomId, notificationEvent.getId() ?? \"\");\n            onDeclined(e);\n        },\n        [notificationEvent, onDeclined, room?.client, room?.roomId],\n    );\n    return (\n        <Tooltip description={_t(\"voip|decline_call\")}>\n            <Button\n                className=\"mx_IncomingCallToast_actionButton\"\n                onClick={onClick}\n                kind=\"primary\"\n                destructive\n                disabled={declining}\n                Icon={CloseIcon}\n                size=\"sm\"\n            >\n                {_t(\"action|decline\")}\n            </Button>\n        </Tooltip>\n    );\n}\n\ninterface Props {\n    /**\n     * A MatrixRTC notification event which has a content type of `IRTCNotificationContent`\n     */\n    notificationEvent: MatrixEvent;\n    /**\n     * The unique key of the toast notification, used to dismiss the toast if the\n     * notification expires for any reason.\n     */\n    toastKey: string;\n}\n\nexport function IncomingCallToast({ notificationEvent, toastKey }: Props): JSX.Element {\n    const roomId = notificationEvent.getRoomId()!;\n    // Use a partial type so ts still helps us to not miss any type checks.\n    const notificationContent = notificationEvent.getContent() as Partial<IRTCNotificationContent>;\n    const room = MatrixClientPeg.safeGet().getRoom(roomId) ?? undefined;\n    const call = useCall(roomId);\n    const [connectedCalls, setConnectedCalls] = useState<Call[]>(Array.from(CallStore.instance.connectedCalls));\n    useEventEmitter(CallStore.instance, CallStoreEvent.ConnectedCalls, () => {\n        setConnectedCalls(Array.from(CallStore.instance.connectedCalls));\n    });\n    const otherCallIsOngoing = connectedCalls.find((call) => call.roomId !== roomId);\n    const soundHasStarted = useRef<boolean>(false);\n    useEffect(() => {\n        // This section can race, so we use a ref to keep track of whether we have started trying to play.\n        // This is because `LegacyCallHandler.play` tries to load the sound and then play it asynchonously\n        // and `LegacyCallHandler.isPlaying` will not be `true` until the sound starts playing.\n        const isRingToast = notificationContent.notification_type === \"ring\";\n        if (isRingToast && !soundHasStarted.current && !LegacyCallHandler.instance.isPlaying(AudioID.Ring)) {\n            // Start ringing if not already.\n            soundHasStarted.current = true;\n            void LegacyCallHandler.instance.play(AudioID.Ring);\n        }\n    }, [notificationContent.notification_type, soundHasStarted]);\n\n    // Stop ringing on dismiss.\n    const dismissToast = useCallback((): void => {\n        ToastStore.sharedInstance().dismissToast(toastKey);\n        LegacyCallHandler.instance.pause(AudioID.Ring);\n    }, [toastKey]);\n\n    // Dismiss if the notification event or call event is redacted\n    useTypedEventEmitter(room, MatrixEventEvent.BeforeRedaction, (ev: MatrixEvent) => {\n        if ([ev.getId(), ev.getRelation()?.event_id].includes(ev.getId())) {\n            dismissToast();\n        }\n    });\n\n    // Dismiss if session got ended remotely.\n    const onCall = useCallback(\n        (call: Call, callRoomId: string): void => {\n            const roomId = notificationEvent.getRoomId();\n            if (!roomId && roomId !== callRoomId) return;\n            if (call === null || call.participants.size === 0) {\n                dismissToast();\n            }\n        },\n        [dismissToast, notificationEvent],\n    );\n\n    // Dismiss if session got declined remotely.\n    const onTimelineChange = useCallback(\n        (ev: MatrixEvent) => {\n            const userId = room?.client.getUserId();\n            if (\n                ev.getType() === EventType.RTCDecline &&\n                userId !== undefined &&\n                ev.getSender() === userId && // It is our decline not someone elses\n                ev.relationEventId === notificationEvent.getId() // The event declines this ringing toast.\n            ) {\n                dismissToast();\n            }\n        },\n        [dismissToast, notificationEvent, room?.client],\n    );\n\n    // Dismiss if another device from this user joins.\n    const onParticipantChange = useCallback(\n        (participants: Map<RoomMember, Set<string>>, prevParticipants: Map<RoomMember, Set<string>>) => {\n            if (Array.from(participants.keys()).some((p) => p.userId == room?.client.getUserId())) {\n                dismissToast();\n            }\n        },\n        [dismissToast, room?.client],\n    );\n\n    // Dismiss on timeout.\n    useEffect(() => {\n        const lifetime = notificationContent.lifetime ?? MAX_RING_TIME_MS;\n        const timeout = setTimeout(dismissToast, getNotificationEventSendTs(notificationEvent) + lifetime - Date.now());\n        return () => clearTimeout(timeout);\n    });\n\n    // Dismiss on viewing call.\n    useDispatcher(\n        defaultDispatcher,\n        useCallback(\n            (payload: ActionPayload) => {\n                if (payload.action === Action.ViewRoom && payload.room_id === roomId && payload.view_call) {\n                    dismissToast();\n                }\n            },\n            [roomId, dismissToast],\n        ),\n    );\n\n    const [skipLobbyToggle, setSkipLobbyToggle] = useState(true);\n\n    // Dismiss on clicking join.\n    // If the skip lobby option is undefined, it will use to the shift key state to decide if the lobby is skipped.\n    const onJoinClick = useCallback(\n        (e: ButtonEvent): void => {\n            e.stopPropagation();\n\n            // The toast will be automatically dismissed by the dispatcher callback above\n            defaultDispatcher.dispatch<ViewRoomPayload>({\n                action: Action.ViewRoom,\n                room_id: room?.roomId,\n                view_call: true,\n                skipLobby: (\"shiftKey\" in e && e.shiftKey) || skipLobbyToggle,\n                voiceOnly: notificationContent[\"m.call.intent\"] === \"audio\",\n                metricsTrigger: undefined,\n            });\n        },\n        [room, skipLobbyToggle, notificationContent],\n    );\n\n    // Dismiss on closing toast.\n    const onCloseClick = useCallback(\n        (e: ButtonEvent): void => {\n            e.stopPropagation();\n\n            dismissToast();\n        },\n        [dismissToast],\n    );\n\n    useEventEmitter(CallStore.instance, CallStoreEvent.Call, onCall);\n    useEventEmitter(call ?? undefined, CallEvent.Participants, onParticipantChange);\n    useEventEmitter(room, RoomEvent.Timeline, onTimelineChange);\n    const isVoice = notificationContent[\"m.call.intent\"] === \"audio\";\n    const otherUserId = DMRoomMap.shared().getUserIdForRoomId(roomId);\n    const participantCount = useParticipantCount(call);\n    const detailsInformation =\n        notificationContent.notification_type === \"ring\" ? (\n            <span>{otherUserId}</span>\n        ) : (\n            <LiveContentSummary\n                type={isVoice ? LiveContentType.Voice : LiveContentType.Video}\n                text={isVoice ? _t(\"common|voice\") : _t(\"common|video\")}\n                active={false}\n                participantCount={participantCount}\n            />\n        );\n\n    return (\n        <TooltipProvider>\n            <>\n                <div className=\"mx_IncomingCallToast_content\">\n                    {isVoice ? (\n                        <div className=\"mx_IncomingCallToast_message\">\n                            <VoiceCallIcon width=\"20px\" height=\"20px\" style={{ position: \"relative\", top: \"4px\" }} />{\" \"}\n                            {_t(\"voip|voice_call_incoming\")}\n                        </div>\n                    ) : (\n                        <div className=\"mx_IncomingCallToast_message\">\n                            <VideoCallIcon width=\"20px\" height=\"20px\" style={{ position: \"relative\", top: \"4px\" }} />{\" \"}\n                            {notificationContent.notification_type === \"ring\"\n                                ? _t(\"voip|video_call_incoming\")\n                                : _t(\"voip|video_call_started\")}\n                        </div>\n                    )}\n                    <AvatarWithDetails\n                        avatar={<RoomAvatar room={room ?? undefined} size=\"32px\" />}\n                        details={detailsInformation}\n                        title={room ? room.name : _t(\"voip|call_toast_unknown_room\")}\n                        className=\"mx_IncomingCallToast_AvatarWithDetails\"\n                    />\n                    {!isVoice && (\n                        <div className=\"mx_IncomingCallToast_toggleWithLabel\">\n                            <span>{_t(\"voip|skip_lobby_toggle_option\")}</span>\n                            <ToggleInput\n                                onChange={(e) => setSkipLobbyToggle(e.target.checked)}\n                                checked={skipLobbyToggle}\n                            />\n                        </div>\n                    )}\n                    <div className=\"mx_IncomingCallToast_buttons\">\n                        <DeclineCallButtonWithNotificationEvent\n                            notificationEvent={notificationEvent}\n                            room={room}\n                            onDeclined={onCloseClick}\n                        />\n                        <JoinCallButtonWithCall\n                            onClick={onJoinClick}\n                            call={call}\n                            isRinging={notificationContent.notification_type === \"ring\"}\n                            disabledTooltip={otherCallIsOngoing ? \"Ongoing call\" : undefined}\n                        />\n                    </div>\n                </div>\n                <AccessibleButton\n                    className=\"mx_IncomingCallToast_closeButton\"\n                    onClick={onCloseClick}\n                    title={_t(\"action|close\")}\n                >\n                    <CloseIcon />\n                </AccessibleButton>\n            </>\n        </TooltipProvider>\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Vector Creations Ltd\nCopyright 2017 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    MatrixEvent,\n    MatrixEventEvent,\n    type Room,\n    RoomEvent,\n    ClientEvent,\n    MsgType,\n    SyncState,\n    type SyncStateData,\n    type IRoomTimelineData,\n    M_LOCATION,\n    EventType,\n    TypedEventEmitter,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type PermissionChanged as PermissionChangedEvent } from \"@matrix-org/analytics-events/types/typescript/PermissionChanged\";\nimport { type SessionMembershipData, type IRTCNotificationContent } from \"matrix-js-sdk/src/matrixrtc\";\n\nimport { MatrixClientPeg } from \"./MatrixClientPeg\";\nimport { PosthogAnalytics } from \"./PosthogAnalytics\";\nimport SdkConfig from \"./SdkConfig\";\nimport PlatformPeg from \"./PlatformPeg\";\nimport * as TextForEvent from \"./TextForEvent\";\nimport * as Avatar from \"./Avatar\";\nimport dis from \"./dispatcher/dispatcher\";\nimport { _t } from \"./languageHandler\";\nimport Modal from \"./Modal\";\nimport SettingsStore from \"./settings/SettingsStore\";\nimport { hideToast as hideNotificationsToast } from \"./toasts/DesktopNotificationsToast\";\nimport { SettingLevel } from \"./settings/SettingLevel\";\nimport { isPushNotifyDisabled } from \"./settings/controllers/NotificationControllers\";\nimport UserActivity from \"./UserActivity\";\nimport { mediaFromMxc } from \"./customisations/Media\";\nimport ErrorDialog from \"./components/views/dialogs/ErrorDialog\";\nimport { SdkContextClass } from \"./contexts/SDKContext\";\nimport { localNotificationsAreSilenced, createLocalNotificationSettingsIfNeeded } from \"./utils/notifications\";\nimport { getIncomingCallToastKey, getNotificationEventSendTs, IncomingCallToast } from \"./toasts/IncomingCallToast\";\nimport ToastStore from \"./stores/ToastStore\";\nimport { stripPlainReply } from \"./utils/Reply\";\nimport { BackgroundAudio } from \"./audio/BackgroundAudio\";\n\n/*\n * Dispatches:\n * {\n *   action: \"notifier_enabled\",\n *   value: boolean\n * }\n */\n\nconst MAX_PENDING_ENCRYPTED = 20;\n\n/*\nOverride both the content body and the TextForEvent handler for specific msgtypes, in notifications.\nThis is useful when the content body contains fallback text that would explain that the client can't handle a particular\ntype of tile.\n*/\nconst msgTypeHandlers: Record<string, (event: MatrixEvent) => string | null> = {\n    [MsgType.KeyVerificationRequest]: (event: MatrixEvent) => {\n        const name = event.sender?.name;\n        return _t(\"notifier|m.key.verification.request\", { name });\n    },\n    [M_LOCATION.name]: (event: MatrixEvent) => {\n        return TextForEvent.textForLocationEvent(event)();\n    },\n    [M_LOCATION.altName]: (event: MatrixEvent) => {\n        return TextForEvent.textForLocationEvent(event)();\n    },\n    [MsgType.Audio]: (event: MatrixEvent): string | null => {\n        return TextForEvent.textForEvent(event, MatrixClientPeg.safeGet());\n    },\n};\n\nexport const enum NotifierEvent {\n    NotificationHiddenChange = \"notification_hidden_change\",\n}\n\ninterface EmittedEvents {\n    [NotifierEvent.NotificationHiddenChange]: (hidden: boolean) => void;\n}\n\nclass NotifierClass extends TypedEventEmitter<keyof EmittedEvents, EmittedEvents> {\n    private notifsByRoom: Record<string, Notification[]> = {};\n\n    // A list of event IDs that we've received but need to wait until\n    // they're decrypted until we decide whether to notify for them\n    // or not\n    private pendingEncryptedEventIds: string[] = [];\n\n    private toolbarHidden?: boolean;\n    private isSyncing?: boolean;\n\n    private backgroundAudio = new BackgroundAudio();\n\n    public notificationMessageForEvent(ev: MatrixEvent): string | null {\n        const msgType = ev.getContent().msgtype;\n        if (msgType && msgTypeHandlers.hasOwnProperty(msgType)) {\n            return msgTypeHandlers[msgType](ev);\n        }\n        return TextForEvent.textForEvent(ev, MatrixClientPeg.safeGet());\n    }\n\n    // XXX: exported for tests\n    public displayPopupNotification(ev: MatrixEvent, room: Room): void {\n        const plaf = PlatformPeg.get();\n        const cli = MatrixClientPeg.safeGet();\n        if (!plaf) {\n            return;\n        }\n        if (!plaf.supportsNotifications() || !plaf.maySendNotifications()) {\n            return;\n        }\n\n        if (localNotificationsAreSilenced(cli)) {\n            return;\n        }\n\n        let msg = this.notificationMessageForEvent(ev);\n        if (!msg) return;\n\n        let title: string | undefined;\n        if (!ev.sender || room.name === ev.sender.name) {\n            title = room.name;\n            // notificationMessageForEvent includes sender, but we already have the sender here\n            const msgType = ev.getContent().msgtype;\n            if (ev.getContent().body && (!msgType || !msgTypeHandlers.hasOwnProperty(msgType))) {\n                msg = stripPlainReply(ev.getContent().body);\n            }\n        } else if (ev.getType() === \"m.room.member\") {\n            // context is all in the message here, we don't need\n            // to display sender info\n            title = room.name;\n        } else if (ev.sender) {\n            title = ev.sender.name + \" (\" + room.name + \")\";\n            // notificationMessageForEvent includes sender, but we've just out sender in the title\n            const msgType = ev.getContent().msgtype;\n            if (ev.getContent().body && (!msgType || !msgTypeHandlers.hasOwnProperty(msgType))) {\n                msg = stripPlainReply(ev.getContent().body);\n            }\n        }\n\n        if (!title) return;\n\n        if (!this.isBodyEnabled()) {\n            msg = \"\";\n        }\n\n        let avatarUrl: string | null = null;\n        if (ev.sender && !SettingsStore.getValue(\"lowBandwidth\")) {\n            avatarUrl = Avatar.avatarUrlForMember(ev.sender, 40, 40, \"crop\");\n        }\n\n        const notif = plaf.displayNotification(title, msg!, avatarUrl, room, ev);\n\n        // if displayNotification returns non-null,  the platform supports\n        // clearing notifications later, so keep track of this.\n        if (notif) {\n            if (this.notifsByRoom[ev.getRoomId()!] === undefined) this.notifsByRoom[ev.getRoomId()!] = [];\n            this.notifsByRoom[ev.getRoomId()!].push(notif);\n        }\n    }\n\n    public getSoundForRoom(roomId: string): {\n        url: string;\n        name: string;\n        type: string;\n        size: number;\n    } | null {\n        // We do no caching here because the SDK caches setting\n        // and the browser will cache the sound.\n        const content = SettingsStore.getValue(\"notificationSound\", roomId);\n        if (!content) {\n            return null;\n        }\n\n        if (typeof content.url !== \"string\") {\n            logger.warn(`${roomId} has custom notification sound event, but no url string`);\n            return null;\n        }\n\n        if (!content.url.startsWith(\"mxc://\")) {\n            logger.warn(`${roomId} has custom notification sound event, but url is not a mxc url`);\n            return null;\n        }\n\n        // Ideally in here we could use MSC1310 to detect the type of file, and reject it.\n\n        const url = mediaFromMxc(content.url).srcHttp;\n        if (!url) {\n            logger.warn(\"Something went wrong when generating src http url for mxc\");\n            return null;\n        }\n\n        return {\n            url,\n            name: content.name,\n            type: content.type,\n            size: content.size,\n        };\n    }\n\n    // XXX: Exported for tests\n    public async playAudioNotification(ev: MatrixEvent, room: Room): Promise<void> {\n        const cli = MatrixClientPeg.safeGet();\n        if (localNotificationsAreSilenced(cli)) {\n            return;\n        }\n\n        // Play notification sound here\n        const sound = this.getSoundForRoom(room.roomId);\n        logger.log(`Got sound ${sound?.name || \"default\"} for ${room.roomId}`);\n\n        if (sound) {\n            await this.backgroundAudio.play(sound.url);\n        } else {\n            await this.backgroundAudio.pickFormatAndPlay(\"media/message\", [\"mp3\", \"ogg\"]);\n        }\n    }\n\n    public start(): void {\n        const cli = MatrixClientPeg.safeGet();\n        cli.on(RoomEvent.Timeline, this.onEvent);\n        cli.on(RoomEvent.Receipt, this.onRoomReceipt);\n        cli.on(MatrixEventEvent.Decrypted, this.onEventDecrypted);\n        cli.on(ClientEvent.Sync, this.onSyncStateChange);\n        this.toolbarHidden = false;\n        this.isSyncing = false;\n    }\n\n    public stop(): void {\n        if (MatrixClientPeg.get()) {\n            MatrixClientPeg.get()!.removeListener(RoomEvent.Timeline, this.onEvent);\n            MatrixClientPeg.get()!.removeListener(RoomEvent.Receipt, this.onRoomReceipt);\n            MatrixClientPeg.get()!.removeListener(MatrixEventEvent.Decrypted, this.onEventDecrypted);\n            MatrixClientPeg.get()!.removeListener(ClientEvent.Sync, this.onSyncStateChange);\n        }\n        this.isSyncing = false;\n    }\n\n    public supportsDesktopNotifications(): boolean {\n        return PlatformPeg.get()?.supportsNotifications() ?? false;\n    }\n\n    public setEnabled(enable: boolean, callback?: () => void): void {\n        const plaf = PlatformPeg.get();\n        if (!plaf) return;\n\n        // Dev note: We don't set the \"notificationsEnabled\" setting to true here because it is a\n        // calculated value. It is determined based upon whether or not the master rule is enabled\n        // and other flags. Setting it here would cause a circular reference.\n\n        // make sure that we persist the current setting audio_enabled setting\n        // before changing anything\n        if (SettingsStore.isLevelSupported(SettingLevel.DEVICE)) {\n            SettingsStore.setValue(\"audioNotificationsEnabled\", null, SettingLevel.DEVICE, this.isEnabled());\n        }\n\n        if (enable) {\n            // Attempt to get permission from user\n            plaf.requestNotificationPermission().then((result) => {\n                if (result !== \"granted\") {\n                    // The permission request was dismissed or denied\n                    // TODO: Support alternative branding in messaging\n                    const brand = SdkConfig.get().brand;\n                    const description =\n                        result === \"denied\"\n                            ? _t(\"settings|notifications|error_permissions_denied\", { brand })\n                            : _t(\"settings|notifications|error_permissions_missing\", {\n                                  brand,\n                              });\n                    Modal.createDialog(ErrorDialog, {\n                        title: _t(\"settings|notifications|error_title\"),\n                        description,\n                    });\n                    return;\n                }\n\n                if (callback) callback();\n\n                PosthogAnalytics.instance.trackEvent<PermissionChangedEvent>({\n                    eventName: \"PermissionChanged\",\n                    permission: \"Notification\",\n                    granted: true,\n                });\n                dis.dispatch({\n                    action: \"notifier_enabled\",\n                    value: true,\n                });\n            });\n        } else {\n            PosthogAnalytics.instance.trackEvent<PermissionChangedEvent>({\n                eventName: \"PermissionChanged\",\n                permission: \"Notification\",\n                granted: false,\n            });\n            dis.dispatch({\n                action: \"notifier_enabled\",\n                value: false,\n            });\n        }\n        // set the notifications_hidden flag, as the user has knowingly interacted\n        // with the setting we shouldn't nag them any further\n        this.setPromptHidden(true);\n    }\n\n    public isEnabled(): boolean {\n        return this.isPossible() && SettingsStore.getValue(\"notificationsEnabled\");\n    }\n\n    public isPossible(): boolean {\n        const plaf = PlatformPeg.get();\n        if (!plaf?.supportsNotifications()) return false;\n        if (!plaf.maySendNotifications()) return false;\n\n        return true; // possible, but not necessarily enabled\n    }\n\n    public isBodyEnabled(): boolean {\n        return this.isEnabled() && SettingsStore.getValue(\"notificationBodyEnabled\");\n    }\n\n    public isAudioEnabled(): boolean {\n        // We don't route Audio via the HTML Notifications API so it is possible regardless of other things\n        return SettingsStore.getValue(\"audioNotificationsEnabled\");\n    }\n\n    public setPromptHidden(hidden: boolean, persistent = true): void {\n        this.toolbarHidden = hidden;\n\n        hideNotificationsToast();\n\n        // update the info to localStorage for persistent settings\n        if (persistent && global.localStorage) {\n            global.localStorage.setItem(\"notifications_hidden\", String(hidden));\n        }\n        this.emit(NotifierEvent.NotificationHiddenChange, hidden);\n    }\n\n    public shouldShowPrompt(): boolean {\n        const client = MatrixClientPeg.get();\n        if (!client) {\n            return false;\n        }\n        const isGuest = client.isGuest();\n        return (\n            !isGuest &&\n            this.supportsDesktopNotifications() &&\n            !isPushNotifyDisabled() &&\n            !this.isEnabled() &&\n            !this.isPromptHidden()\n        );\n    }\n\n    private isPromptHidden(): boolean {\n        // Check localStorage for any such meta data\n        if (global.localStorage) {\n            return global.localStorage.getItem(\"notifications_hidden\") === \"true\";\n        }\n\n        return !!this.toolbarHidden;\n    }\n\n    // XXX: Exported for tests\n    public onSyncStateChange = (state: SyncState, prevState: SyncState | null, data?: SyncStateData): void => {\n        if (state === SyncState.Syncing) {\n            this.isSyncing = true;\n        } else if (state === SyncState.Stopped || state === SyncState.Error) {\n            this.isSyncing = false;\n        }\n\n        // wait for first non-cached sync to complete\n        if (![SyncState.Stopped, SyncState.Error].includes(state) && !data?.fromCache) {\n            createLocalNotificationSettingsIfNeeded(MatrixClientPeg.safeGet());\n        }\n    };\n\n    private onEvent = (\n        ev: MatrixEvent,\n        room: Room | undefined,\n        toStartOfTimeline: boolean | undefined,\n        removed: boolean,\n        data: IRoomTimelineData,\n    ): void => {\n        if (removed) return; // only notify for new events, not removed ones\n        if (!data.liveEvent || !!toStartOfTimeline) return; // only notify for new things, not old.\n        if (!this.isSyncing) return; // don't alert for any messages initially\n        if (ev.getSender() === MatrixClientPeg.safeGet().getUserId()) return;\n        if (data.timeline.getTimelineSet().threadListType !== null) return; // Ignore events on the thread list generated timelines\n\n        MatrixClientPeg.safeGet().decryptEventIfNeeded(ev);\n\n        // If it's an encrypted event and the type is still 'm.room.encrypted',\n        // it hasn't yet been decrypted, so wait until it is.\n        if (ev.isBeingDecrypted() || ev.isDecryptionFailure()) {\n            this.pendingEncryptedEventIds.push(ev.getId()!);\n            // don't let the list fill up indefinitely\n            while (this.pendingEncryptedEventIds.length > MAX_PENDING_ENCRYPTED) {\n                this.pendingEncryptedEventIds.shift();\n            }\n            return;\n        }\n\n        this.evaluateEvent(ev);\n    };\n\n    private onEventDecrypted = (ev: MatrixEvent): void => {\n        // 'decrypted' means the decryption process has finished: it may have failed,\n        // in which case it might decrypt soon if the keys arrive\n        if (ev.isDecryptionFailure()) return;\n\n        const idx = this.pendingEncryptedEventIds.indexOf(ev.getId()!);\n        if (idx === -1) return;\n\n        this.pendingEncryptedEventIds.splice(idx, 1);\n        this.evaluateEvent(ev);\n    };\n\n    private onRoomReceipt = (ev: MatrixEvent, room: Room): void => {\n        if (room.getUnreadNotificationCount() === 0) {\n            // ideally we would clear each notification when it was read,\n            // but we have no way, given a read receipt, to know whether\n            // the receipt comes before or after an event, so we can't\n            // do this. Instead, clear all notifications for a room once\n            // there are no notifs left in that room., which is not quite\n            // as good but it's something.\n            const plaf = PlatformPeg.get();\n            if (!plaf) return;\n            if (this.notifsByRoom[room.roomId] === undefined) return;\n            for (const notif of this.notifsByRoom[room.roomId]) {\n                plaf.clearNotification(notif);\n            }\n            delete this.notifsByRoom[room.roomId];\n        }\n    };\n\n    // XXX: exported for tests\n    public evaluateEvent(ev: MatrixEvent): void {\n        const roomId = ev.getRoomId()!;\n        const room = MatrixClientPeg.safeGet().getRoom(roomId);\n        if (!room) {\n            // e.g we are in the process of joining a room.\n            // Seen in the Playwright lazy-loading test.\n            return;\n        }\n\n        const actions = MatrixClientPeg.safeGet().getPushActionsForEvent(ev);\n\n        if (actions?.notify) {\n            this.performCustomEventHandling(ev);\n\n            const store = SdkContextClass.instance.roomViewStore;\n            const isViewingRoom = store.getRoomId() === room.roomId;\n            const threadId: string | undefined = ev.getId() !== ev.threadRootId ? ev.threadRootId : undefined;\n            const isViewingThread = store.getThreadId() === threadId;\n\n            const isViewingEventTimeline = isViewingRoom && (!threadId || isViewingThread);\n\n            if (isViewingEventTimeline && UserActivity.sharedInstance().userActiveRecently() && !Modal.hasDialogs()) {\n                // don't bother notifying as user was recently active in this room\n                return;\n            }\n\n            if (this.isEnabled()) {\n                this.displayPopupNotification(ev, room);\n            }\n            if (actions.tweaks.sound && this.isAudioEnabled()) {\n                PlatformPeg.get()?.loudNotification(ev, room);\n                this.playAudioNotification(ev, room);\n            }\n        }\n    }\n\n    /**\n     * Handle `EventType.RTCNotification` notifications.\n     * @param ev The notification event.\n     * @param toaster The toast store.\n     * @param room The room that contains the notification\n     * @returns A promise that will always resolve.\n     */\n    private async handleRTCNotification(ev: MatrixEvent, toaster: ToastStore, room: Room): Promise<void> {\n        // TODO: Use the call_id to get the *correct* call. We assume there is only one call per room here.\n        const rtcSession = room && room.client.matrixRTC.getRoomSession(room);\n        if (\n            rtcSession?.slotDescription?.application == \"m.call\" &&\n            rtcSession.memberships.some((membership) => membership.userId === room.client.getUserId())\n        ) {\n            // If we're already joined to the session, don't notify.\n            return;\n        }\n\n        // XXX: Should use parseCallNotificationContent once the types are exported.\n        const content = ev.getContent() as IRTCNotificationContent;\n        const roomId = ev.getRoomId();\n        const referencedMembershipEventId = ev.getRelation()?.event_id;\n\n        // Check maximum age of a call notification event that will trigger a ringing notification\n        if (Date.now() - getNotificationEventSendTs(ev) > content.lifetime) {\n            logger.warn(\"Received outdated RTCNotification event.\");\n            return;\n        }\n        if (!roomId) {\n            logger.warn(\"Could not get roomId for RTCNotification event\");\n            return;\n        }\n        if (!referencedMembershipEventId) {\n            logger.warn(\"Could not get referenced membership for notification\");\n            return;\n        }\n        if (content[\"m.relates_to\"].rel_type !== \"m.reference\") {\n            logger.warn(\"Ignored RTCNotification due to invalid rel_type\");\n            return;\n        }\n\n        let callMembership = room?.findEventById(referencedMembershipEventId);\n\n        if (!callMembership) {\n            // Attempt to fetch from the homeserver, if we do not have the event locally.\n            // This is a rare case as obviously the referenced event for a m.call notification must\n            // be sent first.\n            try {\n                callMembership = new MatrixEvent(await room.client.fetchRoomEvent(roomId, referencedMembershipEventId));\n            } catch (ex) {\n                logger.warn(`Call membership for notification could not be found`, ex);\n            }\n        }\n        // If the event could not be found even after requesting it from the homeserver.\n        if (!callMembership) {\n            // We will not show a call notification if there is no valid call membership.\n            logger.warn(\n                `Could not find call membership (${referencedMembershipEventId} ${roomId}) for notification event.`,\n            );\n            return;\n        }\n\n        // If we cannot determine the key, we'll accept it but assume it's empty string.\n        // This means if you have malformed notifications or call memberships your notifications\n        // will overwrite, but the solution to that is to use well-formed events.\n        const callId = callMembership.getContent<SessionMembershipData>().call_id ?? \"\";\n        const key = getIncomingCallToastKey(callId, roomId);\n\n        if (toaster.hasToast(key)) {\n            logger.debug(`Detected duplicate notification for call ${key}, ignoring`);\n            return;\n        }\n\n        toaster.addOrReplaceToast({\n            key,\n            priority: 100,\n            component: IncomingCallToast,\n            bodyClassName: \"mx_IncomingCallToast\",\n            props: { notificationEvent: ev },\n        });\n    }\n\n    /**\n     * Some events require special handling such as showing in-app toasts.\n     * This function may either create a toast or ignore the event based\n     * on current app state.\n     */\n    private performCustomEventHandling(ev: MatrixEvent): void {\n        const toaster = ToastStore.sharedInstance();\n        const cli = MatrixClientPeg.safeGet();\n        const room = cli.getRoom(ev.getRoomId());\n\n        if (room && EventType.RTCNotification === ev.getType()) {\n            // We don't need to await this.\n            void this.handleRTCNotification(ev, toaster, room);\n        }\n    }\n}\n\nif (!window.mxNotifier) {\n    window.mxNotifier = new NotifierClass();\n}\n\nexport default window.mxNotifier;\nexport const Notifier: NotifierClass = window.mxNotifier;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017 Vector Creations Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/** The types of page which can be shown by the LoggedInView */\nenum PageType {\n    HomePage = \"home_page\",\n    RoomView = \"room_view\",\n    UserView = \"user_view\",\n}\n\nexport default PageType;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type BasePlatform from \"./BasePlatform\";\n\n/*\n * Holds the current instance of the `Platform` to use across the codebase.\n * Looking for an `Platform`? Just look for the `PlatformPeg` on the peg board.\n * \"Peg\" is the literal meaning of something you hang something on. So you'll\n * find a `Platform` hanging on the `PlatformPeg`.\n *\n * Used by the code to do anything specific to the platform we're running on\n * (eg. web, electron). Platforms are provided by the app layer. This allows the\n * app layer to set a Platform without necessarily having to have a MatrixChat\n * object.\n */\nexport class PlatformPeg {\n    private platform: BasePlatform | null = null;\n    private platformPromiseWithResolvers = Promise.withResolvers<BasePlatform>();\n\n    /**\n     * Returns a promise for the Platform object for the application.\n     */\n    public get platformPromise(): Promise<BasePlatform> {\n        return this.platformPromiseWithResolvers.promise;\n    }\n\n    /**\n     * Returns the current Platform object for the application.\n     * This should be an instance of a class extending BasePlatform.\n     */\n    public get(): BasePlatform | null {\n        return this.platform;\n    }\n\n    /**\n     * Sets the current platform handler object to use for the application.\n     * @param {BasePlatform} platform an instance of a class extending BasePlatform.\n     */\n    public set(platform: BasePlatform): void {\n        this.platformPromiseWithResolvers.resolve(platform);\n        this.platform = platform;\n    }\n}\n\nif (!window.mxPlatformPeg) {\n    window.mxPlatformPeg = new PlatformPeg();\n}\nexport default window.mxPlatformPeg;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport posthog, { type CaptureOptions, type PostHog, type Properties } from \"posthog-js\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type UserProperties } from \"@matrix-org/analytics-events/types/typescript/UserProperties\";\nimport { type Signup } from \"@matrix-org/analytics-events/types/typescript/Signup\";\n\nimport PlatformPeg from \"./PlatformPeg\";\nimport SdkConfig from \"./SdkConfig\";\nimport { MatrixClientPeg } from \"./MatrixClientPeg\";\nimport SettingsStore from \"./settings/SettingsStore\";\nimport { type ScreenName } from \"./PosthogTrackers\";\nimport { type ActionPayload } from \"./dispatcher/payloads\";\nimport { Action } from \"./dispatcher/actions\";\nimport { type SettingUpdatedPayload } from \"./dispatcher/payloads/SettingUpdatedPayload\";\nimport dis from \"./dispatcher/dispatcher\";\nimport { Layout } from \"./settings/enums/Layout\";\n\n/* Posthog analytics tracking.\n *\n * Anonymity behaviour is as follows:\n *\n * - If Posthog isn't configured in `config.json`, events are not sent.\n * - If [Do Not Track](https://developer.mozilla.org/en-US/docs/Web/API/Navigator/doNotTrack) is\n *   enabled, events are not sent (this detection is built into posthog and turned on via the\n *   `respect_dnt` flag being passed to `posthog.init`).\n * - If the `feature_pseudonymous_analytics_opt_in` labs flag is `true`, track pseudonomously by maintaining\n *   a randomised analytics ID in account_data for that user (shared between devices) and sending it to posthog to\n     identify the user.\n * - Otherwise, if the existing `analyticsOptIn` flag is `true`, track anonymously, i.e. do not identify the user\n     using any identifier that would be consistent across devices.\n * - If both flags are false or not set, events are not sent.\n */\n\nexport interface IPosthogEvent {\n    // The event name that will be used by PostHog. Event names should use camelCase.\n    eventName: string;\n\n    // do not allow these to be sent manually, we enqueue them all for caching purposes\n    $set?: void;\n    $set_once?: void;\n}\n\nexport enum Anonymity {\n    Disabled,\n    Anonymous,\n    Pseudonymous,\n}\n\nconst whitelistedScreens = new Set([\n    \"register\",\n    \"login\",\n    \"forgot_password\",\n    \"soft_logout\",\n    \"new\",\n    \"settings\",\n    \"welcome\",\n    \"home\",\n    \"start\",\n    \"directory\",\n    \"start_sso\",\n    \"start_cas\",\n    \"complete_security\",\n    \"post_registration\",\n    \"room\",\n    \"user\",\n]);\n\nexport function getRedactedCurrentLocation(origin: string, hash: string, pathname: string): string {\n    // Redact PII from the current location.\n    // For known screens, assumes a URL structure of /<screen name>/might/be/pii\n    if (origin.startsWith(\"file://\")) {\n        pathname = \"/<redacted_file_scheme_url>/\";\n    }\n\n    let hashStr;\n    if (hash == \"\") {\n        hashStr = \"\";\n    } else {\n        let [beforeFirstSlash, screen] = hash.split(\"/\");\n\n        if (!whitelistedScreens.has(screen)) {\n            screen = \"<redacted_screen_name>\";\n        }\n\n        hashStr = `${beforeFirstSlash}/${screen}/<redacted>`;\n    }\n    return origin + pathname + hashStr;\n}\n\ninterface PlatformProperties {\n    appVersion: string;\n    appPlatform: string;\n}\n\nexport class PosthogAnalytics {\n    /* Wrapper for Posthog analytics.\n     * 3 modes of anonymity are supported, governed by this.anonymity\n     * - Anonymity.Disabled means *no data* is passed to posthog\n     * - Anonymity.Anonymous means no identifier is passed to posthog\n     * - Anonymity.Pseudonymous means an analytics ID stored in account_data and shared between devices\n     *   is passed to posthog.\n     *\n     * To update anonymity, call updateAnonymityFromSettings() or you can set it directly via setAnonymity().\n     *\n     * To pass an event to Posthog:\n     *\n     * 1. Declare a type for the event, extending IAnonymousEvent or IPseudonymousEvent.\n     * 2. Call the appropriate track*() method. Pseudonymous events will be dropped when anonymity is\n     *    Anonymous or Disabled; Anonymous events will be dropped when anonymity is Disabled.\n     */\n\n    private anonymity = Anonymity.Disabled;\n    // set true during the constructor if posthog config is present, otherwise false\n    private readonly enabled: boolean = false;\n    private static _instance: PosthogAnalytics | null = null;\n    private platformSuperProperties: Properties = {};\n    public static readonly ANALYTICS_EVENT_TYPE = \"im.vector.analytics\";\n    private propertiesForNextEvent: Partial<Record<\"$set\" | \"$set_once\", UserProperties>> = {};\n    private userPropertyCache: UserProperties = {};\n    private authenticationType: Signup[\"authenticationType\"] = \"Other\";\n    private watchSettingRef?: string;\n\n    // Will be set when the matrixClient is passed to the analytics object (e.g. on login).\n    private currentCryptoBackend?: \"Rust\" | \"Legacy\" = undefined;\n\n    public static get instance(): PosthogAnalytics {\n        if (!this._instance) {\n            this._instance = new PosthogAnalytics(posthog);\n        }\n        return this._instance;\n    }\n\n    public constructor(private readonly posthog: PostHog) {\n        const posthogConfig = SdkConfig.getObject(\"posthog\");\n        if (posthogConfig) {\n            this.posthog.init(posthogConfig.get(\"project_api_key\"), {\n                api_host: posthogConfig.get(\"api_host\"),\n                autocapture: false,\n                mask_all_text: true,\n                mask_all_element_attributes: true,\n                // This only triggers on page load, which for our SPA isn't particularly useful.\n                // Plus, the .capture call originating from somewhere in posthog makes it hard\n                // to redact URLs, which requires async code.\n                //\n                // To raise this manually, just call .capture(\"$pageview\") or posthog.capture_pageview.\n                capture_pageview: false,\n                sanitize_properties: this.sanitizeProperties,\n                respect_dnt: true,\n                advanced_disable_decide: true,\n            });\n            this.enabled = true;\n        } else {\n            this.enabled = false;\n        }\n\n        dis.register(this.onAction);\n        SettingsStore.monitorSetting(\"layout\", null);\n        SettingsStore.monitorSetting(\"useCompactLayout\", null);\n        this.onLayoutUpdated();\n        this.updateCryptoSuperProperty();\n    }\n\n    private onLayoutUpdated = (): void => {\n        let layout: UserProperties[\"WebLayout\"];\n\n        switch (SettingsStore.getValue(\"layout\")) {\n            case Layout.IRC:\n                layout = \"IRC\";\n                break;\n            case Layout.Bubble:\n                layout = \"Bubble\";\n                break;\n            case Layout.Group:\n                layout = SettingsStore.getValue(\"useCompactLayout\") ? \"Compact\" : \"Group\";\n                break;\n        }\n\n        // This is known to clobber other devices but is a good enough solution\n        // to get an idea of how much use each layout gets.\n        this.setProperty(\"WebLayout\", layout);\n    };\n\n    private onAction = (payload: ActionPayload): void => {\n        if (payload.action !== Action.SettingUpdated) return;\n        const settingsPayload = payload as SettingUpdatedPayload;\n        if ([\"layout\", \"useCompactLayout\"].includes(settingsPayload.settingName)) {\n            this.onLayoutUpdated();\n        }\n    };\n\n    // we persist the last `$screen_name` and send it for all events until it is replaced\n    private lastScreen: ScreenName = \"Loading\";\n\n    private sanitizeProperties = (properties: Properties, eventName: string): Properties => {\n        // Callback from posthog to sanitize properties before sending them to the server.\n        //\n        // Here we sanitize posthog's built in properties which leak PII e.g. url reporting.\n        // See utils.js _.info.properties in posthog-js.\n\n        if (eventName === \"$pageview\") {\n            this.lastScreen = properties[\"$current_url\"];\n        }\n        // We inject a screen identifier in $current_url as per https://posthog.com/tutorials/spa\n        properties[\"$current_url\"] = this.lastScreen;\n\n        if (this.anonymity == Anonymity.Anonymous) {\n            // drop referrer information for anonymous users\n            properties[\"$referrer\"] = null;\n            properties[\"$referring_domain\"] = null;\n            properties[\"$initial_referrer\"] = null;\n            properties[\"$initial_referring_domain\"] = null;\n\n            // drop device ID, which is a UUID persisted in local storage\n            properties[\"$device_id\"] = null;\n        }\n\n        return properties;\n    };\n\n    private registerSuperProperties(properties: Properties): void {\n        if (this.enabled) {\n            this.posthog.register(properties);\n        }\n    }\n\n    private static async getPlatformProperties(): Promise<Partial<PlatformProperties>> {\n        const platform = PlatformPeg.get();\n        let appVersion: string | undefined;\n        try {\n            appVersion = await platform?.getAppVersion();\n        } catch {\n            // this happens if no version is set i.e. in dev\n            appVersion = \"unknown\";\n        }\n\n        return {\n            appVersion,\n            appPlatform: platform?.getHumanReadableName(),\n        };\n    }\n\n    // eslint-disable-nextline no-unused-vars\n    private capture(eventName: string, properties: Properties, options?: CaptureOptions): void {\n        if (!this.enabled) {\n            return;\n        }\n        const { origin, hash, pathname } = window.location;\n        properties[\"redactedCurrentUrl\"] = getRedactedCurrentLocation(origin, hash, pathname);\n        this.posthog.capture(eventName, { ...this.propertiesForNextEvent, ...properties }, options);\n        this.propertiesForNextEvent = {};\n    }\n\n    public isEnabled(): boolean {\n        return this.enabled;\n    }\n\n    public setAnonymity(anonymity: Anonymity): void {\n        // Update this.anonymity.\n        // This is public for testing purposes, typically you want to call updateAnonymityFromSettings\n        // to ensure this value is in step with the user's settings.\n        if (this.enabled && (anonymity == Anonymity.Disabled || anonymity == Anonymity.Anonymous)) {\n            // when transitioning to Disabled or Anonymous ensure we clear out any prior state\n            // set in posthog e.g. distinct ID\n            this.posthog.reset();\n            // Restore any previously set platform super properties\n            this.registerSuperProperties(this.platformSuperProperties);\n        }\n        this.anonymity = anonymity;\n        // update anyhow, no-op if not enabled or Disabled.\n        this.updateCryptoSuperProperty();\n    }\n\n    private static getRandomAnalyticsId(): string {\n        return [...crypto.getRandomValues(new Uint8Array(16))].map((c) => c.toString(16)).join(\"\");\n    }\n\n    public async identifyUser(client: MatrixClient, analyticsIdGenerator: () => string): Promise<void> {\n        if (this.anonymity == Anonymity.Pseudonymous) {\n            // Check the user's account_data for an analytics ID to use. Storing the ID in account_data allows\n            // different devices to send the same ID.\n            try {\n                const accountData = await client.getAccountDataFromServer(PosthogAnalytics.ANALYTICS_EVENT_TYPE);\n                let analyticsID = accountData?.id;\n                if (!analyticsID) {\n                    // Couldn't retrieve an analytics ID from user settings, so create one and set it on the server.\n                    // Note there's a race condition here - if two devices do these steps at the same time, last write\n                    // wins, and the first writer will send tracking with an ID that doesn't match the one on the server\n                    // until the next time account data is refreshed and this function is called (most likely on next\n                    // page load). This will happen pretty infrequently, so we can tolerate the possibility.\n                    analyticsID = analyticsIdGenerator();\n                    await client.setAccountData(PosthogAnalytics.ANALYTICS_EVENT_TYPE, {\n                        id: analyticsID,\n                        ...accountData,\n                    });\n                }\n                if (this.posthog.get_distinct_id() === analyticsID) {\n                    // No point identifying again\n                    return;\n                }\n                if (this.posthog.persistence?.get_property(\"$user_state\") === \"identified\") {\n                    // Analytics ID has changed, reset as Posthog will refuse to merge in this case\n                    this.posthog.reset();\n                }\n                this.posthog.identify(analyticsID);\n            } catch (e) {\n                // The above could fail due to network requests, but not essential to starting the application,\n                // so swallow it.\n                logger.log(\"Unable to identify user for tracking\", e);\n            }\n        }\n    }\n\n    public getAnonymity(): Anonymity {\n        return this.anonymity;\n    }\n\n    public logout(): void {\n        if (this.enabled) {\n            this.posthog.reset();\n        }\n        SettingsStore.unwatchSetting(this.watchSettingRef);\n        this.setAnonymity(Anonymity.Disabled);\n    }\n\n    public trackEvent<E extends IPosthogEvent>({ eventName, ...properties }: E, options?: CaptureOptions): void {\n        if (this.anonymity == Anonymity.Disabled || this.anonymity == Anonymity.Anonymous) return;\n        this.capture(eventName, properties, options);\n    }\n\n    public setProperty<K extends keyof UserProperties>(key: K, value: UserProperties[K]): void {\n        if (this.userPropertyCache[key] === value) return; // nothing to do\n        this.userPropertyCache[key] = value;\n\n        if (!this.propertiesForNextEvent[\"$set\"]) {\n            this.propertiesForNextEvent[\"$set\"] = {};\n        }\n        this.propertiesForNextEvent[\"$set\"][key] = value;\n    }\n\n    public setPropertyOnce<K extends keyof UserProperties>(key: K, value: UserProperties[K]): void {\n        if (this.userPropertyCache[key]) return; // nothing to do\n        this.userPropertyCache[key] = value;\n\n        if (!this.propertiesForNextEvent[\"$set_once\"]) {\n            this.propertiesForNextEvent[\"$set_once\"] = {};\n        }\n        this.propertiesForNextEvent[\"$set_once\"][key] = value;\n    }\n\n    public async updatePlatformSuperProperties(): Promise<void> {\n        // Update super properties in posthog with our platform (app version, platform).\n        // These properties will be subsequently passed in every event.\n        //\n        // This only needs to be done once per page lifetime. Note that getPlatformProperties\n        // is async and can involve a network request if we are running in a browser.\n        this.platformSuperProperties = await PosthogAnalytics.getPlatformProperties();\n        this.registerSuperProperties(this.platformSuperProperties);\n    }\n\n    private updateCryptoSuperProperty(): void {\n        if (!this.enabled || this.anonymity === Anonymity.Disabled) return;\n        // Update super property for cryptoSDK in posthog.\n        // This property will be subsequently passed in every event.\n        if (this.currentCryptoBackend) {\n            this.registerSuperProperties({ cryptoSDK: this.currentCryptoBackend });\n        }\n    }\n\n    public async updateAnonymityFromSettings(client: MatrixClient, pseudonymousOptIn: boolean): Promise<void> {\n        // Temporary until we have migration code to switch crypto sdk.\n        if (client.getCrypto()) {\n            const cryptoVersion = client.getCrypto()!.getVersion();\n            // version for rust is something like \"Rust SDK 0.6.0 (9c6b550), Vodozemac 0.5.0\"\n            // for legacy it will be 'Olm x.x.x\"\n            if (cryptoVersion.includes(\"Rust SDK\")) {\n                this.currentCryptoBackend = \"Rust\";\n            } else {\n                this.currentCryptoBackend = \"Legacy\";\n            }\n        }\n\n        // Update this.anonymity based on the user's analytics opt-in settings\n        const anonymity = pseudonymousOptIn ? Anonymity.Pseudonymous : Anonymity.Disabled;\n        this.setAnonymity(anonymity);\n        if (anonymity === Anonymity.Pseudonymous) {\n            await this.identifyUser(client, PosthogAnalytics.getRandomAnalyticsId);\n            if (MatrixClientPeg.currentUserIsJustRegistered()) {\n                this.trackNewUserEvent();\n            }\n        }\n\n        if (anonymity !== Anonymity.Disabled) {\n            await this.updatePlatformSuperProperties();\n            this.updateCryptoSuperProperty();\n        }\n    }\n\n    public startListeningToSettingsChanges(client: MatrixClient): void {\n        // Listen to account data changes from sync so we can observe changes to relevant flags and update.\n        // This is called -\n        //  * On page load, when the account data is first received by sync\n        //  * On login\n        //  * When another device changes account data\n        //  * When the user changes their preferences on this device\n        // Note that for new accounts, pseudonymousAnalyticsOptIn won't be set, so updateAnonymityFromSettings\n        // won't be called (i.e. this.anonymity will be left as the default, until the setting changes)\n        this.watchSettingRef = SettingsStore.watchSetting(\n            \"pseudonymousAnalyticsOptIn\",\n            null,\n            (originalSettingName, changedInRoomId, atLevel, newValueAtLevel, newValue) => {\n                this.updateAnonymityFromSettings(client, !!newValue);\n            },\n        );\n    }\n\n    public setAuthenticationType(authenticationType: Signup[\"authenticationType\"]): void {\n        this.authenticationType = authenticationType;\n    }\n\n    private trackNewUserEvent(): void {\n        // This is the only event that could have occured before analytics opt-in\n        // that we want to accumulate before the user has given consent\n        // All other scenarios should not track a user before they have given\n        // explicit consent that they are ok with their analytics data being collected\n        const options: CaptureOptions = {};\n        const registrationTime = parseInt(window.localStorage.getItem(\"mx_registration_time\")!, 10);\n        if (!isNaN(registrationTime)) {\n            options.timestamp = new Date(registrationTime);\n        }\n\n        return this.trackEvent<Signup>(\n            {\n                eventName: \"Signup\",\n                authenticationType: this.authenticationType,\n            },\n            options,\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { PureComponent, type SyntheticEvent } from \"react\";\nimport { type WebScreen as ScreenEvent } from \"@matrix-org/analytics-events/types/typescript/WebScreen\";\nimport { type Interaction as InteractionEvent } from \"@matrix-org/analytics-events/types/typescript/Interaction\";\nimport { type PinUnpinAction } from \"@matrix-org/analytics-events/types/typescript/PinUnpinAction\";\n\nimport PageType from \"./PageTypes\";\nimport Views from \"./Views\";\nimport { PosthogAnalytics } from \"./PosthogAnalytics\";\n\nexport type ScreenName = ScreenEvent[\"$current_url\"];\nexport type InteractionName = InteractionEvent[\"name\"];\n\nconst notLoggedInMap: Record<Exclude<Views, Views.LOGGED_IN>, ScreenName> = {\n    [Views.LOADING]: \"Loading\",\n    [Views.CONFIRM_LOCK_THEFT]: \"ConfirmStartup\",\n    [Views.WELCOME]: \"Welcome\",\n    [Views.LOGIN]: \"Login\",\n    [Views.REGISTER]: \"Register\",\n    [Views.FORGOT_PASSWORD]: \"ForgotPassword\",\n    [Views.COMPLETE_SECURITY]: \"CompleteSecurity\",\n    [Views.E2E_SETUP]: \"E2ESetup\",\n    [Views.PENDING_CLIENT_START]: \"Loading\",\n    [Views.SOFT_LOGOUT]: \"SoftLogout\",\n    [Views.LOCK_STOLEN]: \"SessionLockStolen\",\n};\n\nconst loggedInPageTypeMap: Record<PageType | string, ScreenName> = {\n    [PageType.HomePage]: \"Home\",\n    [PageType.RoomView]: \"Room\",\n    [PageType.UserView]: \"User\",\n};\n\nexport default class PosthogTrackers {\n    private static internalInstance: PosthogTrackers;\n\n    public static get instance(): PosthogTrackers {\n        if (!PosthogTrackers.internalInstance) {\n            PosthogTrackers.internalInstance = new PosthogTrackers();\n        }\n        return PosthogTrackers.internalInstance;\n    }\n\n    private view: Views = Views.LOADING;\n    private pageType?: PageType | string;\n    private override?: ScreenName;\n\n    public trackPageChange(view: Views, pageType: PageType | string | undefined, durationMs: number): void {\n        this.view = view;\n        this.pageType = pageType;\n        if (this.override) return;\n        this.trackPage(durationMs);\n    }\n\n    private trackPage(durationMs?: number): void {\n        const screenName =\n            this.view === Views.LOGGED_IN ? loggedInPageTypeMap[this.pageType!] : notLoggedInMap[this.view];\n        PosthogAnalytics.instance.trackEvent<ScreenEvent>({\n            eventName: \"$pageview\",\n            $current_url: screenName,\n            durationMs,\n        });\n    }\n\n    public trackOverride(screenName: ScreenName): void {\n        if (!screenName) return;\n        this.override = screenName;\n        PosthogAnalytics.instance.trackEvent<ScreenEvent>({\n            eventName: \"$pageview\",\n            $current_url: screenName,\n        });\n    }\n\n    public clearOverride(screenName: ScreenName): void {\n        if (screenName !== this.override) return;\n        this.override = undefined;\n        this.trackPage();\n    }\n\n    public static trackInteraction(name: InteractionName, ev?: SyntheticEvent | Event, index?: number): void {\n        let interactionType: InteractionEvent[\"interactionType\"];\n        if (ev?.type === \"click\") {\n            interactionType = \"Pointer\";\n        } else if (ev?.type.startsWith(\"key\")) {\n            interactionType = \"Keyboard\";\n        }\n\n        PosthogAnalytics.instance.trackEvent<InteractionEvent>({\n            eventName: \"Interaction\",\n            interactionType,\n            index,\n            name,\n        });\n    }\n\n    /**\n     * Track a pin or unpin action on a message.\n     * @param kind - Is pin or unpin.\n     * @param from - From where the action is triggered.\n     */\n    public static trackPinUnpinMessage(kind: PinUnpinAction[\"kind\"], from: PinUnpinAction[\"from\"]): void {\n        PosthogAnalytics.instance.trackEvent<PinUnpinAction>({\n            eventName: \"PinUnpinAction\",\n            kind,\n            from,\n        });\n    }\n}\n\nexport class PosthogScreenTracker extends PureComponent<{ screenName: ScreenName }> {\n    public componentDidMount(): void {\n        PosthogTrackers.instance.trackOverride(this.props.screenName);\n    }\n\n    public componentDidUpdate(): void {\n        // We do not clear the old override here so that we do not send the non-override screen as a transition\n        PosthogTrackers.instance.trackOverride(this.props.screenName);\n    }\n\n    public componentWillUnmount(): void {\n        PosthogTrackers.instance.clearOverride(this.props.screenName);\n    }\n\n    public render(): React.ReactNode {\n        return null; // no need to render anything, we just need to hook into the React lifecycle\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, EventStatus, type Room, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport dis from \"./dispatcher/dispatcher\";\n\nexport default class Resend {\n    public static resendUnsentEvents(room: Room): Promise<void[]> {\n        return Promise.all(\n            room\n                .getPendingEvents()\n                .filter(function (ev: MatrixEvent) {\n                    return ev.status === EventStatus.NOT_SENT;\n                })\n                .map(function (event: MatrixEvent) {\n                    return Resend.resend(room.client, event);\n                }),\n        );\n    }\n\n    public static cancelUnsentEvents(room: Room): void {\n        room.getPendingEvents()\n            .filter(function (ev: MatrixEvent) {\n                return ev.status === EventStatus.NOT_SENT;\n            })\n            .forEach(function (event: MatrixEvent) {\n                Resend.removeFromQueue(room.client, event);\n            });\n    }\n\n    public static resend(client: MatrixClient, event: MatrixEvent): Promise<void> {\n        const room = client.getRoom(event.getRoomId())!;\n        return client.resendEvent(event, room).then(\n            function (res) {\n                dis.dispatch({\n                    action: \"message_sent\",\n                    event: event,\n                });\n            },\n            function (err: Error) {\n                // XXX: temporary logging to try to diagnose\n                // https://github.com/vector-im/element-web/issues/3148\n                logger.log(\"Resend got send failure: \" + err.name + \"(\" + err + \")\");\n            },\n        );\n    }\n\n    public static removeFromQueue(client: MatrixClient, event: MatrixEvent): void {\n        client.cancelPendingEvent(event);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017 Vector Creations Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { _t } from \"./languageHandler\";\n\nexport function levelRoleMap(usersDefault: number): Record<number | \"undefined\", string> {\n    return {\n        undefined: _t(\"power_level|default\"),\n        0: _t(\"power_level|restricted\"),\n        [usersDefault]: _t(\"power_level|default\"),\n        50: _t(\"power_level|moderator\"),\n        100: _t(\"power_level|admin\"),\n    };\n}\n\nexport function textualPowerLevel(level: number, usersDefault: number): string {\n    const LEVEL_ROLE_MAP = levelRoleMap(usersDefault);\n    if (LEVEL_ROLE_MAP[level]) {\n        return LEVEL_ROLE_MAP[level];\n    } else {\n        return _t(\"power_level|custom\", { level });\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\ntype CacheResult = { roomId: string; viaServers: string[] };\n\n/**\n * This is meant to be a cache of room alias to room ID so that moving between\n * rooms happens smoothly (for example using browser back / forward buttons).\n *\n * For the moment, it's in memory only and so only applies for the current\n * session for simplicity, but could be extended further in the future.\n *\n * A similar thing could also be achieved via `pushState` with a state object,\n * but keeping it separate like this seems easier in case we do want to extend.\n */\nconst cache = new Map<string, CacheResult>();\n\nexport function storeRoomAliasInCache(alias: string, roomId: string, viaServers: string[]): void {\n    cache.set(alias, { roomId, viaServers });\n}\n\nexport function getCachedRoomIdForAlias(alias: string): CacheResult | undefined {\n    return cache.get(alias);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2016-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ComponentProps } from \"react\";\nimport { EventType, type MatrixClient, type MatrixEvent, type Room, type User } from \"matrix-js-sdk/src/matrix\";\n\nimport MultiInviter, { type CompletionStates, type MultiInviterOptions } from \"./utils/MultiInviter\";\nimport Modal from \"./Modal\";\nimport { _t } from \"./languageHandler\";\nimport InviteDialog from \"./components/views/dialogs/InviteDialog\";\nimport BaseAvatar from \"./components/views/avatars/BaseAvatar\";\nimport { mediaFromMxc } from \"./customisations/Media\";\nimport ErrorDialog from \"./components/views/dialogs/ErrorDialog\";\nimport { InviteKind } from \"./components/views/dialogs/InviteDialogTypes\";\nimport { type Member } from \"./utils/direct-messages\";\n\nexport interface IInviteResult {\n    states: CompletionStates;\n    inviter: MultiInviter;\n}\n\n/**\n * Invites multiple addresses to a room.\n *\n * Simpler interface to {@link MultiInviter}.\n *\n * Any failures are returned via the `states` in the result.\n *\n * @param {string} roomId The ID of the room to invite to\n * @param {string[]} addresses Array of strings of addresses to invite. May be matrix IDs or 3pids.\n * @param options Options object.\n * @returns {Promise} Promise\n */\nexport async function inviteMultipleToRoom(\n    client: MatrixClient,\n    roomId: string,\n    addresses: string[],\n    options: MultiInviterOptions = {},\n): Promise<IInviteResult> {\n    const inviter = new MultiInviter(client, roomId, options);\n    return { states: await inviter.invite(addresses), inviter };\n}\n\nexport function showStartChatInviteDialog(initialText = \"\"): void {\n    // This dialog handles the room creation internally - we don't need to worry about it.\n    Modal.createDialog(\n        InviteDialog,\n        { kind: InviteKind.Dm, initialText },\n        /*className=*/ \"mx_InviteDialog_flexWrapper\",\n        /*isPriority=*/ false,\n        /*isStatic=*/ true,\n    );\n}\n\nexport function showRoomInviteDialog(roomId: string, initialText = \"\"): void {\n    // This dialog handles the room creation internally - we don't need to worry about it.\n    Modal.createDialog(\n        InviteDialog,\n        {\n            kind: InviteKind.Invite,\n            initialText,\n            roomId,\n        } as Omit<ComponentProps<typeof InviteDialog>, \"onFinished\">,\n        /*className=*/ \"mx_InviteDialog_flexWrapper\",\n        /*isPriority=*/ false,\n        /*isStatic=*/ true,\n    );\n}\n\n/**\n * Checks if the given MatrixEvent is a valid 3rd party user invite.\n * @param {MatrixEvent} event The event to check\n * @returns {boolean} True if valid, false otherwise\n */\nexport function isValid3pidInvite(event: MatrixEvent): boolean {\n    if (!event || event.getType() !== EventType.RoomThirdPartyInvite) return false;\n\n    // any events without these keys are not valid 3pid invites, so we ignore them\n    const requiredKeys = [\"key_validity_url\", \"public_key\", \"display_name\"];\n    if (requiredKeys.some((key) => !event.getContent()[key])) {\n        return false;\n    }\n\n    // Valid enough by our standards\n    return true;\n}\n\nexport function showAnyInviteErrors(\n    states: CompletionStates,\n    room: Room,\n    inviter: MultiInviter,\n    userMap?: Map<string, Member>,\n): boolean {\n    // Show user any errors\n    const failedUsers = Object.keys(states).filter((a) => states[a] === \"error\");\n    if (failedUsers.length === 1 && inviter.fatal) {\n        // Just get the first message because there was a fatal problem on the first\n        // user. This usually means that no other users were attempted, making it\n        // pointless for us to list who failed exactly.\n        Modal.createDialog(ErrorDialog, {\n            title: _t(\"invite|room_failed_title\", { roomName: room.name }),\n            description: inviter.getErrorText(failedUsers[0]),\n        });\n        return false;\n    } else {\n        const errorList: string[] = [];\n        for (const addr of failedUsers) {\n            if (states[addr] === \"error\") {\n                const reason = inviter.getErrorText(addr);\n                errorList.push(addr + \": \" + reason);\n            }\n        }\n\n        const cli = room.client;\n        if (errorList.length > 0) {\n            // React 16 doesn't let us use `errorList.join(<br />)` anymore, so this is our solution\n            const description = (\n                <div className=\"mx_InviteDialog_multiInviterError\">\n                    <h4>\n                        {_t(\n                            \"invite|room_failed_partial\",\n                            {},\n                            {\n                                RoomName: () => <strong>{room.name}</strong>,\n                            },\n                        )}\n                    </h4>\n                    <div>\n                        {failedUsers.map((addr) => {\n                            const user = userMap?.get(addr) || cli.getUser(addr);\n                            const name = (user as Member).name || (user as User).rawDisplayName;\n                            const avatarUrl = (user as Member).getMxcAvatarUrl?.() || (user as User).avatarUrl;\n                            return (\n                                <div key={addr} className=\"mx_InviteDialog_tile mx_InviteDialog_tile--inviterError\">\n                                    <div className=\"mx_InviteDialog_tile_avatarStack\">\n                                        <BaseAvatar\n                                            url={\n                                                (avatarUrl && mediaFromMxc(avatarUrl).getSquareThumbnailHttp(24)) ??\n                                                undefined\n                                            }\n                                            name={name!}\n                                            idName={user?.userId}\n                                            size=\"36px\"\n                                        />\n                                    </div>\n                                    <div className=\"mx_InviteDialog_tile_nameStack\">\n                                        <span className=\"mx_InviteDialog_tile_nameStack_name\">{name}</span>\n                                        <span className=\"mx_InviteDialog_tile_nameStack_userId\">{user?.userId}</span>\n                                    </div>\n                                    <div className=\"mx_InviteDialog_tile--inviterError_errorText\">\n                                        {inviter.getErrorText(addr)}\n                                    </div>\n                                </div>\n                            );\n                        })}\n                    </div>\n                </div>\n            );\n\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"invite|room_failed_partial_title\"),\n                description,\n            });\n            return false;\n        }\n    }\n\n    return true;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2016-2019 , 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { PushProcessor } from \"matrix-js-sdk/src/pushprocessor\";\nimport {\n    NotificationCountType,\n    ConditionKind,\n    PushRuleActionName,\n    PushRuleKind,\n    TweakName,\n    EventStatus,\n} from \"matrix-js-sdk/src/matrix\";\n\nimport type { IPushRule, Room, MatrixClient, MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { NotificationLevel } from \"./stores/notifications/NotificationLevel\";\nimport { doesRoomHaveUnreadMessages, doesRoomOrThreadHaveUnreadMessages } from \"./Unread\";\nimport { EffectiveMembership, getEffectiveMembership, isKnockDenied } from \"./utils/membership\";\nimport SettingsStore from \"./settings/SettingsStore\";\nimport { getMarkedUnreadState } from \"./utils/notifications\";\n\n/**\n * Gets all pending events in a room that have a status of `EventStatus.NOT_SENT`\n * and belong to the current thread, if specified.\n * @param room The room to check.\n * @param threadId The thread to check. If not specified, no thread filtering is performed.\n * @returns An array of unsent matrix events.\n */\nexport function getUnsentMessages(room: Room, threadId?: string): MatrixEvent[] {\n    if (!room) {\n        return [];\n    }\n    return room.getPendingEvents().filter(function (ev) {\n        if (ev.status !== EventStatus.NOT_SENT) {\n            return false;\n        }\n        if (threadId && threadId !== ev.threadRootId) {\n            return false;\n        }\n        return true;\n    });\n}\n\nexport enum RoomNotifState {\n    AllMessagesLoud = \"all_messages_loud\",\n    AllMessages = \"all_messages\",\n    MentionsOnly = \"mentions_only\",\n    Mute = \"mute\",\n}\n\nexport function getRoomNotifsState(client: MatrixClient, roomId: string): RoomNotifState | null {\n    if (client.isGuest()) return RoomNotifState.AllMessages;\n\n    // look through the override rules for a rule affecting this room:\n    // if one exists, it will take precedence.\n    const muteRule = findOverrideMuteRule(client, roomId);\n    if (muteRule) {\n        return RoomNotifState.Mute;\n    }\n\n    // for everything else, look at the room rule.\n    let roomRule: IPushRule | undefined;\n    try {\n        roomRule = client.getRoomPushRule(\"global\", roomId);\n    } catch {\n        // Possible that the client doesn't have pushRules yet. If so, it\n        // hasn't started either, so indicate that this room is not notifying.\n        return null;\n    }\n\n    // XXX: We have to assume the default is to notify for all messages\n    // (in particular this will be 'wrong' for one to one rooms because\n    // they will notify loudly for all messages)\n    if (!roomRule?.enabled) return RoomNotifState.AllMessages;\n\n    // a mute at the room level will still allow mentions\n    // to notify\n    if (isMuteRule(roomRule)) return RoomNotifState.MentionsOnly;\n\n    const actionsObject = PushProcessor.actionListToActionsObject(roomRule.actions);\n    if (actionsObject.tweaks.sound) return RoomNotifState.AllMessagesLoud;\n\n    return null;\n}\n\nexport function setRoomNotifsState(client: MatrixClient, roomId: string, newState: RoomNotifState): Promise<void> {\n    if (newState === RoomNotifState.Mute) {\n        return setRoomNotifsStateMuted(client, roomId);\n    } else {\n        return setRoomNotifsStateUnmuted(client, roomId, newState);\n    }\n}\n\nexport function getUnreadNotificationCount(\n    room: Room,\n    type: NotificationCountType,\n    includeThreads: boolean,\n    threadId?: string,\n): number {\n    const getCountShownForRoom = (r: Room, type: NotificationCountType): number => {\n        return includeThreads ? r.getUnreadNotificationCount(type) : r.getRoomUnreadNotificationCount(type);\n    };\n\n    let notificationCount = !!threadId\n        ? room.getThreadUnreadNotificationCount(threadId, type)\n        : getCountShownForRoom(room, type);\n\n    // Check notification counts in the old room just in case there's some lost\n    // there. We only go one level down to avoid performance issues, and theory\n    // is that 1st generation rooms will have already been read by the 3rd generation.\n    const msc3946ProcessDynamicPredecessor = SettingsStore.getValue(\"feature_dynamic_room_predecessors\");\n    const predecessor = room.findPredecessor(msc3946ProcessDynamicPredecessor);\n    // Exclude threadId, as the same thread can't continue over a room upgrade\n    if (!threadId && predecessor?.roomId) {\n        const oldRoomId = predecessor.roomId;\n        const oldRoom = room.client.getRoom(oldRoomId);\n        if (oldRoom) {\n            // We only ever care if there's highlights in the old room. No point in\n            // notifying the user for unread messages because they would have extreme\n            // difficulty changing their notification preferences away from \"All Messages\"\n            // and \"Noisy\".\n            notificationCount += getCountShownForRoom(oldRoom, NotificationCountType.Highlight);\n        }\n    }\n\n    return notificationCount;\n}\n\nfunction setRoomNotifsStateMuted(cli: MatrixClient, roomId: string): Promise<any> {\n    const promises: Promise<unknown>[] = [];\n\n    // delete the room rule\n    const roomRule = cli.getRoomPushRule(\"global\", roomId);\n    if (roomRule) {\n        promises.push(cli.deletePushRule(\"global\", PushRuleKind.RoomSpecific, roomRule.rule_id));\n    }\n\n    // add/replace an override rule to squelch everything in this room\n    // NB. We use the room ID as the name of this rule too, although this\n    // is an override rule, not a room rule: it still pertains to this room\n    // though, so using the room ID as the rule ID is logical and prevents\n    // duplicate copies of the rule.\n    promises.push(\n        cli.addPushRule(\"global\", PushRuleKind.Override, roomId, {\n            conditions: [\n                {\n                    kind: ConditionKind.EventMatch,\n                    key: \"room_id\",\n                    pattern: roomId,\n                },\n            ],\n            actions: [PushRuleActionName.DontNotify],\n        }),\n    );\n\n    return Promise.all(promises);\n}\n\nfunction setRoomNotifsStateUnmuted(cli: MatrixClient, roomId: string, newState: RoomNotifState): Promise<any> {\n    const promises: Promise<unknown>[] = [];\n\n    const overrideMuteRule = findOverrideMuteRule(cli, roomId);\n    if (overrideMuteRule) {\n        promises.push(cli.deletePushRule(\"global\", PushRuleKind.Override, overrideMuteRule.rule_id));\n    }\n\n    if (newState === RoomNotifState.AllMessages) {\n        const roomRule = cli.getRoomPushRule(\"global\", roomId);\n        if (roomRule) {\n            promises.push(cli.deletePushRule(\"global\", PushRuleKind.RoomSpecific, roomRule.rule_id));\n        }\n    } else if (newState === RoomNotifState.MentionsOnly) {\n        promises.push(\n            cli.addPushRule(\"global\", PushRuleKind.RoomSpecific, roomId, {\n                actions: [PushRuleActionName.DontNotify],\n            }),\n        );\n    } else if (newState === RoomNotifState.AllMessagesLoud) {\n        promises.push(\n            cli.addPushRule(\"global\", PushRuleKind.RoomSpecific, roomId, {\n                actions: [\n                    PushRuleActionName.Notify,\n                    {\n                        set_tweak: TweakName.Sound,\n                        value: \"default\",\n                    },\n                ],\n            }),\n        );\n    }\n\n    return Promise.all(promises);\n}\n\nfunction findOverrideMuteRule(cli: MatrixClient | undefined, roomId: string): IPushRule | null {\n    if (!cli?.pushRules?.global?.override) {\n        return null;\n    }\n    for (const rule of cli.pushRules.global.override) {\n        if (rule.enabled && isRuleRoomMuteRuleForRoomId(roomId, rule)) {\n            return rule;\n        }\n    }\n    return null;\n}\n\n/**\n * Checks if a given rule is a room mute rule as implemented by EW\n * - matches every event in one room (one condition that is an event match on roomId)\n * - silences notifications (one action that is `DontNotify`)\n * @param rule - push rule\n * @returns {boolean} - true when rule mutes a room\n */\nexport function isRuleMaybeRoomMuteRule(rule: IPushRule): boolean {\n    return (\n        // matches every event in one room\n        rule.conditions?.length === 1 &&\n        rule.conditions[0].kind === ConditionKind.EventMatch &&\n        rule.conditions[0].key === \"room_id\" &&\n        // silences notifications\n        isMuteRule(rule)\n    );\n}\n\n/**\n * Checks if a given rule is a room mute rule as implemented by EW\n * @param roomId - id of room to match\n * @param rule - push rule\n * @returns {boolean} true when rule mutes the given room\n */\nfunction isRuleRoomMuteRuleForRoomId(roomId: string, rule: IPushRule): boolean {\n    if (!isRuleMaybeRoomMuteRule(rule)) {\n        return false;\n    }\n    // isRuleMaybeRoomMuteRule checks this condition exists\n    const cond = rule.conditions![0]!;\n    return cond.pattern === roomId;\n}\n\nfunction isMuteRule(rule: IPushRule): boolean {\n    // DontNotify is equivalent to the empty actions array\n    return (\n        rule.actions.length === 0 || (rule.actions.length === 1 && rule.actions[0] === PushRuleActionName.DontNotify)\n    );\n}\n\n/**\n * Returns an object giving information about the unread state of a room or thread\n * @param room The room to query, or the room the thread is in\n * @param threadId The thread to check the unread state of, or undefined to query the main thread\n * @param includeThreads If threadId is undefined, true to include threads other than the main thread, or\n *   false to exclude them. Ignored if threadId is specified.\n * @returns\n */\nexport function determineUnreadState(\n    room?: Room,\n    threadId?: string,\n    includeThreads?: boolean,\n): { level: NotificationLevel; symbol: string | null; count: number; invited: boolean } {\n    if (!room) {\n        return { symbol: null, count: 0, level: NotificationLevel.None, invited: false };\n    }\n\n    if (getUnsentMessages(room, threadId).length > 0) {\n        return { symbol: \"!\", count: 1, level: NotificationLevel.Unsent, invited: false };\n    }\n\n    if (getEffectiveMembership(room.getMyMembership()) === EffectiveMembership.Invite) {\n        return { symbol: \"!\", count: 1, level: NotificationLevel.Highlight, invited: true };\n    }\n\n    if (SettingsStore.getValue(\"feature_ask_to_join\") && isKnockDenied(room)) {\n        return { symbol: \"!\", count: 1, level: NotificationLevel.Highlight, invited: false };\n    }\n\n    if (getRoomNotifsState(room.client, room.roomId) === RoomNotifState.Mute) {\n        return { symbol: null, count: 0, level: NotificationLevel.None, invited: false };\n    }\n\n    const redNotifs = getUnreadNotificationCount(\n        room,\n        NotificationCountType.Highlight,\n        includeThreads ?? false,\n        threadId,\n    );\n    const greyNotifs = getUnreadNotificationCount(room, NotificationCountType.Total, includeThreads ?? false, threadId);\n\n    const trueCount = greyNotifs || redNotifs;\n    if (redNotifs > 0) {\n        return { symbol: null, count: trueCount, level: NotificationLevel.Highlight, invited: false };\n    }\n\n    const markedUnreadState = getMarkedUnreadState(room);\n    if (greyNotifs > 0 || markedUnreadState) {\n        return { symbol: null, count: trueCount, level: NotificationLevel.Notification, invited: false };\n    }\n\n    // We don't have any notified messages, but we might have unread messages. Let's find out.\n    let hasUnread = false;\n    if (threadId) {\n        const thread = room.getThread(threadId);\n        if (thread) {\n            hasUnread = doesRoomOrThreadHaveUnreadMessages(thread);\n        }\n        // If the thread does not exist, assume it contains no unreads\n    } else {\n        hasUnread = doesRoomHaveUnreadMessages(room, includeThreads ?? false);\n    }\n\n    return {\n        symbol: null,\n        count: trueCount,\n        level: hasUnread ? NotificationLevel.Activity : NotificationLevel.None,\n        invited: false,\n    };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room, EventType, type RoomMember, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport AliasCustomisations from \"./customisations/Alias\";\nimport { filterValidMDirect } from \"./utils/dm/filterValidMDirect.ts\";\n\n/**\n * Given a room object, return the alias we should use for it,\n * if any. This could be the canonical alias if one exists, otherwise\n * an alias selected arbitrarily but deterministically from the list\n * of aliases. Otherwise return null;\n *\n * @param {Object} room The room object\n * @returns {string} A display alias for the given room\n */\nexport function getDisplayAliasForRoom(room: Room): string | null {\n    return getDisplayAliasForAliasSet(room.getCanonicalAlias(), room.getAltAliases());\n}\n\n// The various display alias getters should all feed through this one path so\n// there's a single place to change the logic.\nexport function getDisplayAliasForAliasSet(canonicalAlias: string | null, altAliases: string[]): string | null {\n    if (AliasCustomisations.getDisplayAliasForAliasSet) {\n        return AliasCustomisations.getDisplayAliasForAliasSet(canonicalAlias, altAliases);\n    }\n    return (canonicalAlias || altAliases?.[0]) ?? \"\";\n}\n\nexport function guessAndSetDMRoom(room: Room, isDirect: boolean): Promise<void> {\n    let newTarget;\n    if (isDirect) {\n        const guessedUserId = guessDMRoomTargetId(room, room.client.getSafeUserId());\n        newTarget = guessedUserId;\n    } else {\n        newTarget = null;\n    }\n\n    return setDMRoom(room.client, room.roomId, newTarget);\n}\n\n/**\n * Marks or unmarks the given room as being as a DM room.\n * @param client the Matrix Client instance of the logged-in user\n * @param {string} roomId The ID of the room to modify\n * @param {string | null} userId The user ID of the desired DM room target user or\n *                        null to un-mark this room as a DM room\n * @returns {object} A promise\n */\nexport async function setDMRoom(client: MatrixClient, roomId: string, userId: string | null): Promise<void> {\n    if (client.isGuest()) return;\n\n    const mDirectEvent = client.getAccountData(EventType.Direct);\n    const { filteredContent } = filterValidMDirect(mDirectEvent?.getContent() ?? {});\n\n    // remove it from the lists of all users (it can only be a DM room for one person)\n    for (const thisUserId in filteredContent) {\n        if (!filteredContent[thisUserId]) continue;\n        filteredContent[thisUserId] = filteredContent[thisUserId].filter((room) => room !== roomId);\n    }\n\n    // now add it if the caller asked for it to be a DM room\n    if (userId) {\n        if (!filteredContent[userId]) {\n            filteredContent[userId] = [];\n        }\n        filteredContent[userId].push(roomId);\n    }\n\n    await client.setAccountData(EventType.Direct, filteredContent);\n}\n\n/**\n * Given a room, estimate which of its members is likely to\n * be the target if the room were a DM room and return that user.\n *\n * @param {Object} room Target room\n * @param {string} myUserId User ID of the current user\n * @returns {string} User ID of the user that the room is probably a DM with\n */\nfunction guessDMRoomTargetId(room: Room, myUserId: string): string {\n    let oldestTs: number | undefined;\n    let oldestUser: RoomMember | undefined;\n\n    // Pick the joined user who's been here longest (and isn't us),\n    for (const user of room.getJoinedMembers()) {\n        if (user.userId == myUserId) continue;\n\n        if (oldestTs === undefined || (user.events.member && user.events.member.getTs() < oldestTs)) {\n            oldestUser = user;\n            oldestTs = user.events.member?.getTs();\n        }\n    }\n    if (oldestUser) return oldestUser.userId;\n\n    // if there are no joined members other than us, use the oldest member\n    for (const user of room.currentState.getMembers()) {\n        if (user.userId == myUserId) continue;\n\n        if (oldestTs === undefined || (user.events.member && user.events.member.getTs() < oldestTs)) {\n            oldestUser = user;\n            oldestTs = user.events.member?.getTs();\n        }\n    }\n\n    if (oldestUser === undefined) return myUserId;\n    return oldestUser.userId;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2022 The Matrix.org Foundation C.I.C.\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { mergeWith } from \"lodash\";\n\nimport { SnakedObject } from \"./utils/SnakedObject\";\nimport { type IConfigOptions, type ISsoRedirectOptions } from \"./IConfigOptions\";\nimport { isObject, objectClone } from \"./utils/objects\";\nimport { type DeepReadonly, type Defaultize } from \"./@types/common\";\n\n// see element-web config.md for docs, or the IConfigOptions interface for dev docs\nexport const DEFAULTS: DeepReadonly<IConfigOptions> = {\n    brand: \"Element\",\n    help_url: \"https://element.io/help\",\n    help_encryption_url: \"https://element.io/help#encryption\",\n    help_key_storage_url: \"https://element.io/help#encryption5\",\n    integrations_ui_url: \"https://scalar.vector.im/\",\n    integrations_rest_url: \"https://scalar.vector.im/api\",\n    uisi_autorageshake_app: \"element-auto-uisi\",\n    show_labs_settings: false,\n    force_verification: false,\n\n    jitsi: {\n        preferred_domain: \"meet.element.io\",\n    },\n    element_call: {\n        use_exclusively: false,\n        brand: \"Element Call\",\n    },\n\n    // @ts-ignore - we deliberately use the camelCase version here so we trigger\n    // the fallback behaviour. If we used the snake_case version then we'd break\n    // everyone's config which has the camelCase property because our default would\n    // be preferred over their config.\n    desktopBuilds: {\n        available: true,\n        // eslint-disable-next-line @typescript-eslint/no-require-imports\n        logo: require(\"../res/img/element-desktop-logo.svg\").default,\n        url: \"https://element.io/get-started\",\n    },\n\n    feedback: {\n        existing_issues_url:\n            \"https://github.com/vector-im/element-web/issues?q=is%3Aopen+is%3Aissue+sort%3Areactions-%2B1-desc\",\n        new_issue_url: \"https://github.com/vector-im/element-web/issues/new/choose\",\n    },\n\n    desktop_builds: {\n        available: true,\n        logo: \"vector-icons/1024.png\",\n        url: \"https://element.io/download\",\n        url_macos: \"https://packages.element.io/desktop/install/macos/Element.dmg\",\n        url_win64: \"https://packages.element.io/desktop/install/win32/x64/Element%20Setup.exe\",\n        url_win64arm: \"https://packages.element.io/desktop/install/win32/arm64/Element%20Setup.exe\",\n        url_linux: \"https://element.io/download#linux\",\n    },\n    mobile_builds: {\n        ios: \"https://apps.apple.com/app/vector/id1083446067\",\n        android: \"https://play.google.com/store/apps/details?id=im.vector.app\",\n        fdroid: \"https://f-droid.org/repository/browse/?fdid=im.vector.app\",\n    },\n};\n\nexport type ConfigOptions = Defaultize<IConfigOptions, typeof DEFAULTS>;\n\nfunction mergeConfig(\n    config: DeepReadonly<IConfigOptions>,\n    changes: DeepReadonly<Partial<IConfigOptions>>,\n): DeepReadonly<IConfigOptions> {\n    // return { ...config, ...changes };\n    return mergeWith(objectClone(config), changes, (objValue, srcValue) => {\n        // Don't merge arrays, prefer values from newer object\n        if (Array.isArray(objValue)) {\n            return srcValue;\n        }\n\n        // Don't allow objects to get nulled out, this will break our types\n        if (isObject(objValue) && !isObject(srcValue)) {\n            return objValue;\n        }\n    });\n}\n\ntype ObjectType<K extends keyof IConfigOptions> = IConfigOptions[K] extends object\n    ? SnakedObject<NonNullable<IConfigOptions[K]>>\n    : SnakedObject<NonNullable<IConfigOptions[K]>> | null | undefined;\n\nexport default class SdkConfig {\n    private static instance: DeepReadonly<IConfigOptions>;\n    private static fallback: SnakedObject<DeepReadonly<IConfigOptions>>;\n\n    private static setInstance(i: DeepReadonly<IConfigOptions>): void {\n        SdkConfig.instance = i;\n        SdkConfig.fallback = new SnakedObject(i);\n\n        // For debugging purposes\n        window.mxReactSdkConfig = i;\n    }\n\n    public static get(): IConfigOptions;\n    public static get<K extends keyof IConfigOptions>(key: K, altCaseName?: string): IConfigOptions[K];\n    public static get<K extends keyof IConfigOptions = never>(\n        key?: K,\n        altCaseName?: string,\n    ): DeepReadonly<IConfigOptions> | DeepReadonly<IConfigOptions>[K] {\n        if (key === undefined) {\n            // safe to cast as a fallback - we want to break the runtime contract in this case\n            return SdkConfig.instance || <IConfigOptions>{};\n        }\n        return SdkConfig.fallback.get(key, altCaseName);\n    }\n\n    public static getObject<K extends keyof IConfigOptions>(key: K, altCaseName?: string): ObjectType<K> {\n        const val = SdkConfig.get(key, altCaseName);\n        if (isObject(val)) {\n            return new SnakedObject(val);\n        }\n\n        // return the same type for sensitive callers (some want `undefined` specifically)\n        return (val === undefined ? undefined : null) as ObjectType<K>;\n    }\n\n    public static put(cfg: DeepReadonly<ConfigOptions>): void {\n        SdkConfig.setInstance(mergeConfig(DEFAULTS, cfg));\n    }\n\n    /**\n     * Resets the config.\n     */\n    public static reset(): void {\n        SdkConfig.setInstance(mergeConfig(DEFAULTS, {})); // safe to cast - defaults will be applied\n    }\n\n    public static add(cfg: Partial<ConfigOptions>): void {\n        SdkConfig.put(mergeConfig(SdkConfig.get(), cfg));\n    }\n}\n\nexport function parseSsoRedirectOptions(config: IConfigOptions): ISsoRedirectOptions {\n    // Ignore deprecated options if the config is using new ones\n    if (config.sso_redirect_options) return config.sso_redirect_options;\n\n    // We can cheat here because the default is false anyways\n    if (config.sso_immediate_redirect) return { immediate: true };\n\n    // Default: do nothing\n    return {};\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { Button, PasswordInput } from \"@vector-im/compound-web\";\nimport LockSolidIcon from \"@vector-im/compound-design-tokens/assets/web/icons/lock-solid\";\nimport { debounce } from \"lodash\";\nimport classNames from \"classnames\";\nimport React, { type ChangeEvent, type FormEvent, type ReactNode } from \"react\";\nimport { type SecretStorage } from \"matrix-js-sdk/src/matrix\";\nimport { Flex } from \"@element-hq/web-shared-components\";\nimport { ErrorSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport { EncryptionCard } from \"../../settings/encryption/EncryptionCard\";\nimport { EncryptionCardButtons } from \"../../settings/encryption/EncryptionCardButtons\";\nimport BaseDialog from \"../BaseDialog\";\n\n// Don't shout at the user that their key is invalid every time they type a key: wait a short time\nconst VALIDATION_THROTTLE_MS = 200;\n\nexport type KeyParams = { passphrase?: string; recoveryKey?: string };\n\ninterface IProps {\n    /**\n     * Information about the Secret Storage key that we want to get.\n     */\n    keyInfo: SecretStorage.SecretStorageKeyDescription;\n    /**\n     * Callback to check whether the given key is correct.\n     */\n    checkPrivateKey: (k: KeyParams) => Promise<boolean>;\n    /**\n     * Callback for when the user is done with this dialog.  `result` will\n     * contain information about the key that was entered, or will be `false` if\n     * the user cancelled.\n     */\n    onFinished(result?: false | KeyParams): void;\n}\n\ninterface IState {\n    //! The recovery key/phrase that the user entered\n    recoveryKey: string;\n    //! Is the recovery key/phrase correct?  `null` means no key/phrase has been entered\n    recoveryKeyCorrect: boolean | null;\n}\n\n/*\n * Access Secure Secret Storage by requesting the user's passphrase.\n */\nexport default class AccessSecretStorageDialog extends React.PureComponent<IProps, IState> {\n    private inputRef = React.createRef<HTMLInputElement>();\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            recoveryKey: \"\",\n            recoveryKeyCorrect: null,\n        };\n    }\n\n    private onCancel = (): void => {\n        this.props.onFinished(false);\n    };\n\n    private validateRecoveryKeyOnChange = debounce(async (): Promise<void> => {\n        await this.validateRecoveryKey(this.state.recoveryKey);\n    }, VALIDATION_THROTTLE_MS);\n\n    /**\n     * Checks whether the security key/phrase is correct.\n     *\n     * Sets `state.recoveryKeyCorrect` accordingly, and if the key/phrase is\n     * correct, returns a `KeyParams` structure.\n     */\n    private async validateRecoveryKey(recoveryKey: string): Promise<KeyParams | undefined> {\n        recoveryKey = recoveryKey.trim();\n\n        if (recoveryKey === \"\") {\n            this.setState({\n                recoveryKeyCorrect: null,\n            });\n            return;\n        }\n\n        const hasPassphrase = this.props.keyInfo?.passphrase?.salt && this.props.keyInfo?.passphrase?.iterations;\n\n        // If the user has a passphrase, we want to try validating it both as a\n        // key and as a passphrase.  We first try to validate it as a key, since\n        // that check is faster.\n\n        try {\n            const input = { recoveryKey };\n            const recoveryKeyCorrect = await this.props.checkPrivateKey(input);\n            if (recoveryKeyCorrect) {\n                this.setState({ recoveryKeyCorrect });\n                return input;\n            }\n        } catch {}\n\n        if (hasPassphrase) {\n            try {\n                const input = { passphrase: recoveryKey };\n                const recoveryKeyCorrect = await this.props.checkPrivateKey(input);\n                if (recoveryKeyCorrect) {\n                    this.setState({ recoveryKeyCorrect });\n                    return input;\n                }\n            } catch {}\n        }\n\n        this.setState({\n            recoveryKeyCorrect: false,\n        });\n    }\n\n    private onRecoveryKeyChange = (ev: ChangeEvent<HTMLInputElement>): void => {\n        this.setState({\n            recoveryKey: ev.target.value,\n        });\n\n        // We don't use Field's validation here because we want it in a separate place rather\n        // than in a tooltip. Ideally we would refactor Field's validation logic so we could\n        // re-use some of it.\n        this.validateRecoveryKeyOnChange();\n    };\n\n    private onRecoveryKeyNext = async (ev: FormEvent<HTMLFormElement> | React.MouseEvent): Promise<void> => {\n        ev.preventDefault();\n\n        const keyParams = await this.validateRecoveryKey(this.state.recoveryKey);\n\n        if (keyParams !== undefined) {\n            this.props.onFinished(keyParams);\n        } else {\n            this.inputRef.current?.focus();\n        }\n    };\n\n    private getRecoveryKeyFeedback(): React.ReactNode | null {\n        let content: ReactNode;\n        let classes: string | undefined;\n\n        if (this.state.recoveryKeyCorrect) {\n            // The recovery key is good. Empty feedback.\n            content = \"\\xA0\"; // &nbsp;\n        } else if (this.state.recoveryKeyCorrect === null) {\n            // The input element is empty. Tell the user they can also use a passphrase.\n            content = _t(\"encryption|access_secret_storage_dialog|alternatives\");\n        } else {\n            // The entered key is not (yet) correct. Tell them so.\n            content = (\n                <>\n                    <ErrorSolidIcon />\n                    {_t(\"encryption|access_secret_storage_dialog|key_validation_text|wrong_security_key\")}\n                </>\n            );\n            classes = \"mx_AccessSecretStorageDialog_recoveryKeyFeedback--invalid\";\n        }\n\n        return (\n            <Flex align=\"center\" className={classNames(\"mx_AccessSecretStorageDialog_recoveryKeyFeedback\", classes)}>\n                {content}\n            </Flex>\n        );\n    }\n\n    public render(): React.ReactNode {\n        const title = _t(\"encryption|access_secret_storage_dialog|security_key_title\");\n\n        const recoveryKeyFeedback = this.getRecoveryKeyFeedback();\n        const content = (\n            <div>\n                <form\n                    className=\"mx_AccessSecretStorageDialog_primaryContainer\"\n                    onSubmit={this.onRecoveryKeyNext}\n                    spellCheck={false}\n                    autoComplete=\"off\"\n                >\n                    <div className=\"mx_AccessSecretStorageDialog_recoveryKeyEntry\">\n                        <PasswordInput\n                            ref={this.inputRef}\n                            id=\"mx_securityKey\"\n                            title={_t(\"encryption|access_secret_storage_dialog|security_key_label\")}\n                            placeholder={_t(\"encryption|access_secret_storage_dialog|security_key_label\")}\n                            value={this.state.recoveryKey}\n                            onChange={this.onRecoveryKeyChange}\n                            autoFocus={true}\n                            autoComplete=\"off\"\n                        />\n                    </div>\n                    {recoveryKeyFeedback}\n                    <EncryptionCardButtons>\n                        <Button disabled={!this.state.recoveryKeyCorrect} onClick={this.onRecoveryKeyNext}>\n                            {_t(\"action|continue\")}\n                        </Button>\n                        <Button kind=\"tertiary\" onClick={this.onCancel}>\n                            {_t(\"action|cancel\")}\n                        </Button>\n                    </EncryptionCardButtons>\n                </form>\n            </div>\n        );\n\n        // We wrap the content in `BaseDialog` mostly so that we get a `FocusLock` container; otherwise, if the\n        // SettingsDialog is open, then the `FocusLock` in *that* stops us getting the focus.\n        return (\n            <BaseDialog fixedWidth={false} hasCancel={false}>\n                <EncryptionCard\n                    Icon={LockSolidIcon}\n                    className=\"mx_AccessSecretStorageDialog\"\n                    title={title}\n                    description={_t(\"encryption|access_secret_storage_dialog|privacy_warning\")}\n                >\n                    {content}\n                </EncryptionCard>\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { lazy } from \"react\";\nimport { type SecretStorage } from \"matrix-js-sdk/src/matrix\";\nimport { deriveRecoveryKeyFromPassphrase, decodeRecoveryKey, type CryptoCallbacks } from \"matrix-js-sdk/src/crypto-api\";\nimport { logger as rootLogger } from \"matrix-js-sdk/src/logger\";\n\nimport Modal from \"./Modal\";\nimport { MatrixClientPeg } from \"./MatrixClientPeg\";\nimport { _t } from \"./languageHandler\";\nimport AccessSecretStorageDialog, {\n    type KeyParams,\n} from \"./components/views/dialogs/security/AccessSecretStorageDialog\";\nimport { ModuleRunner } from \"./modules/ModuleRunner\";\nimport InteractiveAuthDialog from \"./components/views/dialogs/InteractiveAuthDialog\";\n\n// This stores the secret storage private keys in memory for the JS SDK. This is\n// only meant to act as a cache to avoid prompting the user multiple times\n// during the same single operation. Use `accessSecretStorage` below to scope a\n// single secret storage operation, as it will clear the cached keys once the\n// operation ends.\nlet secretStorageKeys: Record<string, Uint8Array<ArrayBuffer>> = {};\nlet secretStorageKeyInfo: Record<string, SecretStorage.SecretStorageKeyDescription> = {};\nlet secretStorageBeingAccessed = false;\n\nconst logger = rootLogger.getChild(\"SecurityManager:\");\n\n/**\n * This can be used by other components to check if secret storage access is in\n * progress, so that we can e.g. avoid intermittently showing toasts during\n * secret storage setup.\n *\n * @returns {bool}\n */\nexport function isSecretStorageBeingAccessed(): boolean {\n    return secretStorageBeingAccessed;\n}\n\nexport class AccessCancelledError extends Error {\n    public constructor() {\n        super(\"Secret storage access canceled\");\n    }\n}\n\nfunction makeInputToKey(\n    keyInfo: SecretStorage.SecretStorageKeyDescription,\n): (keyParams: KeyParams) => Promise<Uint8Array<ArrayBuffer>> {\n    return async ({ passphrase, recoveryKey }): Promise<Uint8Array<ArrayBuffer>> => {\n        if (passphrase) {\n            return deriveRecoveryKeyFromPassphrase(passphrase, keyInfo.passphrase.salt, keyInfo.passphrase.iterations);\n        } else if (recoveryKey) {\n            return decodeRecoveryKey(recoveryKey);\n        }\n        throw new Error(\"Invalid input, passphrase or recoveryKey need to be provided\");\n    };\n}\n\nasync function getSecretStorageKey(\n    {\n        keys: keyInfos,\n    }: {\n        keys: Record<string, SecretStorage.SecretStorageKeyDescription>;\n    },\n    secretName: string,\n): Promise<[string, Uint8Array<ArrayBuffer>]> {\n    const cli = MatrixClientPeg.safeGet();\n    const defaultKeyId = await cli.secretStorage.getDefaultKeyId();\n\n    let keyId: string;\n    // If the defaultKey is useful, use that\n    if (defaultKeyId && keyInfos[defaultKeyId]) {\n        keyId = defaultKeyId;\n    } else {\n        // Fall back to a heuristic of using the\n        // only available key, if only one key is set\n        const usefulKeys = Object.keys(keyInfos);\n        if (usefulKeys.length > 1) {\n            throw new Error(\"Multiple storage key requests not implemented\");\n        }\n        keyId = usefulKeys[0];\n    }\n    const keyInfo = keyInfos[keyId];\n    logger.debug(\n        `getSecretStorageKey: request for 4S keys [${Object.keys(keyInfos)}] for secret \\`${secretName}\\`: looking for key ${keyId}`,\n    );\n\n    // Check the in-memory cache\n    if (secretStorageBeingAccessed && secretStorageKeys[keyId]) {\n        logger.debug(`getSecretStorageKey: returning key ${keyId} from cache`);\n        return [keyId, secretStorageKeys[keyId]];\n    }\n\n    const keyFromCustomisations = ModuleRunner.instance.extensions.cryptoSetup.getSecretStorageKey();\n    if (keyFromCustomisations) {\n        logger.debug(\"getSecretStorageKey: Using secret storage key from CryptoSetupExtension\");\n        cacheSecretStorageKey(keyId, keyInfo, keyFromCustomisations);\n        return [keyId, keyFromCustomisations];\n    }\n\n    // We only prompt the user for the default key\n    if (keyId !== defaultKeyId) {\n        logger.debug(`getSecretStorageKey: request for non-default key ${keyId}: not prompting user`);\n        throw new Error(\"Request for non-default 4S key\");\n    }\n\n    logger.debug(`getSecretStorageKey: prompting user for key ${keyId}`);\n    const inputToKey = makeInputToKey(keyInfo);\n    const { finished } = Modal.createDialog(\n        AccessSecretStorageDialog,\n        /* props= */\n        {\n            keyInfo,\n            checkPrivateKey: async (input: KeyParams): Promise<boolean> => {\n                const key = await inputToKey(input);\n                return MatrixClientPeg.safeGet().secretStorage.checkKey(key, keyInfo);\n            },\n        },\n    );\n    const [keyParams] = await finished;\n    if (!keyParams) {\n        throw new AccessCancelledError();\n    }\n    logger.debug(`getSecretStorageKey: got key ${keyId} from user`);\n    const key = await inputToKey(keyParams);\n\n    // Save to cache to avoid future prompts in the current session\n    cacheSecretStorageKey(keyId, keyInfo, key);\n\n    return [keyId, key];\n}\n\nfunction cacheSecretStorageKey(\n    keyId: string,\n    keyInfo: SecretStorage.SecretStorageKeyDescription,\n    key: Uint8Array<ArrayBuffer>,\n): void {\n    if (secretStorageBeingAccessed) {\n        logger.debug(`Caching 4S key ${keyId}`);\n        secretStorageKeys[keyId] = key;\n        secretStorageKeyInfo[keyId] = keyInfo;\n    }\n}\n\nexport const crossSigningCallbacks: CryptoCallbacks = {\n    getSecretStorageKey,\n    cacheSecretStorageKey,\n};\n\n/**\n * Carry out an operation that may require multiple accesses to secret storage, caching the key.\n *\n * Use this helper to wrap an operation that may require multiple accesses to secret storage; the user will be prompted\n * to enter the 4S key or passphrase on the first access, and the key will be cached for the rest of the operation.\n *\n * @param func - The operation to be wrapped.\n */\nexport async function withSecretStorageKeyCache<T>(func: () => Promise<T>): Promise<T> {\n    logger.debug(\"enabling 4S key cache\");\n    secretStorageBeingAccessed = true;\n    try {\n        return await func();\n    } finally {\n        // Clear secret storage key cache now that work is complete\n        logger.debug(\"disabling 4S key cache\");\n        secretStorageBeingAccessed = false;\n        secretStorageKeys = {};\n        secretStorageKeyInfo = {};\n    }\n}\n\nexport interface AccessSecretStorageOpts {\n    /**\n     * Reset secret storage even if it's already set up.\n     * @deprecated send the user to the Encryption settings tab to reset secret storage\n     */\n    forceReset?: boolean;\n}\n\n/**\n * This helper should be used whenever you need to access secret storage. It\n * ensures that secret storage (and also cross-signing since they each depend on\n * each other in a cycle of sorts) have been bootstrapped before running the\n * provided function.\n *\n * Bootstrapping secret storage may take one of these paths:\n * 1. (Only if `opts.forceReset` is set) create secret storage from a passphrase\n *    and store cross-signing keys in secret storage.\n * 2. Access existing secret storage by requesting passphrase and accessing\n *    cross-signing keys as needed.\n * 3. All keys are loaded and there's nothing to do.\n *\n * Additionally, the secret storage keys are cached during the scope of this function\n * to ensure the user is prompted only once for their secret storage\n * passphrase. The cache is then cleared once the provided function completes.\n *\n * Throws an error if secret storage is not set up (and `opts.forceReset` is not set)\n *\n * @param {Function} [func] An operation to perform once secret storage has been\n * bootstrapped. Optional.\n * @param [opts] The options to use when accessing secret storage.\n */\nexport async function accessSecretStorage(\n    func = async (): Promise<void> => {},\n    opts: AccessSecretStorageOpts = {},\n): Promise<void> {\n    await withSecretStorageKeyCache(() => doAccessSecretStorage(func, opts));\n}\n\n/** Helper for {@link #accessSecretStorage} */\nasync function doAccessSecretStorage(func: () => Promise<void>, opts: AccessSecretStorageOpts): Promise<void> {\n    try {\n        const cli = MatrixClientPeg.safeGet();\n        const crypto = cli.getCrypto();\n        if (!crypto) {\n            throw new Error(\"End-to-end encryption is disabled - unable to access secret storage.\");\n        }\n\n        if (opts.forceReset) {\n            logger.debug(\"accessSecretStorage: resetting 4S\");\n            // This dialog calls bootstrap itself after guiding the user through\n            // passphrase creation.\n            const { finished } = Modal.createDialog(\n                lazy(() => import(\"./async-components/views/dialogs/security/CreateSecretStorageDialog\")),\n                opts,\n                undefined,\n                /* priority = */ false,\n                /* static = */ true,\n            );\n            const [confirmed] = await finished;\n            if (!confirmed) {\n                throw new Error(\"Secret storage creation canceled\");\n            }\n        } else if (!(await cli.secretStorage.hasKey())) {\n            logger.debug(\"accessSecretStorage: no 4S key configured\");\n            throw new Error(\"Secret storage has not been created yet.\");\n        } else {\n            logger.debug(\"accessSecretStorage: bootstrapCrossSigning\");\n            await crypto.bootstrapCrossSigning({\n                authUploadDeviceSigningKeys: async (makeRequest): Promise<void> => {\n                    logger.debug(\"accessSecretStorage: performing UIA to upload cross-signing keys\");\n                    const { finished } = Modal.createDialog(InteractiveAuthDialog, {\n                        title: _t(\"encryption|bootstrap_title\"),\n                        matrixClient: cli,\n                        makeRequest,\n                    });\n                    const [confirmed] = await finished;\n                    if (!confirmed) {\n                        throw new Error(\"Cross-signing key upload auth canceled\");\n                    }\n                    logger.debug(\"accessSecretStorage: Cross-signing key upload successful\");\n                },\n            });\n            logger.debug(\"accessSecretStorage: bootstrapSecretStorage\");\n            await crypto.bootstrapSecretStorage({});\n        }\n\n        logger.debug(\"accessSecretStorage: 4S now ready\");\n        // `return await` needed here to ensure `finally` block runs after the\n        // inner operation completes.\n        await func();\n        logger.debug(\"accessSecretStorage: operation complete\");\n    } catch (e) {\n        ModuleRunner.instance.extensions.cryptoSetup.catchAccessSecretStorageError(e as Error);\n        logger.error(\"accessSecretStorage: error during operation\", e);\n        // Re-throw so that higher level logic can abort as needed\n        throw e;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017 Aviral Dasgupta\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { clamp } from \"lodash\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { type SerializedPart } from \"./editor/parts\";\nimport type EditorModel from \"./editor/model\";\n\ninterface IHistoryItem {\n    parts: SerializedPart[];\n    replyEventId?: string;\n}\n\nexport default class SendHistoryManager {\n    public history: Array<IHistoryItem> = [];\n    public prefix: string;\n    public lastIndex = 0; // used for indexing the storage\n    public currentIndex = 0; // used for indexing the loaded validated history Array\n\n    public constructor(roomId: string, prefix: string) {\n        this.prefix = prefix + roomId;\n\n        // TODO: Performance issues?\n        let index = 0;\n        let itemJSON;\n\n        while ((itemJSON = sessionStorage.getItem(`${this.prefix}[${index}]`))) {\n            try {\n                this.history.push(JSON.parse(itemJSON));\n            } catch (e) {\n                logger.warn(\"Throwing away unserialisable history\", e);\n                break;\n            }\n            ++index;\n        }\n        this.lastIndex = this.history.length - 1;\n        // reset currentIndex to account for any unserialisable history\n        this.currentIndex = this.lastIndex + 1;\n    }\n\n    public static createItem(model: EditorModel, replyEvent?: MatrixEvent): IHistoryItem {\n        return {\n            parts: model.serializeParts(),\n            replyEventId: replyEvent ? replyEvent.getId() : undefined,\n        };\n    }\n\n    public save(editorModel: EditorModel, replyEvent?: MatrixEvent): void {\n        const item = SendHistoryManager.createItem(editorModel, replyEvent);\n        this.history.push(item);\n        this.currentIndex = this.history.length;\n        this.lastIndex += 1;\n        sessionStorage.setItem(`${this.prefix}[${this.lastIndex}]`, JSON.stringify(item));\n    }\n\n    public getItem(offset: number): IHistoryItem {\n        this.currentIndex = clamp(this.currentIndex + offset, 0, this.history.length - 1);\n        return this.history[this.currentIndex];\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/*\n * Sliding Sync Architecture - MSC https://github.com/matrix-org/matrix-spec-proposals/pull/3575\n *\n * This is a holistic summary of the changes made to Element-Web / React SDK / JS SDK to enable sliding sync.\n * This summary will hopefully signpost where developers need to look if they want to make changes to this code.\n *\n * At the lowest level, the JS SDK contains an HTTP API wrapper function in client.ts. This is used by\n * a SlidingSync class in JS SDK, which contains code to handle list operations (INSERT/DELETE/SYNC/etc)\n * and contains the main request API bodies, but has no code to control updating JS SDK structures: it just\n * exposes an EventEmitter to listen for updates. When MatrixClient.startClient is called, callers need to\n * provide a SlidingSync instance as this contains the main request API params (timeline limit, required state,\n * how many lists, etc).\n *\n * The SlidingSyncSdk INTERNAL class in JS SDK attaches listeners to SlidingSync to update JS SDK Room objects,\n * and it conveniently exposes an identical public API to SyncApi (to allow it to be a drop-in replacement).\n *\n * At the highest level, SlidingSyncManager contains mechanisms to tell UI lists which rooms to show,\n * and contains the core request API params used in Element-Web. It does this by listening for events\n * emitted by the SlidingSync class and by modifying the request API params on the SlidingSync class.\n *\n *    (entry point)                     (updates JS SDK)\n *  SlidingSyncManager                   SlidingSyncSdk\n *       |                                     |\n *       +------------------.------------------+\n *         listens          |          listens\n *                     SlidingSync\n *                     (sync loop,\n *                      list ops)\n */\n\nimport { type MatrixClient, ClientEvent, EventType, type Room } from \"matrix-js-sdk/src/matrix\";\nimport {\n    type MSC3575Filter,\n    type MSC3575List,\n    type MSC3575SlidingSyncResponse,\n    MSC3575_STATE_KEY_LAZY,\n    MSC3575_STATE_KEY_ME,\n    MSC3575_WILDCARD,\n    SlidingSync,\n    SlidingSyncEvent,\n    SlidingSyncState,\n} from \"matrix-js-sdk/src/sliding-sync\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { sleep } from \"matrix-js-sdk/src/utils\";\n\n// how long to long poll for\nconst SLIDING_SYNC_TIMEOUT_MS = 20 * 1000;\n\n// The state events we will get for every single room/space/old room/etc\n// This list is only augmented when a direct room subscription is made. (e.g you view a room)\nconst REQUIRED_STATE_LIST = [\n    [EventType.RoomJoinRules, \"\"], // the public icon on the room list\n    [EventType.RoomAvatar, \"\"], // any room avatar\n    [EventType.RoomCanonicalAlias, \"\"], // for room name calculations\n    [EventType.RoomTombstone, \"\"], // lets JS SDK hide rooms which are dead\n    [EventType.RoomEncryption, \"\"], // lets rooms be configured for E2EE correctly\n    [EventType.RoomCreate, \"\"], // for isSpaceRoom checks\n    [EventType.SpaceChild, MSC3575_WILDCARD], // all space children\n    [EventType.SpaceParent, MSC3575_WILDCARD], // all space parents\n    [EventType.RoomMember, MSC3575_STATE_KEY_ME], // lets the client calculate that we are in fact in the room\n];\n\n// the things to fetch when a user clicks on a room\nconst DEFAULT_ROOM_SUBSCRIPTION_INFO = {\n    timeline_limit: 50,\n    // missing required_state which will change depending on the kind of room\n    include_old_rooms: {\n        timeline_limit: 0,\n        required_state: REQUIRED_STATE_LIST,\n    },\n};\n// lazy load room members so rooms like Matrix HQ don't take forever to load\nconst UNENCRYPTED_SUBSCRIPTION_NAME = \"unencrypted\";\nconst UNENCRYPTED_SUBSCRIPTION = {\n    required_state: [\n        [EventType.RoomMember, MSC3575_STATE_KEY_ME], // except for m.room.members, get our own membership\n        [EventType.RoomMember, MSC3575_STATE_KEY_LAZY], // ...and lazy load the rest.\n    ],\n    ...DEFAULT_ROOM_SUBSCRIPTION_INFO,\n};\n\n// we need all the room members in encrypted rooms because we need to know which users to encrypt\n// messages for.\nconst ENCRYPTED_SUBSCRIPTION = {\n    required_state: [\n        [MSC3575_WILDCARD, MSC3575_WILDCARD], // all events\n    ],\n    ...DEFAULT_ROOM_SUBSCRIPTION_INFO,\n};\n\n// the complete set of lists made in SSS. The manager will spider all of these lists depending\n// on the count for each one.\nconst sssLists: Record<string, MSC3575List> = {\n    spaces: {\n        ranges: [[0, 10]],\n        timeline_limit: 0, // we don't care about the most recent message for spaces\n        required_state: REQUIRED_STATE_LIST,\n        include_old_rooms: {\n            timeline_limit: 0,\n            required_state: REQUIRED_STATE_LIST,\n        },\n        filters: {\n            room_types: [\"m.space\"],\n        },\n    },\n    invites: {\n        ranges: [[0, 10]],\n        timeline_limit: 1, // most recent message display\n        required_state: REQUIRED_STATE_LIST,\n        include_old_rooms: {\n            timeline_limit: 0,\n            required_state: REQUIRED_STATE_LIST,\n        },\n        filters: {\n            is_invite: true,\n        },\n    },\n    favourites: {\n        ranges: [[0, 10]],\n        timeline_limit: 1, // most recent message display\n        required_state: REQUIRED_STATE_LIST,\n        include_old_rooms: {\n            timeline_limit: 0,\n            required_state: REQUIRED_STATE_LIST,\n        },\n        filters: {\n            tags: [\"m.favourite\"],\n        },\n    },\n    dms: {\n        ranges: [[0, 10]],\n        timeline_limit: 1, // most recent message display\n        required_state: REQUIRED_STATE_LIST,\n        include_old_rooms: {\n            timeline_limit: 0,\n            required_state: REQUIRED_STATE_LIST,\n        },\n        filters: {\n            is_dm: true,\n            is_invite: false,\n            // If a DM has a Favourite & Low Prio tag then it'll be shown in those lists instead\n            not_tags: [\"m.favourite\", \"m.lowpriority\"],\n        },\n    },\n    untagged: {\n        // SSS will dupe suppress invites/dms from here, so we don't need \"not dms, not invites\"\n        ranges: [[0, 10]],\n        timeline_limit: 1, // most recent message display\n        required_state: REQUIRED_STATE_LIST,\n        include_old_rooms: {\n            timeline_limit: 0,\n            required_state: REQUIRED_STATE_LIST,\n        },\n    },\n};\n\nexport type PartialSlidingSyncRequest = {\n    filters?: MSC3575Filter;\n    sort?: string[];\n    ranges?: [startIndex: number, endIndex: number][];\n};\n\n/**\n * This class manages the entirety of sliding sync at a high UI/UX level. It controls the placement\n * of placeholders in lists, controls updating sliding window ranges, and controls which events\n * are pulled down when. The intention behind this manager is be the single place to look for sliding\n * sync options and code.\n */\nexport class SlidingSyncManager {\n    public static serverSupportsSlidingSync: boolean;\n\n    public static readonly ListSpaces = \"space_list\";\n    public static readonly ListSearch = \"search_list\";\n    private static readonly internalInstance = new SlidingSyncManager();\n\n    public slidingSync?: SlidingSync;\n    private client?: MatrixClient;\n\n    private configureDefer = Promise.withResolvers<void>();\n\n    public static get instance(): SlidingSyncManager {\n        return SlidingSyncManager.internalInstance;\n    }\n\n    private configure(client: MatrixClient, proxyUrl: string): SlidingSync {\n        this.client = client;\n        // create the set of lists we will use.\n        const lists = new Map();\n        for (const listName in sssLists) {\n            lists.set(listName, sssLists[listName]);\n        }\n        // by default use the encrypted subscription as that gets everything, which is a safer\n        // default than potentially missing member events.\n        this.slidingSync = new SlidingSync(proxyUrl, lists, ENCRYPTED_SUBSCRIPTION, client, SLIDING_SYNC_TIMEOUT_MS);\n        this.slidingSync.addCustomSubscription(UNENCRYPTED_SUBSCRIPTION_NAME, UNENCRYPTED_SUBSCRIPTION);\n        this.configureDefer.resolve();\n        return this.slidingSync;\n    }\n\n    /**\n     * Ensure that this list is registered.\n     * @param listKey The list key to register\n     * @param updateArgs The fields to update on the list.\n     * @returns The complete list request params\n     */\n    public async ensureListRegistered(listKey: string, updateArgs: PartialSlidingSyncRequest): Promise<MSC3575List> {\n        logger.debug(\"ensureListRegistered:::\", listKey, updateArgs);\n        await this.configureDefer.promise;\n        let list = this.slidingSync!.getListParams(listKey);\n        if (!list) {\n            list = {\n                ranges: [[0, 20]],\n                sort: [\"by_notification_level\", \"by_recency\"],\n                timeline_limit: 1, // most recent message display: though this seems to only be needed for favourites?\n                required_state: [\n                    [EventType.RoomJoinRules, \"\"], // the public icon on the room list\n                    [EventType.RoomAvatar, \"\"], // any room avatar\n                    [EventType.RoomTombstone, \"\"], // lets JS SDK hide rooms which are dead\n                    [EventType.RoomEncryption, \"\"], // lets rooms be configured for E2EE correctly\n                    [EventType.RoomCreate, \"\"], // for isSpaceRoom checks\n                    [EventType.RoomMember, MSC3575_STATE_KEY_ME], // lets the client calculate that we are in fact in the room\n                ],\n                include_old_rooms: {\n                    timeline_limit: 0,\n                    required_state: [\n                        [EventType.RoomCreate, \"\"],\n                        [EventType.RoomTombstone, \"\"], // lets JS SDK hide rooms which are dead\n                        [EventType.SpaceChild, MSC3575_WILDCARD], // all space children\n                        [EventType.SpaceParent, MSC3575_WILDCARD], // all space parents\n                        [EventType.RoomMember, MSC3575_STATE_KEY_ME], // lets the client calculate that we are in fact in the room\n                    ],\n                },\n                ...updateArgs,\n            };\n        } else {\n            const updatedList = { ...list, ...updateArgs };\n            // cannot use objectHasDiff as we need to do deep diff checking\n            if (JSON.stringify(list) === JSON.stringify(updatedList)) {\n                logger.debug(\"list matches, not sending, update => \", updateArgs);\n                return list;\n            }\n            list = updatedList;\n        }\n\n        try {\n            // if we only have range changes then call a different function so we don't nuke the list from before\n            if (updateArgs.ranges && Object.keys(updateArgs).length === 1) {\n                await this.slidingSync!.setListRanges(listKey, updateArgs.ranges);\n            } else {\n                await this.slidingSync!.setList(listKey, list);\n            }\n        } catch (err) {\n            logger.debug(\"ensureListRegistered: update failed txn_id=\", err);\n        }\n        return this.slidingSync!.getListParams(listKey)!;\n    }\n\n    /**\n     * Announces that the user has chosen to view the given room and that room will now\n     * be displayed, so it should have more state loaded.\n     * @param roomId The room to set visible\n     */\n    public async setRoomVisible(roomId: string): Promise<void> {\n        await this.configureDefer.promise;\n        const subscriptions = this.slidingSync!.getRoomSubscriptions();\n        if (subscriptions.has(roomId)) return;\n\n        subscriptions.add(roomId);\n\n        const room = this.client?.getRoom(roomId);\n        // default to safety: request all state if we can't work it out. This can happen if you\n        // refresh the app whilst viewing a room: we call setRoomVisible before we know anything\n        // about the room.\n        let shouldLazyLoad = false;\n        if (room) {\n            // do not lazy load encrypted rooms as we need the entire member list.\n            shouldLazyLoad = !(await this.client?.getCrypto()?.isEncryptionEnabledInRoom(roomId));\n        }\n        logger.log(\"SlidingSync setRoomVisible:\", roomId, \"shouldLazyLoad:\", shouldLazyLoad);\n        if (shouldLazyLoad) {\n            // lazy load this room\n            this.slidingSync!.useCustomSubscription(roomId, UNENCRYPTED_SUBSCRIPTION_NAME);\n        }\n        this.slidingSync!.modifyRoomSubscriptions(subscriptions);\n        if (room) {\n            return; // we have data already for this room, show immediately e.g it's in a list\n        }\n        // wait until we know about this room. This may take a little while.\n        return new Promise((resolve) => {\n            logger.log(`SlidingSync setRoomVisible room ${roomId} not found, waiting for ClientEvent.Room`);\n            const waitForRoom = (r: Room): void => {\n                if (r.roomId === roomId) {\n                    this.client?.off(ClientEvent.Room, waitForRoom);\n                    logger.log(`SlidingSync room ${roomId} found, resolving setRoomVisible`);\n                    resolve();\n                }\n            };\n            this.client?.on(ClientEvent.Room, waitForRoom);\n        });\n    }\n\n    /**\n     * Retrieve all rooms on the user's account. Retrieval is gradual over time.\n     * This function MUST be called BEFORE the first sync request goes out.\n     * @param batchSize The number of rooms to return in each request.\n     * @param gapBetweenRequestsMs The number of milliseconds to wait between requests.\n     */\n    private async startSpidering(\n        slidingSync: SlidingSync,\n        batchSize: number,\n        gapBetweenRequestsMs: number,\n    ): Promise<void> {\n        // The manager has created several lists (see `sssLists` in this file), all of which will be spidered simultaneously.\n        // There are multiple lists to ensure that we can populate invites/favourites/DMs sections immediately, rather than\n        // potentially waiting minutes if they are all very old rooms (and hence are returned last by the server). In this\n        // way, the lists are effectively priority requests. We don't actually care which room goes into which list at this\n        // point, as the RoomListStore will calculate this based on the returned data.\n\n        // copy the initial set of list names and ranges, we'll keep this map updated.\n        const listToUpperBound = new Map(\n            Object.keys(sssLists).map((listName) => {\n                return [listName, sssLists[listName].ranges[0][1]];\n            }),\n        );\n        console.log(\"startSpidering:\", listToUpperBound);\n\n        // listen for a response from the server. ANY 200 OK will do here, as we assume that it is ACKing\n        // the request change we have sent out. TODO: this may not be true if you concurrently subscribe to a room :/\n        // but in that case, for spidering at least, it isn't the end of the world as request N+1 includes all indexes\n        // from request N.\n        const lifecycle = async (\n            state: SlidingSyncState,\n            _: MSC3575SlidingSyncResponse | null,\n            err?: Error,\n        ): Promise<void> => {\n            if (state !== SlidingSyncState.Complete) {\n                return;\n            }\n            await sleep(gapBetweenRequestsMs); // don't tightloop; even on errors\n            if (err) {\n                return;\n            }\n\n            // for all lists with total counts > range => increase the range\n            let hasSetRanges = false;\n            listToUpperBound.forEach((currentUpperBound, listName) => {\n                const totalCount = slidingSync.getListData(listName)?.joinedCount || 0;\n                if (currentUpperBound < totalCount) {\n                    // increment the upper bound\n                    const newUpperBound = currentUpperBound + batchSize;\n                    console.log(`startSpidering: ${listName} ${currentUpperBound} => ${newUpperBound}`);\n                    listToUpperBound.set(listName, newUpperBound);\n                    // make the next request. This will only send the request when this callback has finished, so if\n                    // we set all the list ranges at once we will only send 1 new request.\n                    slidingSync.setListRanges(listName, [[0, newUpperBound]]);\n                    hasSetRanges = true;\n                }\n            });\n            if (!hasSetRanges) {\n                // finish spidering\n                slidingSync.off(SlidingSyncEvent.Lifecycle, lifecycle);\n            }\n        };\n        slidingSync.on(SlidingSyncEvent.Lifecycle, lifecycle);\n    }\n\n    /**\n     * Set up the Sliding Sync instance; configures the end point and starts spidering.\n     * The sliding sync endpoint is derived the following way:\n     *   1. The user-defined sliding sync proxy URL (legacy, for backwards compatibility)\n     *   2. The client `well-known` sliding sync proxy URL [declared at the unstable prefix](https://github.com/matrix-org/matrix-spec-proposals/blob/kegan/sync-v3/proposals/3575-sync.md#unstable-prefix)\n     *   3. The homeserver base url (for native server support)\n     * @param client The MatrixClient to use\n     * @returns A working Sliding Sync or undefined\n     */\n    public async setup(client: MatrixClient): Promise<SlidingSync | undefined> {\n        const slidingSync = this.configure(client, client.baseUrl);\n        logger.info(\"Simplified Sliding Sync activated at\", client.baseUrl);\n        this.startSpidering(slidingSync, 50, 50); // 50 rooms at a time, 50ms apart\n        return slidingSync;\n    }\n\n    /**\n     * Check if the server \"natively\" supports sliding sync (with an unstable endpoint).\n     * @param client The MatrixClient to use\n     * @return Whether the \"native\" (unstable) endpoint is supported\n     */\n    public async nativeSlidingSyncSupport(client: MatrixClient): Promise<boolean> {\n        // Per https://github.com/matrix-org/matrix-spec-proposals/pull/3575/files#r1589542561\n        // `client` can be undefined/null in tests for some reason.\n        const support = await client?.doesServerSupportUnstableFeature(\"org.matrix.simplified_msc3575\");\n        if (support) {\n            logger.log(\"nativeSlidingSyncSupport: org.matrix.simplified_msc3575 sliding sync advertised as unstable\");\n        }\n        return support;\n    }\n\n    /**\n     * Check whether our homeserver has sliding sync support, that the endpoint is up, and\n     * is a sliding sync endpoint.\n     *\n     * Sets static member `SlidingSyncController.serverSupportsSlidingSync`\n     * @param client The MatrixClient to use\n     */\n    public async checkSupport(client: MatrixClient): Promise<void> {\n        if (await this.nativeSlidingSyncSupport(client)) {\n            SlidingSyncManager.serverSupportsSlidingSync = true;\n            return;\n        }\n        SlidingSyncManager.serverSupportsSlidingSync = false;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport browserlist from \"browserslist\";\nimport PopOutIcon from \"@vector-im/compound-design-tokens/assets/web/icons/pop-out\";\n\nimport { DeviceType, parseUserAgent } from \"./utils/device/parseUserAgent\";\nimport ToastStore from \"./stores/ToastStore\";\nimport GenericToast from \"./components/views/toasts/GenericToast\";\nimport { _t } from \"./languageHandler\";\nimport SdkConfig from \"./SdkConfig\";\n\nexport const LOCAL_STORAGE_KEY = \"mx_accepts_unsupported_browser\";\nconst TOAST_KEY = \"unsupportedbrowser\";\n\nconst SUPPORTED_DEVICE_TYPES = [DeviceType.Web, DeviceType.Desktop];\nconst SUPPORTED_BROWSER_QUERY =\n    \"last 2 Chrome versions, last 2 Firefox versions, last 2 Safari versions, last 2 Edge versions\";\nconst LEARN_MORE_URL = \"https://github.com/element-hq/element-web#supported-environments\";\n\nfunction onLearnMoreClick(): void {\n    onDismissClick();\n    window.open(LEARN_MORE_URL, \"_blank\", \"noopener,noreferrer\");\n}\n\nfunction onDismissClick(): void {\n    localStorage.setItem(LOCAL_STORAGE_KEY, String(true));\n    ToastStore.sharedInstance().dismissToast(TOAST_KEY);\n}\n\nfunction getBrowserNameVersion(browser: string): [name: string, version: number] {\n    const [browserName, browserVersion] = browser.split(\" \");\n    const browserNameLc = browserName.toLowerCase();\n    return [browserNameLc, parseInt(browserVersion, 10)];\n}\n\n/**\n * Function to check if the current browser is considered supported by our support policy.\n * Based on user agent parsing so may be inaccurate if the user has fingerprint prevention turned up to 11.\n */\nexport function getBrowserSupport(): boolean {\n    const browsers = browserlist(SUPPORTED_BROWSER_QUERY).sort();\n    const minimumBrowserVersions = new Map<string, number>();\n    for (const browser of browsers) {\n        const [browserName, browserVersion] = getBrowserNameVersion(browser);\n        // We sorted the browsers so will encounter the minimum version first\n        if (minimumBrowserVersions.has(browserName)) continue;\n        minimumBrowserVersions.set(browserName, browserVersion);\n    }\n\n    const details = parseUserAgent(navigator.userAgent);\n\n    let supported = true;\n    if (!SUPPORTED_DEVICE_TYPES.includes(details.deviceType)) {\n        logger.warn(\"Browser unsupported, unsupported device type\", details.deviceType);\n        supported = false;\n    }\n\n    if (details.client) {\n        // We don't care about the browser version for desktop devices\n        // We ship our own browser (electron) for desktop devices\n        if (details.deviceType === DeviceType.Desktop) {\n            return supported;\n        }\n\n        const [browserName, browserVersion] = getBrowserNameVersion(details.client);\n        const minimumVersion = minimumBrowserVersions.get(browserName);\n        // Check both with the sub-version cut off and without as some browsers have less granular versioning e.g. Safari\n        if (!minimumVersion || browserVersion < minimumVersion) {\n            logger.warn(\"Browser unsupported, unsupported user agent\", details.client);\n            supported = false;\n        }\n    } else {\n        logger.warn(\"Browser unsupported, unknown client\", navigator.userAgent);\n        supported = false;\n    }\n\n    return supported;\n}\n\n/**\n * Shows a user warning toast if the user's browser is not supported.\n */\nexport function checkBrowserSupport(): void {\n    const supported = getBrowserSupport();\n    if (supported) return;\n\n    if (localStorage.getItem(LOCAL_STORAGE_KEY)) {\n        logger.warn(\"Browser unsupported, but user has previously accepted\");\n        return;\n    }\n\n    const brand = SdkConfig.get().brand;\n    ToastStore.sharedInstance().addOrReplaceToast({\n        key: TOAST_KEY,\n        title: _t(\"unsupported_browser|title\", { brand }),\n        props: {\n            description: _t(\"unsupported_browser|description\", { brand }),\n            secondaryLabel: _t(\"action|learn_more\"),\n            SecondaryIcon: PopOutIcon,\n            onSecondaryClick: onLearnMoreClick,\n            primaryLabel: _t(\"action|dismiss\"),\n            onPrimaryClick: onDismissClick,\n        },\n        component: GenericToast,\n        priority: 40,\n    });\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { SERVICE_TYPES } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../languageHandler\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport BaseDialog from \"./BaseDialog\";\nimport { pickBestPolicyLanguage, type ServicePolicyPair } from \"../../../Terms\";\nimport ExternalLink from \"../elements/ExternalLink\";\nimport { parseUrl } from \"../../../utils/UrlUtils\";\n\ninterface ITermsCheckboxProps {\n    onChange: (url: string, checked: boolean) => void;\n    url: string;\n    checked: boolean;\n}\n\nclass TermsCheckbox extends React.PureComponent<ITermsCheckboxProps> {\n    private onChange = (ev: React.FormEvent<HTMLInputElement>): void => {\n        this.props.onChange(this.props.url, ev.currentTarget.checked);\n    };\n\n    public render(): React.ReactNode {\n        return <input type=\"checkbox\" onChange={this.onChange} checked={this.props.checked} />;\n    }\n}\n\ninterface ITermsDialogProps {\n    /**\n     * Array of [Service, policies] pairs, where policies is the response from the\n     * /terms endpoint for that service\n     */\n    policiesAndServicePairs: ServicePolicyPair[];\n\n    /**\n     * urls that the user has already agreed to\n     */\n    agreedUrls: string[];\n\n    /**\n     * Called with:\n     *     * success {bool} True if the user accepted any douments, false if cancelled\n     *     * agreedUrls {string[]} List of agreed URLs\n     */\n    onFinished: (success: boolean, agreedUrls?: string[]) => void;\n}\n\ninterface IState {\n    agreedUrls: any;\n}\n\nexport default class TermsDialog extends React.PureComponent<ITermsDialogProps, IState> {\n    public constructor(props: ITermsDialogProps) {\n        super(props);\n        this.state = {\n            // url -> boolean\n            agreedUrls: {},\n        };\n        for (const url of props.agreedUrls) {\n            this.state.agreedUrls[url] = true;\n        }\n    }\n\n    private onCancelClick = (): void => {\n        this.props.onFinished(false);\n    };\n\n    private onNextClick = (): void => {\n        this.props.onFinished(\n            true,\n            Object.keys(this.state.agreedUrls).filter((url) => this.state.agreedUrls[url]),\n        );\n    };\n\n    private nameForServiceType(serviceType: SERVICE_TYPES, host: string): JSX.Element {\n        switch (serviceType) {\n            case SERVICE_TYPES.IS:\n                return (\n                    <div>\n                        {_t(\"common|identity_server\")}\n                        <br />({host})\n                    </div>\n                );\n            case SERVICE_TYPES.IM:\n                return (\n                    <div>\n                        {_t(\"common|integration_manager\")}\n                        <br />({host})\n                    </div>\n                );\n        }\n    }\n\n    private summaryForServiceType(serviceType: SERVICE_TYPES): JSX.Element {\n        switch (serviceType) {\n            case SERVICE_TYPES.IS:\n                return (\n                    <div>\n                        {_t(\"terms|summary_identity_server_1\")}\n                        <br />\n                        {_t(\"terms|summary_identity_server_2\")}\n                    </div>\n                );\n            case SERVICE_TYPES.IM:\n                return <div>{_t(\"terms|integration_manager\")}</div>;\n        }\n    }\n\n    private onTermsCheckboxChange = (url: string, checked: boolean): void => {\n        this.setState({\n            agreedUrls: Object.assign({}, this.state.agreedUrls, { [url]: checked }),\n        });\n    };\n\n    public render(): React.ReactNode {\n        const rows: JSX.Element[] = [];\n        for (const policiesAndService of this.props.policiesAndServicePairs) {\n            const parsedBaseUrl = parseUrl(policiesAndService.service.baseUrl);\n\n            const policyValues = Object.values(policiesAndService.policies);\n            for (let i = 0; i < policyValues.length; ++i) {\n                const internationalisedPolicy = pickBestPolicyLanguage(policyValues[i]);\n                if (!internationalisedPolicy) continue;\n                let serviceName: JSX.Element | undefined;\n                let summary: JSX.Element | undefined;\n                if (i === 0) {\n                    serviceName = this.nameForServiceType(policiesAndService.service.serviceType, parsedBaseUrl.host);\n                    summary = this.summaryForServiceType(policiesAndService.service.serviceType);\n                }\n\n                rows.push(\n                    <tr key={internationalisedPolicy.url}>\n                        <td className=\"mx_TermsDialog_service\">{serviceName}</td>\n                        <td className=\"mx_TermsDialog_summary\">{summary}</td>\n                        <td>\n                            <ExternalLink rel=\"noreferrer noopener\" target=\"_blank\" href={internationalisedPolicy.url}>\n                                {internationalisedPolicy.name}\n                            </ExternalLink>\n                        </td>\n                        <td>\n                            <TermsCheckbox\n                                url={internationalisedPolicy.url}\n                                onChange={this.onTermsCheckboxChange}\n                                checked={Boolean(this.state.agreedUrls[internationalisedPolicy.url])}\n                            />\n                        </td>\n                    </tr>,\n                );\n            }\n        }\n\n        // if all the documents for at least one service have been checked, we can enable\n        // the submit button\n        let enableSubmit = false;\n        for (const policiesAndService of this.props.policiesAndServicePairs) {\n            let docsAgreedForService = 0;\n            for (const terms of Object.values(policiesAndService.policies)) {\n                let docAgreed = false;\n                for (const lang of Object.keys(terms)) {\n                    if (lang === \"version\" || typeof terms[lang] === \"string\") continue;\n                    if (this.state.agreedUrls[terms[lang].url]) {\n                        docAgreed = true;\n                        break;\n                    }\n                }\n                if (docAgreed) {\n                    ++docsAgreedForService;\n                }\n            }\n            if (docsAgreedForService === Object.keys(policiesAndService.policies).length) {\n                enableSubmit = true;\n                break;\n            }\n        }\n\n        return (\n            <BaseDialog\n                fixedWidth={false}\n                onFinished={this.onCancelClick}\n                title={_t(\"terms|tos\")}\n                contentId=\"mx_Dialog_content\"\n                hasCancel={false}\n            >\n                <div id=\"mx_Dialog_content\">\n                    <p>{_t(\"terms|intro\")}</p>\n\n                    <table className=\"mx_TermsDialog_termsTable\">\n                        <tbody>\n                            <tr className=\"mx_TermsDialog_termsTableHeader\">\n                                <th>{_t(\"terms|column_service\")}</th>\n                                <th>{_t(\"terms|column_summary\")}</th>\n                                <th>{_t(\"terms|column_document\")}</th>\n                                <th>{_t(\"action|accept\")}</th>\n                            </tr>\n                            {rows}\n                        </tbody>\n                    </table>\n                </div>\n\n                <DialogButtons\n                    primaryButton={_t(\"action|next\")}\n                    hasCancel={true}\n                    onCancel={this.onCancelClick}\n                    onPrimaryButtonClick={this.onNextClick}\n                    primaryDisabled={!enableSubmit}\n                />\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport classNames from \"classnames\";\nimport {\n    type SERVICE_TYPES,\n    type MatrixClient,\n    type Terms,\n    type Policy,\n    type InternationalisedPolicy,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport Modal from \"./Modal\";\nimport TermsDialog from \"./components/views/dialogs/TermsDialog\";\nimport { pickBestLanguage } from \"./languageHandler.tsx\";\n\nexport class TermsNotSignedError extends Error {}\n\n/**\n * Class representing a service that may have terms & conditions that\n * require agreement from the user before the user can use that service.\n */\nexport class Service {\n    /**\n     * @param {MatrixClient.SERVICE_TYPES} serviceType The type of service\n     * @param {string} baseUrl The Base URL of the service (ie. before '/_matrix')\n     * @param {string} accessToken The user's access token for the service\n     */\n    public constructor(\n        public serviceType: SERVICE_TYPES,\n        public baseUrl: string,\n        public accessToken: string,\n    ) {}\n}\n\nexport type ServicePolicyPair = {\n    policies: Terms[\"policies\"];\n    service: Service;\n};\n\nexport type TermsInteractionCallback = (\n    policiesAndServicePairs: ServicePolicyPair[],\n    agreedUrls: string[],\n    extraClassNames?: string,\n) => Promise<string[]>;\n\nexport function pickBestPolicyLanguage(policy: Policy): InternationalisedPolicy | undefined {\n    const termsLang = pickBestLanguage(Object.keys(policy).filter((k) => k !== \"version\"));\n    return <InternationalisedPolicy>policy[termsLang];\n}\n\n/**\n * Start a flow where the user is presented with terms & conditions for some services\n *\n * @param client The Matrix Client instance of the logged-in user\n * @param {Service[]} services Object with keys 'serviceType', 'baseUrl', 'accessToken'\n * @param {function} interactionCallback Function called with:\n *      * an array of { service: {Service}, policies: {terms response from API} }\n *      * an array of URLs the user has already agreed to\n *     Must return a Promise which resolves with a list of URLs of documents agreed to\n * @returns {Promise} resolves when the user agreed to all necessary terms or rejects\n *     if they cancel.\n */\nexport async function startTermsFlow(\n    client: MatrixClient,\n    services: Service[],\n    interactionCallback: TermsInteractionCallback = dialogTermsInteractionCallback,\n): Promise<void> {\n    const termsPromises = services.map((s) => client.getTerms(s.serviceType, s.baseUrl));\n\n    /*\n     * a /terms response looks like:\n     * {\n     *     \"policies\": {\n     *         \"terms_of_service\": {\n     *             \"version\": \"2.0\",\n     *              \"en\": {\n     *                 \"name\": \"Terms of Service\",\n     *                 \"url\": \"https://example.org/somewhere/terms-2.0-en.html\"\n     *             },\n     *             \"fr\": {\n     *                 \"name\": \"Conditions d'utilisation\",\n     *                 \"url\": \"https://example.org/somewhere/terms-2.0-fr.html\"\n     *             }\n     *         }\n     *     }\n     * }\n     */\n\n    const terms: Terms[] = await Promise.all(termsPromises);\n    const policiesAndServicePairs = terms.map((t, i) => {\n        return { service: services[i], policies: t.policies };\n    });\n\n    // fetch the set of agreed policy URLs from account data\n    const currentAcceptedTerms = client.getAccountData(\"m.accepted_terms\")?.getContent();\n    const agreedUrlSet = new Set<string>(currentAcceptedTerms?.accepted || []);\n\n    // remove any policies the user has already agreed to and any services where\n    // they've already agreed to all the policies\n    // NB. it could be nicer to show the user stuff they've already agreed to,\n    // but then they'd assume they can un-check the boxes to un-agree to a policy,\n    // but that is not a thing the API supports, so probably best to just show\n    // things they've not agreed to yet.\n    const unagreedPoliciesAndServicePairs: ServicePolicyPair[] = [];\n    for (const { service, policies } of policiesAndServicePairs) {\n        const unagreedPolicies: Terms[\"policies\"] = {};\n        for (const [policyName, policy] of Object.entries(policies)) {\n            let policyAgreed = false;\n            for (const lang of Object.keys(policy)) {\n                if (lang === \"version\" || typeof policy[lang] === \"string\") continue;\n                if (agreedUrlSet.has(policy[lang].url)) {\n                    policyAgreed = true;\n                    break;\n                }\n            }\n            if (!policyAgreed) unagreedPolicies[policyName] = policy;\n        }\n        if (Object.keys(unagreedPolicies).length > 0) {\n            unagreedPoliciesAndServicePairs.push({ service, policies: unagreedPolicies });\n        }\n    }\n\n    // if there's anything left to agree to, prompt the user\n    const numAcceptedBeforeAgreement = agreedUrlSet.size;\n    if (unagreedPoliciesAndServicePairs.length > 0) {\n        const newlyAgreedUrls = await interactionCallback(unagreedPoliciesAndServicePairs, [...agreedUrlSet]);\n        logger.log(\"User has agreed to URLs\", newlyAgreedUrls);\n        // Merge with previously agreed URLs\n        newlyAgreedUrls.forEach((url) => agreedUrlSet.add(url));\n    } else {\n        logger.log(\"User has already agreed to all required policies\");\n    }\n\n    // We only ever add to the set of URLs, so if anything has changed then we'd see a different length\n    if (agreedUrlSet.size !== numAcceptedBeforeAgreement) {\n        const newAcceptedTerms = { accepted: Array.from(agreedUrlSet) };\n        await client.setAccountData(\"m.accepted_terms\", newAcceptedTerms);\n    }\n\n    const agreePromises = policiesAndServicePairs.map((policiesAndService) => {\n        // filter the agreed URL list for ones that are actually for this service\n        // (one URL may be used for multiple services)\n        // Not a particularly efficient loop but probably fine given the numbers involved\n        const urlsForService = Array.from(agreedUrlSet).filter((url) => {\n            for (const policy of Object.values(policiesAndService.policies)) {\n                for (const lang of Object.keys(policy)) {\n                    if (lang === \"version\" || typeof policy[lang] === \"string\") continue;\n                    if (policy[lang].url === url) return true;\n                }\n            }\n            return false;\n        });\n\n        if (urlsForService.length === 0) return Promise.resolve();\n\n        return client.agreeToTerms(\n            policiesAndService.service.serviceType,\n            policiesAndService.service.baseUrl,\n            policiesAndService.service.accessToken,\n            urlsForService,\n        );\n    });\n    await Promise.all(agreePromises);\n}\n\nexport async function dialogTermsInteractionCallback(\n    policiesAndServicePairs: {\n        service: Service;\n        policies: { [policy: string]: Policy };\n    }[],\n    agreedUrls: string[],\n    extraClassNames?: string,\n): Promise<string[]> {\n    logger.log(\"Terms that need agreement\", policiesAndServicePairs);\n\n    const { finished } = Modal.createDialog(\n        TermsDialog,\n        {\n            policiesAndServicePairs,\n            agreedUrls,\n        },\n        classNames(\"mx_TermsDialog\", extraClassNames),\n    );\n\n    const [done, _agreedUrls] = await finished;\n    if (!done || !_agreedUrls) {\n        throw new TermsNotSignedError();\n    }\n    return _agreedUrls;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../languageHandler\";\n\nexport function getSenderName(event: MatrixEvent): string {\n    return event.sender?.name ?? event.getSender() ?? _t(\"common|someone\");\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport {\n    type MatrixEvent,\n    type MatrixClient,\n    GuestAccess,\n    HistoryVisibility,\n    JoinRule,\n    EventType,\n    MsgType,\n    M_POLL_START,\n    M_POLL_END,\n    ContentHelpers,\n} from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { removeDirectionOverrideChars } from \"matrix-js-sdk/src/utils\";\nimport { type PollStartEvent } from \"matrix-js-sdk/src/extensible_events_v1/PollStartEvent\";\n\nimport { _t } from \"./languageHandler\";\nimport * as Roles from \"./Roles\";\nimport { isValid3pidInvite } from \"./RoomInvite\";\nimport SettingsStore from \"./settings/SettingsStore\";\nimport { ALL_RULE_TYPES, ROOM_RULE_TYPES, SERVER_RULE_TYPES, USER_RULE_TYPES } from \"./mjolnir/BanList\";\nimport { WIDGET_LAYOUT_EVENT_TYPE } from \"./stores/widgets/WidgetLayoutStore\";\nimport { RightPanelPhases } from \"./stores/right-panel/RightPanelStorePhases\";\nimport defaultDispatcher from \"./dispatcher/dispatcher\";\nimport { RoomSettingsTab } from \"./components/views/dialogs/RoomSettingsDialog\";\nimport AccessibleButton from \"./components/views/elements/AccessibleButton\";\nimport RightPanelStore from \"./stores/right-panel/RightPanelStore\";\nimport { highlightEvent, isLocationEvent } from \"./utils/EventUtils\";\nimport { getSenderName } from \"./utils/event/getSenderName\";\nimport PosthogTrackers from \"./PosthogTrackers.ts\";\nimport { ElementCallEventType } from \"./call-types.ts\";\n\nfunction getRoomMemberDisplayname(client: MatrixClient, event: MatrixEvent, userId = event.getSender()): string {\n    const roomId = event.getRoomId();\n    const member = client.getRoom(roomId)?.getMember(userId!);\n    return member?.name || member?.rawDisplayName || userId || _t(\"common|someone\");\n}\n\nfunction textForCallEvent(event: MatrixEvent, client: MatrixClient): () => string {\n    const roomName = client.getRoom(event.getRoomId()!)?.name;\n    const isSupported = client.supportsVoip();\n\n    return isSupported\n        ? () => _t(\"timeline|m.call|video_call_started\", { roomName })\n        : () => _t(\"timeline|m.call|video_call_started_unsupported\", { roomName });\n}\n\n// These functions are frequently used just to check whether an event has\n// any text to display at all. For this reason they return deferred values\n// to avoid the expense of looking up translations when they're not needed.\n\nfunction textForCallInviteEvent(event: MatrixEvent, client: MatrixClient): (() => string) | null {\n    const senderName = getSenderName(event);\n    // FIXME: Find a better way to determine this from the event?\n    const isVoice = !event.getContent().offer?.sdp?.includes(\"m=video\");\n    const isSupported = client.supportsVoip();\n\n    // This ladder could be reduced down to a couple string variables, however other languages\n    // can have a hard time translating those strings. In an effort to make translations easier\n    // and more accurate, we break out the string-based variables to a couple booleans.\n    if (isVoice && isSupported) {\n        return () => _t(\"timeline|m.call.invite|voice_call\", { senderName });\n    } else if (isVoice && !isSupported) {\n        return () => _t(\"timeline|m.call.invite|voice_call_unsupported\", { senderName });\n    } else if (!isVoice && isSupported) {\n        return () => _t(\"timeline|m.call.invite|video_call\", { senderName });\n    } else if (!isVoice && !isSupported) {\n        return () => _t(\"timeline|m.call.invite|video_call_unsupported\", { senderName });\n    }\n\n    return null;\n}\n\nenum Modification {\n    None,\n    Unset,\n    Set,\n    Changed,\n}\n\nfunction getModification(prev?: string, value?: string): Modification {\n    if (prev && value && prev !== value) {\n        return Modification.Changed;\n    }\n    if (prev && !value) {\n        return Modification.Unset;\n    }\n    if (!prev && value) {\n        return Modification.Set;\n    }\n\n    return Modification.None;\n}\n\nfunction textForMemberEvent(\n    ev: MatrixEvent,\n    client: MatrixClient,\n    allowJSX: boolean,\n    showHiddenEvents?: boolean,\n): (() => string) | null {\n    // XXX: SYJS-16 \"sender is sometimes null for join messages\"\n    const senderName = ev.sender?.name || getRoomMemberDisplayname(client, ev);\n    const targetName = ev.target?.name || getRoomMemberDisplayname(client, ev, ev.getStateKey());\n    const prevContent = ev.getPrevContent();\n    const content = ev.getContent();\n    const reason = content.reason;\n\n    switch (content.membership) {\n        case KnownMembership.Invite: {\n            const threePidContent = content.third_party_invite;\n            if (threePidContent) {\n                if (threePidContent.display_name) {\n                    return () =>\n                        _t(\"timeline|m.room.member|accepted_3pid_invite\", {\n                            targetName,\n                            displayName: threePidContent.display_name,\n                        });\n                } else {\n                    return () => _t(\"timeline|m.room.member|accepted_invite\", { targetName });\n                }\n            } else {\n                return () => _t(\"timeline|m.room.member|invite\", { senderName, targetName });\n            }\n        }\n        case KnownMembership.Ban:\n            return () =>\n                reason\n                    ? _t(\"timeline|m.room.member|ban_reason\", { senderName, targetName, reason })\n                    : _t(\"timeline|m.room.member|ban\", { senderName, targetName });\n        case KnownMembership.Join:\n            if (prevContent && prevContent.membership === KnownMembership.Join) {\n                const modDisplayname = getModification(prevContent.displayname, content.displayname);\n                const modAvatarUrl = getModification(prevContent.avatar_url, content.avatar_url);\n\n                if (modDisplayname !== Modification.None && modAvatarUrl !== Modification.None) {\n                    // Compromise to provide the user with more context without needing 16 translations\n                    return () =>\n                        _t(\"timeline|m.room.member|change_name_avatar\", {\n                            // We're taking the display namke directly from the event content here so we need\n                            // to strip direction override chars which the js-sdk would normally do when\n                            // calculating the display name\n                            oldDisplayName: removeDirectionOverrideChars(prevContent.displayname!),\n                        });\n                } else if (modDisplayname === Modification.Changed) {\n                    return () =>\n                        _t(\"timeline|m.room.member|change_name\", {\n                            // We're taking the display name directly from the event content here so we need\n                            // to strip direction override chars which the js-sdk would normally do when\n                            // calculating the display name\n                            oldDisplayName: removeDirectionOverrideChars(prevContent.displayname!),\n                            displayName: removeDirectionOverrideChars(content.displayname!),\n                        });\n                } else if (modDisplayname === Modification.Set) {\n                    return () =>\n                        _t(\"timeline|m.room.member|set_name\", {\n                            senderName: ev.getSender(),\n                            displayName: removeDirectionOverrideChars(content.displayname!),\n                        });\n                } else if (modDisplayname === Modification.Unset) {\n                    return () =>\n                        _t(\"timeline|m.room.member|remove_name\", {\n                            senderName,\n                            oldDisplayName: removeDirectionOverrideChars(prevContent.displayname!),\n                        });\n                } else if (modAvatarUrl === Modification.Unset) {\n                    return () => _t(\"timeline|m.room.member|remove_avatar\", { senderName });\n                } else if (modAvatarUrl === Modification.Changed) {\n                    return () => _t(\"timeline|m.room.member|change_avatar\", { senderName });\n                } else if (modAvatarUrl === Modification.Set) {\n                    return () => _t(\"timeline|m.room.member|set_avatar\", { senderName });\n                } else if (showHiddenEvents ?? SettingsStore.getValue(\"showHiddenEventsInTimeline\")) {\n                    // This is a null rejoin, it will only be visible if using 'show hidden events' (labs)\n                    return () => _t(\"timeline|m.room.member|no_change\", { senderName });\n                } else {\n                    return null;\n                }\n            } else {\n                if (!ev.target) logger.warn(\"Join message has no target! -- \" + ev.getContent().state_key);\n                return () => _t(\"timeline|m.room.member|join\", { targetName });\n            }\n        case KnownMembership.Leave:\n            if (ev.getSender() === ev.getStateKey()) {\n                if (prevContent.membership === KnownMembership.Invite) {\n                    return () =>\n                        reason\n                            ? _t(\"timeline|m.room.member|reject_invite_reason\", { targetName, reason })\n                            : _t(\"timeline|m.room.member|reject_invite\", { targetName });\n                } else {\n                    return () =>\n                        reason\n                            ? _t(\"timeline|m.room.member|left_reason\", { targetName, reason })\n                            : _t(\"timeline|m.room.member|left\", { targetName });\n                }\n            } else if (prevContent.membership === KnownMembership.Ban) {\n                return () => _t(\"timeline|m.room.member|unban\", { senderName, targetName });\n            } else if (prevContent.membership === KnownMembership.Invite) {\n                return () =>\n                    reason\n                        ? _t(\"timeline|m.room.member|withdrew_invite_reason\", {\n                              senderName,\n                              targetName,\n                              reason,\n                          })\n                        : _t(\"timeline|m.room.member|withdrew_invite\", { senderName, targetName });\n            } else if (prevContent.membership === KnownMembership.Join) {\n                return () =>\n                    reason\n                        ? _t(\"timeline|m.room.member|kick_reason\", {\n                              senderName,\n                              targetName,\n                              reason,\n                          })\n                        : _t(\"timeline|m.room.member|kick\", { senderName, targetName });\n            } else {\n                return null;\n            }\n    }\n\n    return null;\n}\n\nfunction textForTopicEvent(ev: MatrixEvent): (() => string) | null {\n    const senderDisplayName = ev.sender && ev.sender.name ? ev.sender.name : ev.getSender();\n    const topic = ContentHelpers.parseTopicContent(ev.getContent()).text;\n    return () =>\n        topic\n            ? _t(\"timeline|m.room.topic|changed\", {\n                  senderDisplayName,\n                  topic,\n              })\n            : _t(\"timeline|m.room.topic|removed\", {\n                  senderDisplayName,\n              });\n}\n\nfunction textForRoomAvatarEvent(ev: MatrixEvent): (() => string) | null {\n    const senderDisplayName = ev?.sender?.name || ev.getSender();\n    return () => _t(\"timeline|m.room.avatar|changed\", { senderDisplayName });\n}\n\nfunction textForRoomNameEvent(ev: MatrixEvent): (() => string) | null {\n    const senderDisplayName = ev.sender && ev.sender.name ? ev.sender.name : ev.getSender();\n\n    if (!ev.getContent().name || ev.getContent().name.trim().length === 0) {\n        return () => _t(\"timeline|m.room.name|remove\", { senderDisplayName });\n    }\n    if (ev.getPrevContent().name) {\n        return () =>\n            _t(\"timeline|m.room.name|change\", {\n                senderDisplayName,\n                oldRoomName: ev.getPrevContent().name,\n                newRoomName: ev.getContent().name,\n            });\n    }\n    return () =>\n        _t(\"timeline|m.room.name|set\", {\n            senderDisplayName,\n            roomName: ev.getContent().name,\n        });\n}\n\nfunction textForTombstoneEvent(ev: MatrixEvent): (() => string) | null {\n    const senderDisplayName = ev.sender && ev.sender.name ? ev.sender.name : ev.getSender();\n    return () => _t(\"timeline|m.room.tombstone\", { senderDisplayName });\n}\n\nconst onViewJoinRuleSettingsClick = (): void => {\n    defaultDispatcher.dispatch({\n        action: \"open_room_settings\",\n        initial_tab_id: RoomSettingsTab.Security,\n    });\n};\n\nfunction textForJoinRulesEvent(ev: MatrixEvent, client: MatrixClient, allowJSX: boolean): () => Renderable {\n    const senderDisplayName = ev.sender && ev.sender.name ? ev.sender.name : ev.getSender();\n    switch (ev.getContent().join_rule) {\n        case JoinRule.Public:\n            return () =>\n                _t(\"timeline|m.room.join_rules|public\", {\n                    senderDisplayName,\n                });\n        case JoinRule.Invite:\n            return () =>\n                _t(\"timeline|m.room.join_rules|invite\", {\n                    senderDisplayName,\n                });\n        case JoinRule.Knock:\n            return () => _t(\"timeline|m.room.join_rules|knock\", { senderDisplayName });\n        case JoinRule.Restricted:\n            if (allowJSX) {\n                return () => (\n                    <span>\n                        {_t(\n                            \"timeline|m.room.join_rules|restricted_settings\",\n                            {\n                                senderDisplayName,\n                            },\n                            {\n                                a: (sub) => (\n                                    <AccessibleButton kind=\"link_inline\" onClick={onViewJoinRuleSettingsClick}>\n                                        {sub}\n                                    </AccessibleButton>\n                                ),\n                            },\n                        )}\n                    </span>\n                );\n            }\n\n            return () => _t(\"timeline|m.room.join_rules|restricted\", { senderDisplayName });\n        default:\n            // The spec supports \"knock\" and \"private\", however nothing implements these.\n            return () =>\n                _t(\"timeline|m.room.join_rules|unknown\", {\n                    senderDisplayName,\n                    rule: ev.getContent().join_rule,\n                });\n    }\n}\n\nfunction textForGuestAccessEvent(ev: MatrixEvent): (() => string) | null {\n    const senderDisplayName = ev.sender && ev.sender.name ? ev.sender.name : ev.getSender();\n    switch (ev.getContent().guest_access) {\n        case GuestAccess.CanJoin:\n            return () => _t(\"timeline|m.room.guest_access|can_join\", { senderDisplayName });\n        case GuestAccess.Forbidden:\n            return () => _t(\"timeline|m.room.guest_access|forbidden\", { senderDisplayName });\n        default:\n            // There's no other options we can expect, however just for safety's sake we'll do this.\n            return () =>\n                _t(\"timeline|m.room.guest_access|unknown\", {\n                    senderDisplayName,\n                    rule: ev.getContent().guest_access,\n                });\n    }\n}\n\nfunction textForMessageEvent(ev: MatrixEvent, client: MatrixClient): (() => string) | null {\n    if (isLocationEvent(ev)) {\n        return textForLocationEvent(ev);\n    }\n\n    return () => {\n        const senderDisplayName = ev.sender && ev.sender.name ? ev.sender.name : ev.getSender();\n        let message = ev.getContent().body;\n        if (ev.isRedacted()) {\n            message = textForRedactedPollAndMessageEvent(ev, client);\n        }\n\n        if (ev.getContent().msgtype === MsgType.Emote) {\n            message = \"* \" + senderDisplayName + \" \" + message;\n        } else if (ev.getContent().msgtype === MsgType.Image) {\n            message = _t(\"timeline|m.image|sent\", { senderDisplayName });\n        } else if (ev.getType() == EventType.Sticker) {\n            message = _t(\"timeline|m.sticker\", { senderDisplayName });\n        } else {\n            // in this case, parse it as a plain text message\n            message = senderDisplayName + \": \" + message;\n        }\n        return message;\n    };\n}\n\nfunction textForCanonicalAliasEvent(ev: MatrixEvent): (() => string) | null {\n    const senderName = getSenderName(ev);\n    const oldAlias = ev.getPrevContent().alias;\n    const oldAltAliases = ev.getPrevContent().alt_aliases || [];\n    const newAlias = ev.getContent().alias;\n    const newAltAliases = ev.getContent().alt_aliases || [];\n    const removedAltAliases = oldAltAliases.filter((alias: string) => !newAltAliases.includes(alias));\n    const addedAltAliases = newAltAliases.filter((alias: string) => !oldAltAliases.includes(alias));\n\n    if (!removedAltAliases.length && !addedAltAliases.length) {\n        if (newAlias) {\n            return () =>\n                _t(\"timeline|m.room.canonical_alias|set\", {\n                    senderName,\n                    address: ev.getContent().alias,\n                });\n        } else if (oldAlias) {\n            return () =>\n                _t(\"timeline|m.room.canonical_alias|removed\", {\n                    senderName,\n                });\n        }\n    } else if (newAlias === oldAlias) {\n        if (addedAltAliases.length && !removedAltAliases.length) {\n            return () =>\n                _t(\"timeline|m.room.canonical_alias|alt_added\", {\n                    senderName,\n                    addresses: addedAltAliases.join(\", \"),\n                    count: addedAltAliases.length,\n                });\n        }\n        if (removedAltAliases.length && !addedAltAliases.length) {\n            return () =>\n                _t(\"timeline|m.room.canonical_alias|alt_removed\", {\n                    senderName,\n                    addresses: removedAltAliases.join(\", \"),\n                    count: removedAltAliases.length,\n                });\n        }\n        if (removedAltAliases.length && addedAltAliases.length) {\n            return () =>\n                _t(\"timeline|m.room.canonical_alias|changed_alternative\", {\n                    senderName,\n                });\n        }\n    } else {\n        // both alias and alt_aliases where modified\n        return () =>\n            _t(\"timeline|m.room.canonical_alias|changed_main_and_alternative\", {\n                senderName,\n            });\n    }\n    // in case there is no difference between the two events,\n    // say something as we can't simply hide the tile from here\n    return () =>\n        _t(\"timeline|m.room.canonical_alias|changed\", {\n            senderName,\n        });\n}\n\nfunction textForThreePidInviteEvent(event: MatrixEvent): (() => string) | null {\n    const senderName = getSenderName(event);\n\n    if (!isValid3pidInvite(event)) {\n        return () =>\n            _t(\"timeline|m.room.third_party_invite|revoked\", {\n                senderName,\n                targetDisplayName: event.getPrevContent().display_name || _t(\"common|someone\"),\n            });\n    }\n\n    return () =>\n        _t(\"timeline|m.room.third_party_invite|sent\", {\n            senderName,\n            targetDisplayName: event.getContent().display_name,\n        });\n}\n\nfunction textForHistoryVisibilityEvent(event: MatrixEvent): (() => string) | null {\n    const senderName = getSenderName(event);\n    switch (event.getContent().history_visibility) {\n        case HistoryVisibility.Invited:\n            return () => _t(\"timeline|m.room.history_visibility|invited\", { senderName });\n        case HistoryVisibility.Joined:\n            return () =>\n                _t(\"timeline|m.room.history_visibility|joined\", {\n                    senderName,\n                });\n        case HistoryVisibility.Shared:\n            return () => _t(\"timeline|m.room.history_visibility|shared\", { senderName });\n        case HistoryVisibility.WorldReadable:\n            return () => _t(\"timeline|m.room.history_visibility|world_readable\", { senderName });\n        default:\n            return () =>\n                _t(\"timeline|m.room.history_visibility|unknown\", {\n                    senderName,\n                    visibility: event.getContent().history_visibility,\n                });\n    }\n}\n\n// Currently will only display a change if a user's power level is changed\nfunction textForPowerEvent(event: MatrixEvent, client: MatrixClient): (() => string) | null {\n    const senderName = getSenderName(event);\n    if (!event.getPrevContent()?.users || !event.getContent()?.users) {\n        return null;\n    }\n    const previousUserDefault: number = event.getPrevContent().users_default || 0;\n    const currentUserDefault: number = event.getContent().users_default || 0;\n    // Construct set of userIds\n    const users: string[] = [];\n    Object.keys(event.getContent().users).forEach((userId) => {\n        if (users.indexOf(userId) === -1) users.push(userId);\n    });\n    Object.keys(event.getPrevContent().users).forEach((userId) => {\n        if (users.indexOf(userId) === -1) users.push(userId);\n    });\n\n    const diffs: {\n        userId: string;\n        name: string;\n        from: number;\n        to: number;\n    }[] = [];\n    users.forEach((userId) => {\n        // Previous power level\n        let from: number = event.getPrevContent().users[userId];\n        if (!Number.isInteger(from)) {\n            from = previousUserDefault;\n        }\n        // Current power level\n        let to = event.getContent().users[userId];\n        if (!Number.isInteger(to)) {\n            to = currentUserDefault;\n        }\n        if (from === previousUserDefault && to === currentUserDefault) {\n            return;\n        }\n        if (to !== from) {\n            const name = getRoomMemberDisplayname(client, event, userId);\n            diffs.push({ userId, name, from, to });\n        }\n    });\n    if (!diffs.length) {\n        return null;\n    }\n\n    // XXX: This is also surely broken for i18n\n    return () =>\n        _t(\"timeline|m.room.power_levels|changed\", {\n            senderName,\n            powerLevelDiffText: diffs\n                .map((diff) =>\n                    _t(\"timeline|m.room.power_levels|user_from_to\", {\n                        userId: diff.name,\n                        fromPowerLevel: Roles.textualPowerLevel(diff.from, previousUserDefault),\n                        toPowerLevel: Roles.textualPowerLevel(diff.to, currentUserDefault),\n                    }),\n                )\n                .join(\", \"),\n        });\n}\n\nconst onPinnedMessagesClick = (): void => {\n    PosthogTrackers.trackInteraction(\"PinnedMessageStateEventClick\");\n    RightPanelStore.instance.setCard({ phase: RightPanelPhases.PinnedMessages }, false);\n};\n\nfunction textForPinnedEvent(event: MatrixEvent, client: MatrixClient, allowJSX: boolean): (() => Renderable) | null {\n    const senderName = getSenderName(event);\n    const roomId = event.getRoomId()!;\n\n    const content = event.getContent<{ pinned: string[] }>();\n    const prevContent = event.getPrevContent();\n\n    const pinned = Array.isArray(content.pinned) ? content.pinned : [];\n    const previouslyPinned: string[] = Array.isArray(prevContent.pinned) ? prevContent.pinned : [];\n    const newlyPinned = pinned.filter((item) => previouslyPinned.indexOf(item) < 0);\n    const newlyUnpinned = previouslyPinned.filter((item) => pinned.indexOf(item) < 0);\n\n    if (newlyPinned.length === 1 && newlyUnpinned.length === 0) {\n        // A single message was pinned, include a link to that message.\n        if (allowJSX) {\n            const messageId = newlyPinned.pop()!;\n\n            return () => (\n                <span>\n                    {_t(\n                        \"timeline|m.room.pinned_events|pinned_link\",\n                        { senderName },\n                        {\n                            a: (sub) => (\n                                <AccessibleButton\n                                    kind=\"link_inline\"\n                                    onClick={() => {\n                                        PosthogTrackers.trackInteraction(\"PinnedMessageStateEventClick\");\n                                        highlightEvent(roomId, messageId);\n                                    }}\n                                >\n                                    {sub}\n                                </AccessibleButton>\n                            ),\n                            b: (sub) => (\n                                <AccessibleButton kind=\"link_inline\" onClick={onPinnedMessagesClick}>\n                                    {sub}\n                                </AccessibleButton>\n                            ),\n                        },\n                    )}\n                </span>\n            );\n        }\n\n        return () => _t(\"timeline|m.room.pinned_events|pinned\", { senderName });\n    }\n\n    if (newlyUnpinned.length === 1 && newlyPinned.length === 0) {\n        // A single message was unpinned, include a link to that message.\n        if (allowJSX) {\n            const messageId = newlyUnpinned.pop()!;\n\n            return () => (\n                <span>\n                    {_t(\n                        \"timeline|m.room.pinned_events|unpinned_link\",\n                        { senderName },\n                        {\n                            a: (sub) => (\n                                <AccessibleButton\n                                    kind=\"link_inline\"\n                                    onClick={() => {\n                                        PosthogTrackers.trackInteraction(\"PinnedMessageStateEventClick\");\n                                        highlightEvent(roomId, messageId);\n                                    }}\n                                >\n                                    {sub}\n                                </AccessibleButton>\n                            ),\n                            b: (sub) => (\n                                <AccessibleButton kind=\"link_inline\" onClick={onPinnedMessagesClick}>\n                                    {sub}\n                                </AccessibleButton>\n                            ),\n                        },\n                    )}\n                </span>\n            );\n        }\n\n        return () => _t(\"timeline|m.room.pinned_events|unpinned\", { senderName });\n    }\n\n    if (allowJSX) {\n        return () => (\n            <span>\n                {_t(\n                    \"timeline|m.room.pinned_events|changed_link\",\n                    { senderName },\n                    {\n                        a: (sub) => (\n                            <AccessibleButton kind=\"link_inline\" onClick={onPinnedMessagesClick}>\n                                {sub}\n                            </AccessibleButton>\n                        ),\n                    },\n                )}\n            </span>\n        );\n    }\n\n    return () => _t(\"timeline|m.room.pinned_events|changed\", { senderName });\n}\n\nfunction textForWidgetEvent(event: MatrixEvent): (() => string) | null {\n    const senderName = getSenderName(event);\n    const { name: prevName, type: prevType, url: prevUrl } = event.getPrevContent();\n    const { name, type, url } = event.getContent() || {};\n\n    let widgetName = name || prevName || type || prevType || \"\";\n    // Apply sentence case to widget name\n    if (widgetName && widgetName.length > 0) {\n        widgetName = widgetName[0].toUpperCase() + widgetName.slice(1);\n    }\n\n    // If the widget was removed, its content should be {}, but this is sufficiently\n    // equivalent to that condition.\n    if (url) {\n        if (prevUrl) {\n            return () =>\n                _t(\"timeline|m.widget|modified\", {\n                    widgetName,\n                    senderName,\n                });\n        } else {\n            return () =>\n                _t(\"timeline|m.widget|added\", {\n                    widgetName,\n                    senderName,\n                });\n        }\n    } else {\n        return () =>\n            _t(\"timeline|m.widget|removed\", {\n                widgetName,\n                senderName,\n            });\n    }\n}\n\nfunction textForWidgetLayoutEvent(event: MatrixEvent): (() => string) | null {\n    const senderName = getSenderName(event);\n    return () => _t(\"timeline|io.element.widgets.layout\", { senderName });\n}\n\nfunction textForMjolnirEvent(event: MatrixEvent): (() => string) | null {\n    const senderName = getSenderName(event);\n    const { entity: prevEntity } = event.getPrevContent();\n    const { entity, recommendation, reason } = event.getContent();\n\n    // Rule removed\n    if (!entity) {\n        if (USER_RULE_TYPES.includes(event.getType())) {\n            return () => _t(\"timeline|mjolnir|removed_rule_users\", { senderName, glob: prevEntity });\n        } else if (ROOM_RULE_TYPES.includes(event.getType())) {\n            return () => _t(\"timeline|mjolnir|removed_rule_rooms\", { senderName, glob: prevEntity });\n        } else if (SERVER_RULE_TYPES.includes(event.getType())) {\n            return () =>\n                _t(\"timeline|mjolnir|removed_rule_servers\", {\n                    senderName,\n                    glob: prevEntity,\n                });\n        }\n\n        // Unknown type. We'll say something, but we shouldn't end up here.\n        return () => _t(\"timeline|mjolnir|removed_rule\", { senderName, glob: prevEntity });\n    }\n\n    // Invalid rule\n    if (!recommendation || !reason) return () => _t(\"timeline|mjolnir|updated_invalid_rule\", { senderName });\n\n    // Rule updated\n    if (entity === prevEntity) {\n        if (USER_RULE_TYPES.includes(event.getType())) {\n            return () =>\n                _t(\"timeline|mjolnir|updated_rule_users\", {\n                    senderName,\n                    glob: entity,\n                    reason,\n                });\n        } else if (ROOM_RULE_TYPES.includes(event.getType())) {\n            return () =>\n                _t(\"timeline|mjolnir|updated_rule_rooms\", {\n                    senderName,\n                    glob: entity,\n                    reason,\n                });\n        } else if (SERVER_RULE_TYPES.includes(event.getType())) {\n            return () =>\n                _t(\"timeline|mjolnir|updated_rule_servers\", {\n                    senderName,\n                    glob: entity,\n                    reason,\n                });\n        }\n\n        // Unknown type. We'll say something but we shouldn't end up here.\n        return () =>\n            _t(\"timeline|mjolnir|updated_rule\", {\n                senderName,\n                glob: entity,\n                reason,\n            });\n    }\n\n    // New rule\n    if (!prevEntity) {\n        if (USER_RULE_TYPES.includes(event.getType())) {\n            return () =>\n                _t(\"timeline|mjolnir|created_rule_users\", {\n                    senderName,\n                    glob: entity,\n                    reason,\n                });\n        } else if (ROOM_RULE_TYPES.includes(event.getType())) {\n            return () =>\n                _t(\"timeline|mjolnir|created_rule_rooms\", {\n                    senderName,\n                    glob: entity,\n                    reason,\n                });\n        } else if (SERVER_RULE_TYPES.includes(event.getType())) {\n            return () =>\n                _t(\"timeline|mjolnir|created_rule_servers\", {\n                    senderName,\n                    glob: entity,\n                    reason,\n                });\n        }\n\n        // Unknown type. We'll say something but we shouldn't end up here.\n        return () =>\n            _t(\"timeline|mjolnir|created_rule\", {\n                senderName,\n                glob: entity,\n                reason,\n            });\n    }\n\n    // else the entity !== prevEntity - count as a removal & add\n    if (USER_RULE_TYPES.includes(event.getType())) {\n        return () =>\n            _t(\"timeline|mjolnir|changed_rule_users\", { senderName, oldGlob: prevEntity, newGlob: entity, reason });\n    } else if (ROOM_RULE_TYPES.includes(event.getType())) {\n        return () =>\n            _t(\"timeline|mjolnir|changed_rule_rooms\", { senderName, oldGlob: prevEntity, newGlob: entity, reason });\n    } else if (SERVER_RULE_TYPES.includes(event.getType())) {\n        return () =>\n            _t(\"timeline|mjolnir|changed_rule_servers\", { senderName, oldGlob: prevEntity, newGlob: entity, reason });\n    }\n\n    // Unknown type. We'll say something but we shouldn't end up here.\n    return () =>\n        _t(\"timeline|mjolnir|changed_rule_glob\", {\n            senderName,\n            oldGlob: prevEntity,\n            newGlob: entity,\n            reason,\n        });\n}\n\nexport function textForLocationEvent(event: MatrixEvent): () => string {\n    return () =>\n        _t(\"timeline|m.location|full\", {\n            senderName: getSenderName(event),\n        });\n}\n\nfunction textForRedactedPollAndMessageEvent(ev: MatrixEvent, client: MatrixClient): string {\n    let message = _t(\"timeline|self_redaction\");\n    const unsigned = ev.getUnsigned();\n    const redactedBecauseUserId = unsigned?.redacted_because?.sender;\n    if (redactedBecauseUserId && redactedBecauseUserId !== ev.getSender()) {\n        const room = client.getRoom(ev.getRoomId());\n        const sender = room?.getMember(redactedBecauseUserId);\n        message = _t(\"timeline|redaction\", {\n            name: sender?.name || redactedBecauseUserId,\n        });\n    }\n\n    return message;\n}\n\nfunction textForPollStartEvent(event: MatrixEvent, client: MatrixClient): (() => string) | null {\n    return () => {\n        let message = \"\";\n\n        if (event.isRedacted()) {\n            message = textForRedactedPollAndMessageEvent(event, client);\n            const senderDisplayName = event.sender?.name ?? event.getSender();\n            message = senderDisplayName + \": \" + message;\n        } else {\n            message = _t(\"timeline|m.poll.start\", {\n                senderName: getSenderName(event),\n                pollQuestion: (event.unstableExtensibleEvent as PollStartEvent)?.question?.text,\n            });\n        }\n\n        return message;\n    };\n}\n\nfunction textForPollEndEvent(event: MatrixEvent): (() => string) | null {\n    return () =>\n        _t(\"timeline|m.poll.end|sender_ended\", {\n            senderName: getSenderName(event),\n        });\n}\n\ntype Renderable = string | React.ReactNode | null;\n\ninterface IHandlers {\n    [type: string]: (\n        ev: MatrixEvent,\n        client: MatrixClient,\n        allowJSX: boolean,\n        showHiddenEvents?: boolean,\n    ) => (() => Renderable) | null;\n}\n\nconst handlers: IHandlers = {\n    [EventType.RoomMessage]: textForMessageEvent,\n    [EventType.Sticker]: textForMessageEvent,\n    [EventType.CallInvite]: textForCallInviteEvent,\n    [M_POLL_START.name]: textForPollStartEvent,\n    [M_POLL_END.name]: textForPollEndEvent,\n    [M_POLL_START.altName]: textForPollStartEvent,\n    [M_POLL_END.altName]: textForPollEndEvent,\n};\n\nconst stateHandlers: IHandlers = {\n    [EventType.RoomCanonicalAlias]: textForCanonicalAliasEvent,\n    [EventType.RoomName]: textForRoomNameEvent,\n    [EventType.RoomTopic]: textForTopicEvent,\n    [EventType.RoomMember]: textForMemberEvent,\n    [EventType.RoomAvatar]: textForRoomAvatarEvent,\n    [EventType.RoomThirdPartyInvite]: textForThreePidInviteEvent,\n    [EventType.RoomHistoryVisibility]: textForHistoryVisibilityEvent,\n    [EventType.RoomPowerLevels]: textForPowerEvent,\n    [EventType.RoomPinnedEvents]: textForPinnedEvent,\n    [EventType.RoomTombstone]: textForTombstoneEvent,\n    [EventType.RoomJoinRules]: textForJoinRulesEvent,\n    [EventType.RoomGuestAccess]: textForGuestAccessEvent,\n\n    // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n    \"im.vector.modular.widgets\": textForWidgetEvent,\n    [WIDGET_LAYOUT_EVENT_TYPE]: textForWidgetLayoutEvent,\n};\n\n// Add all the Mjolnir stuff to the renderer\nfor (const evType of ALL_RULE_TYPES) {\n    stateHandlers[evType] = textForMjolnirEvent;\n}\n\n// Add both stable and unstable m.call events\nfor (const evType of ElementCallEventType.names) {\n    stateHandlers[evType] = textForCallEvent;\n}\n\n/**\n * Determines whether the given event has text to display.\n *\n * @param client The Matrix Client instance for the logged-in user\n * @param ev The event\n * @param showHiddenEvents An optional cached setting value for showHiddenEventsInTimeline\n *     to avoid hitting the settings store\n */\nexport function hasText(ev: MatrixEvent, client: MatrixClient, showHiddenEvents?: boolean): boolean {\n    const handler = (ev.isState() ? stateHandlers : handlers)[ev.getType()];\n    try {\n        return Boolean(handler?.(ev, client, false, showHiddenEvents));\n    } catch (e) {\n        console.error(`Error encountered when trying to render event type=${ev.getType()} id=${ev.getId()}`, e);\n        // Returning true if we have a handler so we can show an error tile rather than no tile at all\n        return !!handler;\n    }\n}\n\n/**\n * Gets the textual content of the given event.\n *\n * @param ev The event\n * @param client The Matrix Client instance for the logged-in user\n * @param allowJSX Whether to output rich JSX content\n * @param showHiddenEvents An optional cached setting value for showHiddenEventsInTimeline\n *     to avoid hitting the settings store\n */\nexport function textForEvent(ev: MatrixEvent, client: MatrixClient): string;\nexport function textForEvent(\n    ev: MatrixEvent,\n    client: MatrixClient,\n    allowJSX: true,\n    showHiddenEvents?: boolean,\n): string | React.ReactNode;\nexport function textForEvent(\n    ev: MatrixEvent,\n    client: MatrixClient,\n    allowJSX = false,\n    showHiddenEvents?: boolean,\n): string | React.ReactNode {\n    const handler = (ev.isState() ? stateHandlers : handlers)[ev.getType()];\n    return handler?.(ev, client, allowJSX, showHiddenEvents)?.() || \"\";\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { SettingLevel } from \"./settings/SettingLevel\";\nimport SettingsStore from \"./settings/SettingsStore\";\n\nexport const USER_TIMEZONE_KEY = \"userTimezone\";\n\n/**\n * Returning `undefined` ensure that if unset the browser default will be used in `DateTimeFormat`.\n * @returns The user specified timezone or `undefined`\n */\nexport function getUserTimezone(): string | undefined {\n    const tz = SettingsStore.getValueAt(SettingLevel.DEVICE, USER_TIMEZONE_KEY);\n    return tz || undefined;\n}\n\n/**\n * Set in the settings the given timezone\n * @timezone\n */\nexport function setUserTimezone(timezone: string): Promise<void> {\n    return SettingsStore.setValue(USER_TIMEZONE_KEY, null, SettingLevel.DEVICE, timezone);\n}\n\n/**\n * Return all the available timezones\n */\nexport function getAllTimezones(): string[] {\n    return Intl.supportedValuesOf(\"timeZone\");\n}\n\n/**\n * Return the current timezone in a short human readable way\n */\nexport function shortBrowserTimezone(): string {\n    return (\n        new Intl.DateTimeFormat(undefined, { timeZoneName: \"short\" })\n            .formatToParts(new Date())\n            .find((x) => x.type === \"timeZoneName\")?.value ?? \"GMT\"\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport function isNotNull<T>(arg: T): arg is Exclude<T, null> {\n    return arg !== null;\n}\n\nexport function isNotUndefined<T>(arg: T): arg is Exclude<T, undefined> {\n    return arg !== undefined;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { M_BEACON, type Room, Thread, type MatrixEvent, EventType, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport shouldHideEvent from \"./shouldHideEvent\";\nimport { haveRendererForEvent } from \"./events/EventTileFactory\";\nimport { RoomNotifState, getRoomNotifsState } from \"./RoomNotifs\";\n\n/**\n * Returns true if this event arriving in a room should affect the room's\n * count of unread messages\n *\n * @param client The Matrix Client instance of the logged-in user\n * @param {Object} ev The event\n * @returns {boolean} True if the given event should affect the unread message count\n */\nexport function eventTriggersUnreadCount(client: MatrixClient, ev: MatrixEvent): boolean {\n    if (ev.getSender() === client.getSafeUserId()) {\n        return false;\n    }\n\n    switch (ev.getType()) {\n        case EventType.RoomMember:\n        case EventType.RoomThirdPartyInvite:\n        case EventType.CallAnswer:\n        case EventType.CallHangup:\n        case EventType.RoomCanonicalAlias:\n        case EventType.RoomServerAcl:\n        case M_BEACON.name:\n        case M_BEACON.altName:\n            return false;\n    }\n\n    if (ev.isRedacted()) return false;\n    try {\n        return haveRendererForEvent(ev, client, false /* hidden messages should never trigger unread counts anyways */);\n    } catch (e) {\n        console.warn(\"Error determining if event should trigger unread count\", e);\n        return false; // If we can't determine if the event should trigger an unread count, assume it does not.\n    }\n}\n\nexport function doesRoomHaveUnreadMessages(room: Room, includeThreads: boolean): boolean {\n    const toCheck: Array<Room | Thread> = [room];\n    if (includeThreads) {\n        toCheck.push(...room.getThreads());\n    }\n\n    for (const withTimeline of toCheck) {\n        if (doesTimelineHaveUnreadMessages(room, withTimeline.timeline)) {\n            // We found an unread, so the room is unread\n            return true;\n        }\n    }\n\n    // If we got here then no timelines were found with unread messages.\n    return false;\n}\n\nfunction doesTimelineHaveUnreadMessages(room: Room, timeline: Array<MatrixEvent>): boolean {\n    // The room is a space, let's ignore it\n    if (room.isSpaceRoom()) return false;\n\n    const myUserId = room.client.getSafeUserId();\n    const latestImportantEventId = findLatestImportantEvent(room.client, timeline)?.getId();\n    if (latestImportantEventId) {\n        return !room.hasUserReadEvent(myUserId, latestImportantEventId);\n    } else {\n        // We couldn't find an important event to check - check the unimportant ones.\n        const earliestUnimportantEventId = timeline.at(0)?.getId();\n        if (!earliestUnimportantEventId) {\n            // There are no events in this timeline - it is uninitialised, so we\n            // consider it read\n            return false;\n        } else if (room.hasUserReadEvent(myUserId, earliestUnimportantEventId)) {\n            // Some of the unimportant events are read, and there are no\n            // important ones after them, so we've read everything.\n            return false;\n        } else {\n            // We have events. and none of them are read.  We must guess that\n            // the timeline is unread, because there could be older unread\n            // important events that we don't have loaded.\n            logger.warn(\"Falling back to unread room because of no read receipt or counting message found\", {\n                roomId: room.roomId,\n                earliestUnimportantEventId: earliestUnimportantEventId,\n            });\n            return true;\n        }\n    }\n}\n\n/**\n * Returns true if this room has unread threads.\n * @param room The room to check\n * @returns {boolean} True if the given room has unread threads\n */\nexport function doesRoomHaveUnreadThreads(room: Room): boolean {\n    if (getRoomNotifsState(room.client, room.roomId) === RoomNotifState.Mute) {\n        // No unread for muted rooms, nor their threads\n        // NB. This logic duplicated in RoomNotifs.determineUnreadState\n        return false;\n    }\n\n    for (const thread of room.getThreads()) {\n        if (doesTimelineHaveUnreadMessages(room, thread.timeline)) {\n            // We found an unread, so the room has an unread thread\n            return true;\n        }\n    }\n\n    // If we got here then no threads were found with unread messages.\n    return false;\n}\n\nexport function doesRoomOrThreadHaveUnreadMessages(roomOrThread: Room | Thread): boolean {\n    const room = roomOrThread instanceof Thread ? roomOrThread.room : roomOrThread;\n    const events = roomOrThread instanceof Thread ? roomOrThread.timeline : room.getLiveTimeline().getEvents();\n    return doesTimelineHaveUnreadMessages(room, events);\n}\n\n/**\n * Look backwards through the timeline and find the last event that is\n * \"important\" in the sense of isImportantEvent.\n *\n * @returns the latest important event, or null if none were found\n */\nfunction findLatestImportantEvent(client: MatrixClient, timeline: Array<MatrixEvent>): MatrixEvent | null {\n    for (let index = timeline.length - 1; index >= 0; index--) {\n        const event = timeline[index];\n        if (isImportantEvent(client, event)) {\n            return event;\n        }\n    }\n    return null;\n}\n\n/**\n * Given this event does not have a receipt, is it important enough to make\n * this room unread?\n */\nfunction isImportantEvent(client: MatrixClient, event: MatrixEvent): boolean {\n    return !shouldHideEvent(event) && eventTriggersUnreadCount(client, event);\n}\n","/*\nCopyright 2019-2024 New Vector Ltd.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport dis from \"./dispatcher/dispatcher\";\nimport Timer from \"./utils/Timer\";\nimport { Action } from \"./dispatcher/actions.ts\";\n\n// important these are larger than the timeouts of timers\n// used with UserActivity.timeWhileActive*,\n// such as READ_MARKER_INVIEW_THRESHOLD_MS (timeWhileActiveRecently),\n// READ_MARKER_OUTOFVIEW_THRESHOLD_MS (timeWhileActiveRecently),\n// READ_RECEIPT_INTERVAL_MS (timeWhileActiveNow) in TimelinePanel\n\n// 'Under a few seconds'. Must be less than 'RECENTLY_ACTIVE_THRESHOLD_MS'\nconst CURRENTLY_ACTIVE_THRESHOLD_MS = 700;\n\n// 'Under a few minutes'.\nconst RECENTLY_ACTIVE_THRESHOLD_MS = 2 * 60 * 1000;\n\n/**\n * This class watches for user activity (moving the mouse or pressing a key)\n * and starts/stops attached timers while the user is active.\n *\n * There are two classes of 'active': 'active now' and 'active recently'\n * see doc on the userActive* functions for what these mean.\n */\nexport default class UserActivity {\n    private readonly activeNowTimeout: Timer;\n    private readonly activeRecentlyTimeout: Timer;\n    private attachedActiveNowTimers: Timer[] = [];\n    private attachedActiveRecentlyTimers: Timer[] = [];\n    private lastScreenX = 0;\n    private lastScreenY = 0;\n\n    public constructor(\n        private readonly window: Window,\n        private readonly document: Document,\n    ) {\n        this.activeNowTimeout = new Timer(CURRENTLY_ACTIVE_THRESHOLD_MS);\n        this.activeRecentlyTimeout = new Timer(RECENTLY_ACTIVE_THRESHOLD_MS);\n    }\n\n    public static sharedInstance(): UserActivity {\n        if (window.mxUserActivity === undefined) {\n            window.mxUserActivity = new UserActivity(window, document);\n        }\n        return window.mxUserActivity;\n    }\n\n    /**\n     * Runs the given timer while the user is 'active now', aborting when the user is no longer\n     * considered currently active.\n     * See userActiveNow() for what it means for a user to be 'active'.\n     * Can be called multiple times with the same already running timer, which is a NO-OP.\n     * Can be called before the user becomes active, in which case it is only started\n     * later on when the user does become active.\n     * @param {Timer} timer the timer to use\n     */\n    public timeWhileActiveNow(timer: Timer): void {\n        this.timeWhile(timer, this.attachedActiveNowTimers);\n        if (this.userActiveNow()) {\n            timer.start();\n        }\n    }\n\n    /**\n     * Runs the given timer while the user is 'active' now or recently,\n     * aborting when the user becomes inactive.\n     * See userActiveRecently() for what it means for a user to be 'active recently'.\n     * Can be called multiple times with the same already running timer, which is a NO-OP.\n     * Can be called before the user becomes active, in which case it is only started\n     * later on when the user does become active.\n     * @param {Timer} timer the timer to use\n     */\n    public timeWhileActiveRecently(timer: Timer): void {\n        this.timeWhile(timer, this.attachedActiveRecentlyTimers);\n        if (this.userActiveRecently()) {\n            timer.start();\n        }\n    }\n\n    private timeWhile(timer: Timer, attachedTimers: Timer[]): void {\n        // important this happens first\n        const index = attachedTimers.indexOf(timer);\n        if (index === -1) {\n            attachedTimers.push(timer);\n            // remove when done or aborted\n            timer\n                .finished()\n                .finally(() => {\n                    const index = attachedTimers.indexOf(timer);\n                    if (index !== -1) {\n                        // should never be -1\n                        attachedTimers.splice(index, 1);\n                    }\n                    // as we fork the promise here,\n                    // avoid unhandled rejection warnings\n                })\n                .catch((err) => {});\n        }\n    }\n\n    /**\n     * Start listening to user activity\n     */\n    public start(): void {\n        this.document.addEventListener(\"mousedown\", this.onUserActivity);\n        this.document.addEventListener(\"mousemove\", this.onUserActivity);\n        this.document.addEventListener(\"keydown\", this.onUserActivity);\n        this.document.addEventListener(\"visibilitychange\", this.onPageVisibilityChanged);\n        this.window.addEventListener(\"blur\", this.onWindowBlurred);\n        this.window.addEventListener(\"focus\", this.onUserActivity);\n        // can't use document.scroll here because that's only the document\n        // itself being scrolled. Need to use addEventListener's useCapture.\n        // also this needs to be the wheel event, not scroll, as scroll is\n        // fired when the view scrolls down for a new message.\n        this.window.addEventListener(\"wheel\", this.onUserActivity, {\n            passive: true,\n            capture: true,\n        });\n    }\n\n    /**\n     * Stop tracking user activity\n     */\n    public stop(): void {\n        this.document.removeEventListener(\"mousedown\", this.onUserActivity);\n        this.document.removeEventListener(\"mousemove\", this.onUserActivity);\n        this.document.removeEventListener(\"keydown\", this.onUserActivity);\n        this.window.removeEventListener(\"wheel\", this.onUserActivity, {\n            capture: true,\n        });\n        this.document.removeEventListener(\"visibilitychange\", this.onPageVisibilityChanged);\n        this.window.removeEventListener(\"blur\", this.onWindowBlurred);\n        this.window.removeEventListener(\"focus\", this.onUserActivity);\n    }\n\n    /**\n     * Return true if the user is currently 'active'\n     * A user is 'active' while they are interacting with the app and for a very short (<1s)\n     * time after that. This is intended to give a strong indication that the app has the\n     * user's attention at any given moment.\n     * @returns {boolean} true if user is currently 'active'\n     */\n    public userActiveNow(): boolean {\n        return this.activeNowTimeout.isRunning();\n    }\n\n    /**\n     * Return true if the user is currently active or has been recently\n     * A user is 'active recently' for a longer period of time (~2 mins) after\n     * they have been 'active' and while the app still has the focus. This is\n     * intended to indicate when the app may still have the user's attention\n     * (or they may have gone to make tea and left the window focused).\n     * @returns {boolean} true if user has been active recently\n     */\n    public userActiveRecently(): boolean {\n        return this.activeRecentlyTimeout.isRunning();\n    }\n\n    private onPageVisibilityChanged = (e: Event): void => {\n        if (this.document.visibilityState === \"hidden\") {\n            this.activeNowTimeout.abort();\n            this.activeRecentlyTimeout.abort();\n        } else {\n            this.onUserActivity(e);\n        }\n    };\n\n    private onWindowBlurred = (): void => {\n        this.activeNowTimeout.abort();\n        this.activeRecentlyTimeout.abort();\n    };\n\n    // XXX: exported for tests\n    public onUserActivity = (event: Event): void => {\n        // ignore anything if the window isn't focused\n        if (!this.document.hasFocus()) return;\n\n        if (event.type === \"mousemove\" && this.isMouseEvent(event)) {\n            if (event.screenX === this.lastScreenX && event.screenY === this.lastScreenY) {\n                // mouse hasn't actually moved\n                return;\n            }\n            this.lastScreenX = event.screenX;\n            this.lastScreenY = event.screenY;\n        }\n\n        dis.dispatch({ action: Action.UserActivity });\n        if (!this.activeNowTimeout.isRunning()) {\n            this.activeNowTimeout.start();\n            UserActivity.runTimersUntilTimeout(this.attachedActiveNowTimers, this.activeNowTimeout);\n        } else {\n            this.activeNowTimeout.restart();\n        }\n\n        if (!this.activeRecentlyTimeout.isRunning()) {\n            this.activeRecentlyTimeout.start();\n\n            UserActivity.runTimersUntilTimeout(this.attachedActiveRecentlyTimers, this.activeRecentlyTimeout);\n        } else {\n            this.activeRecentlyTimeout.restart();\n        }\n    };\n\n    private static async runTimersUntilTimeout(attachedTimers: Timer[], timeout: Timer): Promise<void> {\n        attachedTimers.forEach((t) => t.start());\n        try {\n            await timeout.finished();\n        } catch {\n            /* aborted */\n        }\n        attachedTimers.forEach((t) => t.abort());\n    }\n\n    private isMouseEvent(event: Event): event is MouseEvent {\n        return event.type.startsWith(\"mouse\");\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nconst emailRegex = /^\\S+@\\S+\\.\\S+$/;\nconst mxUserIdRegex = /^@\\S+:\\S+$/;\nconst mxRoomIdRegex = /^!\\S+:\\S+$/;\n\nexport enum AddressType {\n    Email = \"email\",\n    MatrixUserId = \"mx-user-id\",\n    MatrixRoomId = \"mx-room-id\",\n}\n\nexport function getAddressType(inputText: string): AddressType | null {\n    if (emailRegex.test(inputText)) {\n        return AddressType.Email;\n    } else if (mxUserIdRegex.test(inputText)) {\n        return AddressType.MatrixUserId;\n    } else if (mxRoomIdRegex.test(inputText)) {\n        return AddressType.MatrixRoomId;\n    } else {\n        return null;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\n * Constants for MatrixChat.state.view.\n *\n * The `View` is the primary state machine of the application: it has different states for the various setup flows\n * that the user may find themselves in. Once we have a functioning client, we can transition to the `LOGGED_IN` state\n * which is the \"normal\" state of the application.\n *\n * An incomplete state transition diagram follows.\n *\n *                      (initial state)\n *                    ┌─────────────────┐ Lock held by other instance  ┌─────────────────┐\n *                    │    LOADING      │─────────────────────────────►│ CONFIRM_LOCK_   │\n *                    │                 │◄─────────────────────────────│     THEFT       │\n *                    └─────────────────┘ Lock theft confirmed         └─────────────────┘\n *     Session recovered │     │      │                                           Token/OIDC login succeeded\n *        ┌──────────────┘     │      └──────────────────────────────────────────────────────────────────┐\n *        │                    └───────────────────────────────────────────┐                             │\n *        │                                                                │ No previous session         │\n *        │                                                                ▼                             │\n *        │          (from all other states                        ┌─────────────────┐                   │\n *        │            except LOCK_STOLEN)                         │     WELCOME     │                   │\n *        │                  │                                     │                 │                   │\n *        │                  │ Client logged out                   └─────────────────┘                   │\n *        │                  │                                            │   │                          │\n *        │                  └──────────────────────────┐       \"Sign in\" │   │ \"Create account\"         │\n *        │                                             │    ┌────────────┘   └──────────────┐           │\n *        │                                             │    │                               │           │\n *        │                       \"Forgot               ▼    ▼       \"Create an              ▼           │\n *        │   ┌─────────────────┐  password\"     ┌─────────────────┐   account\"     ┌─────────────────┐  │\n *        │   │ FORGOT_PASSWORD │◄───────────────│      LOGIN      │───────────────►│     REGISTER    │  │\n *        │   │                 │───────────────►│                 │◄───────────────│                 │  │\n *        │   └─────────────────┘ Complete /     └─────────────────┘ \"Sign in here\" └─────────────────┘  │\n *        │            ▲        \"Sign in instead\"        │                                   │           │\n *        │            │                                 └──────────────────────┐  ┌─────────┘           │\n *        │            │\"Forgotten your                                         │  │  ┌──────────────────┘\n *        │            │ password?\"                                             │  │  │\n *        │            │                                                        │  │  │\n *        │   ┌─────────────────┐ Soft-logout error                             │  │  │\n *        │   │  SOFT_LOGOUT    │◄───────────── (from all other states          │  │  │\n *        │   │                 │                except LOCK_STOLEN)            │  │  │\n *        │   └─────────────────┘                                               │  │  │\n *        │         │ Re-authentication succeeded                               ▼  ▼  ▼\n *        │         │                                                    ┌──────────────────┐\n *        ▼         ▼                                                    │ (postLoginSetup) │\n *     ┌─────────────────┐                                               └──────────────────┘\n *     │ PENDING_CLIENT_ │                                      Account has │     │      │ Account lacks\n *     │     START       │                                    cross-signing │     │      │ cross-signing\n *     └─────────────────┘                                           keys   │     │      │ keys\n *        │          │                                                      │     │      │\n *        │          └───────────────────────────────┐                      │     │      │\n *        │            Client started,               │                      │     │      └──────┐\n *        │            force_verification pending    │                      │     │             │\n *        │                                          ▼                      │     │             │\n *        │ Client started,                 ┌─────────────────┐             │     │             │\n *        │ force_verification              │  COMPLETE_      │◄────────────┘     │             ▼\n *        │ not needed                      │      SECURITY   │                   │      ┌─────────────────┐\n *        │                                 └─────────────────┘                   │      │   E2E_SETUP     │\n *        │                                          │                            │      │                 │\n *        │    ┌─────────────────────────────────────┘           E2EE not enabled │      └─────────────────┘\n *        │    │    ┌─────────────────────────────────────────────────────────────┘              │\n *        │    │    │     ┌──────────────────────────────────────────────────────────────────────┘\n *        │    │    │     │\n *        │    │    │     │\n *        │    │    │     │\n *        │    │    │     │\n *        ▼    ▼    ▼     ▼\n *       ┌─────────────────┐\n *       │   LOGGED_IN     │\n *       │                 │\n *       └─────────────────┘\n *\n *       (from all other states)\n *                │\n *                │ Session lock stolen\n *                ▼\n *       ┌─────────────────┐\n *       │  LOCK_STOLEN    │\n *       │                 │\n *       └─────────────────┘\n */\nenum Views {\n    // a special initial state which is only used at startup, while we are\n    // trying to re-animate a matrix client or register as a guest.\n    LOADING,\n\n    // Another tab holds the lock.\n    CONFIRM_LOCK_THEFT,\n\n    // we are showing the welcome view\n    WELCOME,\n\n    // we are showing the login view\n    LOGIN,\n\n    // we are showing the registration view\n    REGISTER,\n\n    // showing the 'forgot password' view\n    FORGOT_PASSWORD,\n\n    // showing flow to trust this new device with cross-signing\n    COMPLETE_SECURITY,\n\n    // flow to setup SSSS / cross-signing on this account\n    E2E_SETUP,\n\n    /**\n     * We have successfully recovered a session from localstorage, but the client\n     * has not yet been started.\n     */\n    PENDING_CLIENT_START,\n\n    // we are logged in with an active matrix client. The logged_in state also\n    // includes guests users as they too are logged in at the client level.\n    LOGGED_IN,\n\n    // We are logged out (invalid token) but have our local state again. The user\n    // should log back in to rehydrate the client.\n    SOFT_LOGOUT,\n\n    // Another instance of the application has started up. We just show an error page.\n    LOCK_STOLEN,\n}\n\nexport default Views;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type WorkerPayload } from \"./workers/worker\";\n\nexport class WorkerManager<Request extends object, Response> {\n    private readonly worker: Worker;\n    private seq = 0;\n    private pendingDeferredMap = new Map<number, PromiseWithResolvers<Response>>();\n\n    public constructor(worker: Worker) {\n        this.worker = worker;\n        this.worker.onmessage = this.onMessage;\n    }\n\n    private onMessage = (ev: MessageEvent<Response & WorkerPayload>): void => {\n        const deferred = this.pendingDeferredMap.get(ev.data.seq);\n        if (deferred) {\n            this.pendingDeferredMap.delete(ev.data.seq);\n            deferred.resolve(ev.data);\n        }\n    };\n\n    public call(request: Request): Promise<Response> {\n        const seq = this.seq++;\n        const deferred = Promise.withResolvers<Response>();\n        this.pendingDeferredMap.set(seq, deferred);\n        this.worker.postMessage({ seq, ...request });\n        return deferred.promise;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 Šimon Brandner <simon.bra.ag@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type KeyCombo } from \"../KeyBindingsManager\";\nimport { IS_MAC, Key } from \"../Keyboard\";\nimport { _t, _td } from \"../languageHandler\";\nimport PlatformPeg from \"../PlatformPeg\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport {\n    DESKTOP_SHORTCUTS,\n    DIGITS,\n    type IKeyboardShortcuts,\n    KeyBindingAction,\n    KEYBOARD_SHORTCUTS,\n    type KeyboardShortcutSetting,\n    MAC_ONLY_SHORTCUTS,\n} from \"./KeyboardShortcuts\";\n\n/**\n * This function gets the keyboard shortcuts that should be presented in the UI\n * but they shouldn't be consumed by KeyBindingDefaults. That means that these\n * have to be manually mirrored in KeyBindingDefaults.\n */\nconst getUIOnlyShortcuts = (): IKeyboardShortcuts => {\n    const ctrlEnterToSend = SettingsStore.getValue(\"MessageComposerInput.ctrlEnterToSend\");\n\n    const keyboardShortcuts: IKeyboardShortcuts = {\n        [KeyBindingAction.SendMessage]: {\n            default: {\n                key: Key.ENTER,\n                ctrlOrCmdKey: ctrlEnterToSend,\n            },\n            displayName: _td(\"composer|send_button_title\"),\n        },\n        [KeyBindingAction.NewLine]: {\n            default: {\n                key: Key.ENTER,\n                shiftKey: !ctrlEnterToSend,\n            },\n            displayName: _td(\"keyboard|composer_new_line\"),\n        },\n        [KeyBindingAction.CompleteAutocomplete]: {\n            default: {\n                key: Key.ENTER,\n            },\n            displayName: _td(\"action|complete\"),\n        },\n        [KeyBindingAction.ForceCompleteAutocomplete]: {\n            default: {\n                key: Key.TAB,\n            },\n            displayName: _td(\"keyboard|autocomplete_force\"),\n        },\n        [KeyBindingAction.SearchInRoom]: {\n            default: {\n                ctrlOrCmdKey: true,\n                key: Key.F,\n            },\n            displayName: _td(\"keyboard|search\"),\n        },\n    };\n\n    if (PlatformPeg.get()?.overrideBrowserShortcuts()) {\n        // XXX: This keyboard shortcut isn't manually added to\n        // KeyBindingDefaults as it can't be easily handled by the\n        // KeyBindingManager\n        keyboardShortcuts[KeyBindingAction.SwitchToSpaceByNumber] = {\n            default: {\n                ctrlOrCmdKey: true,\n                key: DIGITS,\n            },\n            displayName: _td(\"keyboard|switch_to_space\"),\n        };\n    }\n\n    return keyboardShortcuts;\n};\n\n/**\n * This function gets keyboard shortcuts that can be consumed by the KeyBindingDefaults.\n */\nexport const getKeyboardShortcuts = (): IKeyboardShortcuts => {\n    const overrideBrowserShortcuts = PlatformPeg.get()?.overrideBrowserShortcuts();\n\n    return (Object.keys(KEYBOARD_SHORTCUTS) as KeyBindingAction[])\n        .filter((k) => {\n            if (KEYBOARD_SHORTCUTS[k]?.controller?.settingDisabled) return false;\n            if (MAC_ONLY_SHORTCUTS.includes(k) && !IS_MAC) return false;\n            if (DESKTOP_SHORTCUTS.includes(k) && !overrideBrowserShortcuts) return false;\n\n            return true;\n        })\n        .reduce((o, key) => {\n            o[key as KeyBindingAction] = KEYBOARD_SHORTCUTS[key as KeyBindingAction];\n            return o;\n        }, {} as IKeyboardShortcuts);\n};\n\n/**\n * Gets keyboard shortcuts that should be presented to the user in the UI.\n */\nexport const getKeyboardShortcutsForUI = (): IKeyboardShortcuts => {\n    const entries = [...Object.entries(getUIOnlyShortcuts()), ...Object.entries(getKeyboardShortcuts())] as [\n        KeyBindingAction,\n        KeyboardShortcutSetting,\n    ][];\n\n    return entries.reduce((acc, [key, value]) => {\n        acc[key] = value;\n        return acc;\n    }, {} as IKeyboardShortcuts);\n};\n\nexport const getKeyboardShortcutValue = (name: KeyBindingAction): KeyCombo | undefined => {\n    return getKeyboardShortcutsForUI()[name]?.default;\n};\n\nexport const getKeyboardShortcutDisplayName = (name: KeyBindingAction): string | undefined => {\n    const keyboardShortcutDisplayName = getKeyboardShortcutsForUI()[name]?.displayName;\n    return keyboardShortcutDisplayName && _t(keyboardShortcutDisplayName);\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\nCopyright 2021, 2022 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// Import i18n.tsx instead of languageHandler to avoid circular deps\nimport { _td } from \"@element-hq/web-shared-components\";\n\nimport { IS_MAC, IS_ELECTRON, Key } from \"../Keyboard\";\nimport { type IBaseSetting } from \"../settings/Settings\";\nimport { type KeyCombo } from \"../KeyBindingsManager\";\n\nexport enum KeyBindingAction {\n    /** Send a message */\n    SendMessage = \"KeyBinding.sendMessageInComposer\",\n    /** Go backwards through the send history and use the message in composer view */\n    SelectPrevSendHistory = \"KeyBinding.previousMessageInComposerHistory\",\n    /** Go forwards through the send history */\n    SelectNextSendHistory = \"KeyBinding.nextMessageInComposerHistory\",\n    /** Start editing the user's last sent message */\n    EditPrevMessage = \"KeyBinding.editPreviousMessage\",\n    /** Start editing the user's next sent message */\n    EditNextMessage = \"KeyBinding.editNextMessage\",\n    /** Cancel editing a message or cancel replying to a message */\n    CancelReplyOrEdit = \"KeyBinding.cancelReplyInComposer\",\n    /** Show the sticker picker */\n    ShowStickerPicker = \"KeyBinding.showStickerPicker\",\n\n    /** Set bold format the current selection */\n    FormatBold = \"KeyBinding.toggleBoldInComposer\",\n    /** Set italics format the current selection */\n    FormatItalics = \"KeyBinding.toggleItalicsInComposer\",\n    /** Insert link for current selection */\n    FormatLink = \"KeyBinding.FormatLink\",\n    /** Set code format for current selection */\n    FormatCode = \"KeyBinding.FormatCode\",\n    /** Format the current selection as quote */\n    FormatQuote = \"KeyBinding.toggleQuoteInComposer\",\n    /** Undo the last editing */\n    EditUndo = \"KeyBinding.editUndoInComposer\",\n    /** Redo editing */\n    EditRedo = \"KeyBinding.editRedoInComposer\",\n    /** Insert new line */\n    NewLine = \"KeyBinding.newLineInComposer\",\n    /** Move the cursor to the start of the message */\n    MoveCursorToStart = \"KeyBinding.jumpToStartInComposer\",\n    /** Move the cursor to the end of the message */\n    MoveCursorToEnd = \"KeyBinding.jumpToEndInComposer\",\n\n    /** Accepts chosen autocomplete selection */\n    CompleteAutocomplete = \"KeyBinding.completeAutocomplete\",\n    /** Accepts chosen autocomplete selection or,\n     * if the autocompletion window is not shown, open the window and select the first selection */\n    ForceCompleteAutocomplete = \"KeyBinding.forceCompleteAutocomplete\",\n    /** Move to the previous autocomplete selection */\n    PrevSelectionInAutocomplete = \"KeyBinding.previousOptionInAutoComplete\",\n    /** Move to the next autocomplete selection */\n    NextSelectionInAutocomplete = \"KeyBinding.nextOptionInAutoComplete\",\n    /** Close the autocompletion window */\n    CancelAutocomplete = \"KeyBinding.cancelAutoComplete\",\n\n    /** Clear room list filter field */\n    ClearRoomFilter = \"KeyBinding.clearRoomFilter\",\n    /** Navigate up/down in the room list */\n    PrevRoom = \"KeyBinding.downerRoom\",\n    /** Navigate down in the room list */\n    NextRoom = \"KeyBinding.upperRoom\",\n    /** Select room from the room list */\n    SelectRoomInRoomList = \"KeyBinding.selectRoomInRoomList\",\n    /** Collapse room list section */\n    CollapseRoomListSection = \"KeyBinding.collapseSectionInRoomList\",\n    /** Expand room list section, if already expanded, jump to first room in the selection */\n    ExpandRoomListSection = \"KeyBinding.expandSectionInRoomList\",\n\n    /** Scroll up in the timeline */\n    ScrollUp = \"KeyBinding.scrollUpInTimeline\",\n    /** Scroll down in the timeline */\n    ScrollDown = \"KeyBinding.scrollDownInTimeline\",\n    /** Dismiss read marker and jump to bottom */\n    DismissReadMarker = \"KeyBinding.dismissReadMarkerAndJumpToBottom\",\n    /** Jump to oldest unread message */\n    JumpToOldestUnread = \"KeyBinding.jumpToOldestUnreadMessage\",\n    /** Upload a file */\n    UploadFile = \"KeyBinding.uploadFileToRoom\",\n    /** Focus search message in a room (must be enabled) */\n    SearchInRoom = \"KeyBinding.searchInRoom\",\n    /** Jump to the first (downloaded) message in the room */\n    JumpToFirstMessage = \"KeyBinding.jumpToFirstMessageInTimeline\",\n    /** Jump to the latest message in the room */\n    JumpToLatestMessage = \"KeyBinding.jumpToLastMessageInTimeline\",\n\n    /** Jump to room search (search for a room) */\n    FilterRooms = \"KeyBinding.filterRooms\",\n    /** Toggle the space panel */\n    ToggleSpacePanel = \"KeyBinding.toggleSpacePanel\",\n    /** Toggle the room side panel */\n    ToggleRoomSidePanel = \"KeyBinding.toggleRightPanel\",\n    /** Toggle the user menu */\n    ToggleUserMenu = \"KeyBinding.toggleTopLeftMenu\",\n    /** Toggle the short cut help dialog */\n    ShowKeyboardSettings = \"KeyBinding.showKeyBindingsSettings\",\n    /** Got to the Element home screen */\n    GoToHome = \"KeyBinding.goToHomeView\",\n    /** Select prev room */\n    SelectPrevRoom = \"KeyBinding.previousRoom\",\n    /** Select next room */\n    SelectNextRoom = \"KeyBinding.nextRoom\",\n    /** Select prev room with unread messages */\n    SelectPrevUnreadRoom = \"KeyBinding.previousUnreadRoom\",\n    /** Select next room with unread messages */\n    SelectNextUnreadRoom = \"KeyBinding.nextUnreadRoom\",\n\n    /** Switches to a space by number */\n    SwitchToSpaceByNumber = \"KeyBinding.switchToSpaceByNumber\",\n    /** Opens user settings */\n    OpenUserSettings = \"KeyBinding.openUserSettings\",\n    /** Navigates backward */\n    PreviousVisitedRoomOrSpace = \"KeyBinding.PreviousVisitedRoomOrSpace\",\n    /** Navigates forward */\n    NextVisitedRoomOrSpace = \"KeyBinding.NextVisitedRoomOrSpace\",\n    /** Navigates to the next Landmark */\n    NextLandmark = \"KeyBinding.nextLandmark\",\n    /** Navigates to the next Landmark */\n    PreviousLandmark = \"KeyBinding.previousLandmark\",\n\n    /** Toggles microphone while on a call */\n    ToggleMicInCall = \"KeyBinding.toggleMicInCall\",\n    /** Toggles webcam while on a call */\n    ToggleWebcamInCall = \"KeyBinding.toggleWebcamInCall\",\n\n    /** Accessibility actions */\n    Escape = \"KeyBinding.escape\",\n    Enter = \"KeyBinding.enter\",\n    Space = \"KeyBinding.space\",\n    Backspace = \"KeyBinding.backspace\",\n    Delete = \"KeyBinding.delete\",\n    Home = \"KeyBinding.home\",\n    End = \"KeyBinding.end\",\n    ArrowLeft = \"KeyBinding.arrowLeft\",\n    ArrowUp = \"KeyBinding.arrowUp\",\n    ArrowRight = \"KeyBinding.arrowRight\",\n    ArrowDown = \"KeyBinding.arrowDown\",\n    Tab = \"KeyBinding.tab\",\n    Comma = \"KeyBinding.comma\",\n    Save = \"KeyBinding.save\",\n\n    /** Toggle visibility of hidden events */\n    ToggleHiddenEventVisibility = \"KeyBinding.toggleHiddenEventVisibility\",\n}\n\nexport type KeyboardShortcutSetting = Omit<IBaseSetting<KeyCombo>, \"supportedLevels\" | \"displayName\"> & {\n    displayName?: TranslationKey;\n};\n\n// TODO: We should figure out what to do with the keyboard shortcuts that are not handled by KeybindingManager\nexport type IKeyboardShortcuts = Partial<Record<KeyBindingAction, KeyboardShortcutSetting>>;\n\nexport interface ICategory {\n    categoryLabel?: TranslationKey;\n    // TODO: We should figure out what to do with the keyboard shortcuts that are not handled by KeybindingManager\n    settingNames: KeyBindingAction[];\n}\n\nexport enum CategoryName {\n    NAVIGATION = \"Navigation\",\n    ACCESSIBILITY = \"Accessibility\",\n    CALLS = \"Calls\",\n    COMPOSER = \"Composer\",\n    ROOM_LIST = \"Room List\",\n    ROOM = \"Room\",\n    AUTOCOMPLETE = \"Autocomplete\",\n    LABS = \"Labs\",\n}\n\n// Meta-key representing the digits [0-9] often found at the top of standard keyboard layouts\nexport const DIGITS = \"digits\";\n\nexport const ALTERNATE_KEY_NAME: Record<string, TranslationKey> = {\n    [Key.PAGE_UP]: _td(\"keyboard|page_up\"),\n    [Key.PAGE_DOWN]: _td(\"keyboard|page_down\"),\n    [Key.ESCAPE]: _td(\"keyboard|escape\"),\n    [Key.ENTER]: _td(\"keyboard|enter\"),\n    [Key.SPACE]: _td(\"keyboard|space\"),\n    [Key.HOME]: _td(\"keyboard|home\"),\n    [Key.END]: _td(\"keyboard|end\"),\n    [Key.ALT]: _td(\"keyboard|alt\"),\n    [Key.CONTROL]: _td(\"keyboard|control\"),\n    [Key.SHIFT]: _td(\"keyboard|shift\"),\n    [DIGITS]: _td(\"keyboard|number\"),\n};\nexport const KEY_ICON: Record<string, string> = {\n    [Key.ARROW_UP]: \"↑\",\n    [Key.ARROW_DOWN]: \"↓\",\n    [Key.ARROW_LEFT]: \"←\",\n    [Key.ARROW_RIGHT]: \"→\",\n};\nif (IS_MAC) {\n    KEY_ICON[Key.META] = \"⌘\";\n    KEY_ICON[Key.ALT] = \"⌥\";\n    KEY_ICON[Key.SHIFT] = \"⇧\";\n}\n\nexport const CATEGORIES: Record<CategoryName, ICategory> = {\n    [CategoryName.COMPOSER]: {\n        categoryLabel: _td(\"settings|preferences|composer_heading\"),\n        settingNames: [\n            KeyBindingAction.SendMessage,\n            KeyBindingAction.NewLine,\n            KeyBindingAction.FormatBold,\n            KeyBindingAction.FormatItalics,\n            KeyBindingAction.FormatQuote,\n            KeyBindingAction.FormatLink,\n            KeyBindingAction.FormatCode,\n            KeyBindingAction.EditUndo,\n            KeyBindingAction.EditRedo,\n            KeyBindingAction.MoveCursorToStart,\n            KeyBindingAction.MoveCursorToEnd,\n            KeyBindingAction.CancelReplyOrEdit,\n            KeyBindingAction.EditNextMessage,\n            KeyBindingAction.EditPrevMessage,\n            KeyBindingAction.SelectNextSendHistory,\n            KeyBindingAction.SelectPrevSendHistory,\n            KeyBindingAction.ShowStickerPicker,\n        ],\n    },\n    [CategoryName.CALLS]: {\n        categoryLabel: _td(\"keyboard|category_calls\"),\n        settingNames: [KeyBindingAction.ToggleMicInCall, KeyBindingAction.ToggleWebcamInCall],\n    },\n    [CategoryName.ROOM]: {\n        categoryLabel: _td(\"common|room\"),\n        settingNames: [\n            KeyBindingAction.SearchInRoom,\n            KeyBindingAction.UploadFile,\n            KeyBindingAction.DismissReadMarker,\n            KeyBindingAction.JumpToOldestUnread,\n            KeyBindingAction.ScrollUp,\n            KeyBindingAction.ScrollDown,\n            KeyBindingAction.JumpToFirstMessage,\n            KeyBindingAction.JumpToLatestMessage,\n        ],\n    },\n    [CategoryName.ROOM_LIST]: {\n        categoryLabel: _td(\"keyboard|category_room_list\"),\n        settingNames: [\n            KeyBindingAction.SelectRoomInRoomList,\n            KeyBindingAction.ClearRoomFilter,\n            KeyBindingAction.CollapseRoomListSection,\n            KeyBindingAction.ExpandRoomListSection,\n            KeyBindingAction.NextRoom,\n            KeyBindingAction.PrevRoom,\n        ],\n    },\n    [CategoryName.ACCESSIBILITY]: {\n        categoryLabel: _td(\"common|accessibility\"),\n        settingNames: [\n            KeyBindingAction.Escape,\n            KeyBindingAction.Enter,\n            KeyBindingAction.Space,\n            KeyBindingAction.Backspace,\n            KeyBindingAction.Delete,\n            KeyBindingAction.Home,\n            KeyBindingAction.End,\n            KeyBindingAction.ArrowLeft,\n            KeyBindingAction.ArrowUp,\n            KeyBindingAction.ArrowRight,\n            KeyBindingAction.ArrowDown,\n            KeyBindingAction.Comma,\n            KeyBindingAction.Save,\n        ],\n    },\n    [CategoryName.NAVIGATION]: {\n        categoryLabel: _td(\"keyboard|category_navigation\"),\n        settingNames: [\n            KeyBindingAction.ToggleUserMenu,\n            KeyBindingAction.ToggleRoomSidePanel,\n            KeyBindingAction.ToggleSpacePanel,\n            KeyBindingAction.ShowKeyboardSettings,\n            KeyBindingAction.GoToHome,\n            KeyBindingAction.FilterRooms,\n            KeyBindingAction.SelectNextUnreadRoom,\n            KeyBindingAction.SelectPrevUnreadRoom,\n            KeyBindingAction.SelectNextRoom,\n            KeyBindingAction.SelectPrevRoom,\n            KeyBindingAction.OpenUserSettings,\n            KeyBindingAction.SwitchToSpaceByNumber,\n            KeyBindingAction.PreviousVisitedRoomOrSpace,\n            KeyBindingAction.NextVisitedRoomOrSpace,\n            KeyBindingAction.NextLandmark,\n            KeyBindingAction.PreviousLandmark,\n        ],\n    },\n    [CategoryName.AUTOCOMPLETE]: {\n        categoryLabel: _td(\"keyboard|category_autocomplete\"),\n        settingNames: [\n            KeyBindingAction.CancelAutocomplete,\n            KeyBindingAction.NextSelectionInAutocomplete,\n            KeyBindingAction.PrevSelectionInAutocomplete,\n            KeyBindingAction.CompleteAutocomplete,\n            KeyBindingAction.ForceCompleteAutocomplete,\n        ],\n    },\n    [CategoryName.LABS]: {\n        categoryLabel: _td(\"common|labs\"),\n        settingNames: [KeyBindingAction.ToggleHiddenEventVisibility],\n    },\n};\n\nexport const DESKTOP_SHORTCUTS = [\n    KeyBindingAction.OpenUserSettings,\n    KeyBindingAction.SwitchToSpaceByNumber,\n    KeyBindingAction.PreviousVisitedRoomOrSpace,\n    KeyBindingAction.NextVisitedRoomOrSpace,\n];\n\nexport const MAC_ONLY_SHORTCUTS = [KeyBindingAction.OpenUserSettings];\n\n// This is very intentionally modelled after SETTINGS as it will make it easier\n// to implement customizable keyboard shortcuts\n// TODO: TravisR will fix this nightmare when the new version of the SettingsStore becomes a thing\n// XXX: Exported for tests\nexport const KEYBOARD_SHORTCUTS: IKeyboardShortcuts = {\n    [KeyBindingAction.FormatBold]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.B,\n        },\n        displayName: _td(\"keyboard|composer_toggle_bold\"),\n    },\n    [KeyBindingAction.FormatItalics]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.I,\n        },\n        displayName: _td(\"keyboard|composer_toggle_italics\"),\n    },\n    [KeyBindingAction.FormatQuote]: {\n        default: {\n            ctrlOrCmdKey: true,\n            shiftKey: true,\n            key: Key.GREATER_THAN,\n        },\n        displayName: _td(\"keyboard|composer_toggle_quote\"),\n    },\n    [KeyBindingAction.FormatCode]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.E,\n        },\n        displayName: _td(\"keyboard|composer_toggle_code_block\"),\n    },\n    [KeyBindingAction.FormatLink]: {\n        default: {\n            ctrlOrCmdKey: true,\n            shiftKey: true,\n            key: Key.L,\n        },\n        displayName: _td(\"keyboard|composer_toggle_link\"),\n    },\n    [KeyBindingAction.CancelReplyOrEdit]: {\n        default: {\n            key: Key.ESCAPE,\n        },\n        displayName: _td(\"keyboard|cancel_reply\"),\n    },\n    [KeyBindingAction.EditNextMessage]: {\n        default: {\n            key: Key.ARROW_DOWN,\n        },\n        displayName: _td(\"keyboard|navigate_next_message_edit\"),\n    },\n    [KeyBindingAction.EditPrevMessage]: {\n        default: {\n            key: Key.ARROW_UP,\n        },\n        displayName: _td(\"keyboard|navigate_prev_message_edit\"),\n    },\n    [KeyBindingAction.MoveCursorToStart]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.HOME,\n        },\n        displayName: _td(\"keyboard|composer_jump_start\"),\n    },\n    [KeyBindingAction.MoveCursorToEnd]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.END,\n        },\n        displayName: _td(\"keyboard|composer_jump_end\"),\n    },\n    [KeyBindingAction.SelectNextSendHistory]: {\n        default: {\n            altKey: true,\n            ctrlKey: true,\n            key: Key.ARROW_DOWN,\n        },\n        displayName: _td(\"keyboard|composer_navigate_next_history\"),\n    },\n    [KeyBindingAction.SelectPrevSendHistory]: {\n        default: {\n            altKey: true,\n            ctrlKey: true,\n            key: Key.ARROW_UP,\n        },\n        displayName: _td(\"keyboard|composer_navigate_prev_history\"),\n    },\n    [KeyBindingAction.ShowStickerPicker]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.SEMICOLON,\n        },\n        displayName: _td(\"keyboard|send_sticker\"),\n    },\n    [KeyBindingAction.ToggleMicInCall]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.D,\n        },\n        displayName: _td(\"keyboard|toggle_microphone_mute\"),\n    },\n    [KeyBindingAction.ToggleWebcamInCall]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.E,\n        },\n        displayName: _td(\"keyboard|toggle_webcam_mute\"),\n    },\n    [KeyBindingAction.DismissReadMarker]: {\n        default: {\n            key: Key.ESCAPE,\n        },\n        displayName: _td(\"keyboard|dismiss_read_marker_and_jump_bottom\"),\n    },\n    [KeyBindingAction.JumpToOldestUnread]: {\n        default: {\n            shiftKey: true,\n            key: Key.PAGE_UP,\n        },\n        displayName: _td(\"keyboard|jump_to_read_marker\"),\n    },\n    [KeyBindingAction.UploadFile]: {\n        default: {\n            ctrlOrCmdKey: true,\n            shiftKey: true,\n            key: Key.U,\n        },\n        displayName: _td(\"keyboard|upload_file\"),\n    },\n    [KeyBindingAction.ScrollUp]: {\n        default: {\n            key: Key.PAGE_UP,\n        },\n        displayName: _td(\"keyboard|scroll_up_timeline\"),\n    },\n    [KeyBindingAction.ScrollDown]: {\n        default: {\n            key: Key.PAGE_DOWN,\n        },\n        displayName: _td(\"keyboard|scroll_down_timeline\"),\n    },\n    [KeyBindingAction.FilterRooms]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.K,\n        },\n        displayName: _td(\"keyboard|jump_room_search\"),\n    },\n    [KeyBindingAction.SelectRoomInRoomList]: {\n        default: {\n            key: Key.ENTER,\n        },\n        displayName: _td(\"keyboard|room_list_select_room\"),\n    },\n    [KeyBindingAction.CollapseRoomListSection]: {\n        default: {\n            key: Key.ARROW_LEFT,\n        },\n        displayName: _td(\"keyboard|room_list_collapse_section\"),\n    },\n    [KeyBindingAction.ExpandRoomListSection]: {\n        default: {\n            key: Key.ARROW_RIGHT,\n        },\n        displayName: _td(\"keyboard|room_list_expand_section\"),\n    },\n    [KeyBindingAction.NextRoom]: {\n        default: {\n            key: Key.ARROW_DOWN,\n        },\n        displayName: _td(\"keyboard|room_list_navigate_down\"),\n    },\n    [KeyBindingAction.PrevRoom]: {\n        default: {\n            key: Key.ARROW_UP,\n        },\n        displayName: _td(\"keyboard|room_list_navigate_up\"),\n    },\n    [KeyBindingAction.ToggleUserMenu]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.BACKTICK,\n        },\n        displayName: _td(\"keyboard|toggle_top_left_menu\"),\n    },\n    [KeyBindingAction.ToggleRoomSidePanel]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.PERIOD,\n        },\n        displayName: _td(\"keyboard|toggle_right_panel\"),\n    },\n    [KeyBindingAction.ShowKeyboardSettings]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: Key.SLASH,\n        },\n        displayName: _td(\"keyboard|keyboard_shortcuts_tab\"),\n    },\n    [KeyBindingAction.GoToHome]: {\n        default: {\n            ctrlKey: true,\n            altKey: !IS_MAC,\n            shiftKey: IS_MAC,\n            key: Key.H,\n        },\n        displayName: _td(\"keyboard|go_home_view\"),\n    },\n    [KeyBindingAction.SelectNextUnreadRoom]: {\n        default: {\n            shiftKey: true,\n            altKey: true,\n            key: Key.ARROW_DOWN,\n        },\n        displayName: _td(\"keyboard|next_unread_room\"),\n    },\n    [KeyBindingAction.SelectPrevUnreadRoom]: {\n        default: {\n            shiftKey: true,\n            altKey: true,\n            key: Key.ARROW_UP,\n        },\n        displayName: _td(\"keyboard|prev_unread_room\"),\n    },\n    [KeyBindingAction.SelectNextRoom]: {\n        default: {\n            altKey: true,\n            key: Key.ARROW_DOWN,\n        },\n        displayName: _td(\"keyboard|next_room\"),\n    },\n    [KeyBindingAction.SelectPrevRoom]: {\n        default: {\n            altKey: true,\n            key: Key.ARROW_UP,\n        },\n        displayName: _td(\"keyboard|prev_room\"),\n    },\n    [KeyBindingAction.CancelAutocomplete]: {\n        default: {\n            key: Key.ESCAPE,\n        },\n        displayName: _td(\"keyboard|autocomplete_cancel\"),\n    },\n    [KeyBindingAction.NextSelectionInAutocomplete]: {\n        default: {\n            key: Key.ARROW_DOWN,\n        },\n        displayName: _td(\"keyboard|autocomplete_navigate_next\"),\n    },\n    [KeyBindingAction.PrevSelectionInAutocomplete]: {\n        default: {\n            key: Key.ARROW_UP,\n        },\n        displayName: _td(\"keyboard|autocomplete_navigate_prev\"),\n    },\n    [KeyBindingAction.ToggleSpacePanel]: {\n        default: {\n            ctrlOrCmdKey: true,\n            shiftKey: true,\n            key: Key.D,\n        },\n        displayName: _td(\"keyboard|toggle_space_panel\"),\n    },\n    [KeyBindingAction.ToggleHiddenEventVisibility]: {\n        default: {\n            ctrlKey: true,\n            shiftKey: true,\n            key: Key.J,\n        },\n        displayName: _td(\"keyboard|toggle_hidden_events\"),\n    },\n    [KeyBindingAction.JumpToFirstMessage]: {\n        default: {\n            key: Key.HOME,\n            ctrlKey: true,\n        },\n        displayName: _td(\"keyboard|jump_first_message\"),\n    },\n    [KeyBindingAction.JumpToLatestMessage]: {\n        default: {\n            key: Key.END,\n            ctrlKey: true,\n        },\n        displayName: _td(\"keyboard|jump_last_message\"),\n    },\n    [KeyBindingAction.EditUndo]: {\n        default: {\n            key: Key.Z,\n            ctrlOrCmdKey: true,\n        },\n        displayName: _td(\"keyboard|composer_undo\"),\n    },\n    [KeyBindingAction.EditRedo]: {\n        default: {\n            key: IS_MAC ? Key.Z : Key.Y,\n            ctrlOrCmdKey: true,\n            shiftKey: IS_MAC,\n        },\n        displayName: _td(\"keyboard|composer_redo\"),\n    },\n    [KeyBindingAction.Save]: {\n        default: {\n            key: Key.S,\n            ctrlOrCmdKey: true,\n        },\n        displayName: _td(\"keyboard|save\"),\n    },\n    [KeyBindingAction.PreviousVisitedRoomOrSpace]: {\n        default: {\n            metaKey: IS_MAC,\n            altKey: !IS_MAC,\n            key: IS_MAC ? Key.SQUARE_BRACKET_LEFT : Key.ARROW_LEFT,\n        },\n        displayName: _td(\"keyboard|navigate_prev_history\"),\n    },\n    [KeyBindingAction.NextVisitedRoomOrSpace]: {\n        default: {\n            metaKey: IS_MAC,\n            altKey: !IS_MAC,\n            key: IS_MAC ? Key.SQUARE_BRACKET_RIGHT : Key.ARROW_RIGHT,\n        },\n        displayName: _td(\"keyboard|navigate_next_history\"),\n    },\n    [KeyBindingAction.SwitchToSpaceByNumber]: {\n        default: {\n            ctrlOrCmdKey: true,\n            key: DIGITS,\n        },\n        displayName: _td(\"keyboard|switch_to_space\"),\n    },\n    [KeyBindingAction.OpenUserSettings]: {\n        default: {\n            metaKey: true,\n            key: Key.COMMA,\n        },\n        displayName: _td(\"keyboard|open_user_settings\"),\n    },\n    [KeyBindingAction.Escape]: {\n        default: {\n            key: Key.ESCAPE,\n        },\n        displayName: _td(\"keyboard|close_dialog_menu\"),\n    },\n    [KeyBindingAction.Enter]: {\n        default: {\n            key: Key.ENTER,\n        },\n        displayName: _td(\"keyboard|activate_button\"),\n    },\n    [KeyBindingAction.Space]: {\n        default: {\n            key: Key.SPACE,\n        },\n    },\n    [KeyBindingAction.Backspace]: {\n        default: {\n            key: Key.BACKSPACE,\n        },\n    },\n    [KeyBindingAction.Delete]: {\n        default: {\n            key: Key.DELETE,\n        },\n    },\n    [KeyBindingAction.Home]: {\n        default: {\n            key: Key.HOME,\n        },\n    },\n    [KeyBindingAction.End]: {\n        default: {\n            key: Key.END,\n        },\n    },\n    [KeyBindingAction.ArrowLeft]: {\n        default: {\n            key: Key.ARROW_LEFT,\n        },\n    },\n    [KeyBindingAction.ArrowUp]: {\n        default: {\n            key: Key.ARROW_UP,\n        },\n    },\n    [KeyBindingAction.ArrowRight]: {\n        default: {\n            key: Key.ARROW_RIGHT,\n        },\n    },\n    [KeyBindingAction.ArrowDown]: {\n        default: {\n            key: Key.ARROW_DOWN,\n        },\n    },\n    [KeyBindingAction.Comma]: {\n        default: {\n            key: Key.COMMA,\n        },\n    },\n    [KeyBindingAction.NextLandmark]: {\n        default: {\n            ctrlOrCmdKey: !IS_ELECTRON,\n            key: Key.F6,\n        },\n        displayName: _td(\"keyboard|next_landmark\"),\n    },\n    [KeyBindingAction.PreviousLandmark]: {\n        default: {\n            ctrlOrCmdKey: !IS_ELECTRON,\n            key: Key.F6,\n            shiftKey: true,\n        },\n        displayName: _td(\"keyboard|prev_landmark\"),\n    },\n};\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2024 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { TimelineRenderingType } from \"../contexts/RoomContext\";\nimport { Action } from \"../dispatcher/actions\";\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport SettingsStore from \"../settings/SettingsStore\";\n\nexport const enum Landmark {\n    // This is the space/home button in the left panel.\n    ACTIVE_SPACE_BUTTON,\n    // This is the room filter in the left panel.\n    ROOM_SEARCH,\n    // This is the currently opened room/first room in the room list in the left panel.\n    ROOM_LIST,\n    // This is the message composer within the room if available or it is the welcome screen shown when no room is selected\n    MESSAGE_COMPOSER_OR_HOME,\n}\n\nconst ORDERED_LANDMARKS = [\n    Landmark.ACTIVE_SPACE_BUTTON,\n    Landmark.ROOM_SEARCH,\n    Landmark.ROOM_LIST,\n    Landmark.MESSAGE_COMPOSER_OR_HOME,\n];\n\n/**\n * The landmarks are cycled through in the following order:\n * ACTIVE_SPACE_BUTTON <-> ROOM_SEARCH <-> ROOM_LIST <-> MESSAGE_COMPOSER/HOME <-> ACTIVE_SPACE_BUTTON\n */\nexport class LandmarkNavigation {\n    /**\n     * Get the next/previous landmark that must be focused from a given landmark\n     * @param currentLandmark The current landmark\n     * @param backwards If true, the landmark before currentLandmark in ORDERED_LANDMARKS is returned\n     * @returns The next landmark to focus\n     */\n    private static getLandmark(currentLandmark: Landmark, backwards = false): Landmark {\n        const currentIndex = ORDERED_LANDMARKS.findIndex((l) => l === currentLandmark);\n        const offset = backwards ? -1 : 1;\n        const newLandmark = ORDERED_LANDMARKS.at((currentIndex + offset) % ORDERED_LANDMARKS.length)!;\n        return newLandmark;\n    }\n\n    /**\n     * Focus the next landmark from a given landmark.\n     * This method will skip over any missing landmarks.\n     * @param currentLandmark The current landmark\n     * @param backwards If true, search the next landmark to the left in ORDERED_LANDMARKS\n     */\n    public static findAndFocusNextLandmark(currentLandmark: Landmark, backwards = false): void {\n        let landmark = currentLandmark;\n        let element: HTMLElement | null | undefined = null;\n        while (element === null) {\n            landmark = LandmarkNavigation.getLandmark(landmark, backwards);\n            element = landmarkToDomElementMap[landmark]();\n        }\n        element?.focus({ focusVisible: true });\n    }\n}\n\n/**\n * The functions return:\n * - The DOM element of the landmark if it exists\n * - undefined if the DOM element exists but focus is given through an action\n * - null if the landmark does not exist\n */\nconst landmarkToDomElementMap: Record<Landmark, () => HTMLElement | null | undefined> = {\n    [Landmark.ACTIVE_SPACE_BUTTON]: () => document.querySelector<HTMLElement>(\".mx_SpaceButton_active\"),\n\n    [Landmark.ROOM_SEARCH]: () =>\n        SettingsStore.getValue(\"feature_new_room_list\")\n            ? document.querySelector<HTMLElement>(\"#room-list-search-button\")\n            : document.querySelector<HTMLElement>(\".mx_RoomSearch\"),\n    [Landmark.ROOM_LIST]: () =>\n        SettingsStore.getValue(\"feature_new_room_list\")\n            ? document.querySelector<HTMLElement>(\".mx_RoomListItemView_selected\") ||\n              document.querySelector<HTMLElement>(\".mx_RoomListItemView\")\n            : document.querySelector<HTMLElement>(\".mx_RoomTile_selected\") ||\n              document.querySelector<HTMLElement>(\".mx_RoomTile\"),\n\n    [Landmark.MESSAGE_COMPOSER_OR_HOME]: () => {\n        const isComposerOpen = !!document.querySelector(\".mx_MessageComposer\");\n        if (isComposerOpen) {\n            const inThread = !!document.activeElement?.closest(\".mx_ThreadView\");\n            defaultDispatcher.dispatch(\n                {\n                    action: Action.FocusSendMessageComposer,\n                    context: inThread ? TimelineRenderingType.Thread : TimelineRenderingType.Room,\n                },\n                true,\n            );\n            // Special case where the element does exist but we focus it through an action.\n            return undefined;\n        } else {\n            return document.querySelector<HTMLElement>(\".mx_HomePage\");\n        }\n    },\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ReactElement, type RefCallback, type RefObject } from \"react\";\n\nimport type React from \"react\";\nimport { useRovingTabIndex } from \"../RovingTabIndex\";\nimport { type FocusHandler } from \"./types\";\n\ninterface IProps {\n    inputRef?: RefObject<HTMLElement | null>;\n    children(renderProps: {\n        onFocus: FocusHandler;\n        isActive: boolean;\n        ref: RefCallback<HTMLElement>;\n    }): ReactElement<any, any>;\n}\n\n// Wrapper to allow use of useRovingTabIndex outside of React Functional Components.\nexport const RovingTabIndexWrapper: React.FC<IProps> = ({ children, inputRef }) => {\n    const [onFocus, isActive, ref] = useRovingTabIndex(inputRef);\n    return children({ onFocus, isActive, ref });\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type RefObject } from \"react\";\n\nimport AccessibleButton, { type ButtonProps } from \"../../components/views/elements/AccessibleButton\";\nimport { useRovingTabIndex } from \"../RovingTabIndex\";\n\ntype Props<T extends keyof HTMLElementTagNameMap> = Omit<ButtonProps<T>, \"tabIndex\"> & {\n    inputRef?: RefObject<HTMLElementTagNameMap[T] | null>;\n    focusOnMouseOver?: boolean;\n};\n\n// Wrapper to allow use of useRovingTabIndex for simple AccessibleButtons outside of React Functional Components.\nexport const RovingAccessibleButton = <T extends keyof HTMLElementTagNameMap>({\n    inputRef,\n    onFocus,\n    onMouseOver,\n    focusOnMouseOver,\n    ...props\n}: Props<T>): JSX.Element => {\n    const [onFocusInternal, isActive, ref] = useRovingTabIndex<HTMLElementTagNameMap[T]>(inputRef);\n    return (\n        <AccessibleButton\n            {...props}\n            onFocus={(event: React.FocusEvent<never, never>) => {\n                onFocusInternal();\n                onFocus?.(event);\n            }}\n            onMouseOver={(event: React.MouseEvent<never, never>) => {\n                if (focusOnMouseOver) onFocusInternal();\n                onMouseOver?.(event);\n            }}\n            ref={ref}\n            tabIndex={isActive ? 0 : -1}\n        />\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, {\n    createContext,\n    useCallback,\n    useContext,\n    useMemo,\n    useRef,\n    useReducer,\n    type Reducer,\n    type Dispatch,\n    type RefObject,\n    type ReactNode,\n    type RefCallback,\n} from \"react\";\n\nimport { getKeyBindingsManager } from \"../KeyBindingsManager\";\nimport { KeyBindingAction } from \"./KeyboardShortcuts\";\nimport { type FocusHandler } from \"./roving/types\";\n\n/**\n * Module to simplify implementing the Roving TabIndex accessibility technique\n *\n * Wrap the Widget in an RovingTabIndexContextProvider\n * and then for all buttons make use of useRovingTabIndex or RovingTabIndexWrapper.\n * The code will keep track of which tabIndex was most recently focused and expose that information as `isActive` which\n * can then be used to only set the tabIndex to 0 as expected by the roving tabindex technique.\n * When the active button gets unmounted the closest button will be chosen as expected.\n * Initially the first button to mount will be given active state.\n *\n * https://developer.mozilla.org/en-US/docs/Web/Accessibility/Keyboard-navigable_JavaScript_widgets#Technique_1_Roving_tabindex\n */\n\n// Check for form elements which utilize the arrow keys for native functions\n// like many of the text input varieties.\n//\n// i.e. it's ok to press the down arrow on a radio button to move to the next\n// radio. But it's not ok to press the down arrow on a <input type=\"text\"> to\n// move away because the down arrow should move the cursor to the end of the\n// input.\nexport function checkInputableElement(el: HTMLElement): boolean {\n    return el.matches('input:not([type=\"radio\"]):not([type=\"checkbox\"]), textarea, select, [contenteditable=true]');\n}\n\nexport interface IState {\n    activeNode?: HTMLElement;\n    nodes: HTMLElement[];\n}\n\nexport interface IContext {\n    state: IState;\n    dispatch: Dispatch<IAction>;\n}\n\nexport const RovingTabIndexContext = createContext<IContext>({\n    state: {\n        nodes: [], // list of nodes in DOM order\n    },\n    dispatch: () => {},\n});\nRovingTabIndexContext.displayName = \"RovingTabIndexContext\";\n\nexport enum Type {\n    Register = \"REGISTER\",\n    Unregister = \"UNREGISTER\",\n    SetFocus = \"SET_FOCUS\",\n    Update = \"UPDATE\",\n}\n\nexport interface IAction {\n    type: Exclude<Type, Type.Update>;\n    payload: {\n        node: HTMLElement;\n    };\n}\n\ninterface UpdateAction {\n    type: Type.Update;\n    payload?: undefined;\n}\n\ntype Action = IAction | UpdateAction;\n\nconst nodeSorter = (a: HTMLElement, b: HTMLElement): number => {\n    if (a === b) {\n        return 0;\n    }\n\n    const position = a.compareDocumentPosition(b);\n\n    if (position & Node.DOCUMENT_POSITION_FOLLOWING || position & Node.DOCUMENT_POSITION_CONTAINED_BY) {\n        return -1;\n    } else if (position & Node.DOCUMENT_POSITION_PRECEDING || position & Node.DOCUMENT_POSITION_CONTAINS) {\n        return 1;\n    } else {\n        return 0;\n    }\n};\n\nexport const reducer: Reducer<IState, Action> = (state: IState, action: Action) => {\n    switch (action.type) {\n        case Type.Register: {\n            if (!state.activeNode) {\n                // Our list of nodes was empty, set activeNode to this first item\n                state.activeNode = action.payload.node;\n            }\n\n            if (state.nodes.includes(action.payload.node)) return state;\n\n            // Sadly due to the potential of DOM elements swapping order we can't do anything fancy like a binary insert\n            state.nodes.push(action.payload.node);\n            state.nodes.sort(nodeSorter);\n\n            return { ...state };\n        }\n\n        case Type.Unregister: {\n            const oldIndex = state.nodes.findIndex((r) => r === action.payload.node);\n\n            if (oldIndex === -1) {\n                return state; // already removed, this should not happen\n            }\n\n            if (state.nodes.splice(oldIndex, 1)[0] === state.activeNode) {\n                // we just removed the active node, need to replace it\n                // pick the node closest to the index the old node was in\n                if (oldIndex >= state.nodes.length) {\n                    state.activeNode = findSiblingElement(state.nodes, state.nodes.length - 1, true);\n                } else {\n                    state.activeNode =\n                        findSiblingElement(state.nodes, oldIndex) || findSiblingElement(state.nodes, oldIndex, true);\n                }\n                if (document.activeElement === document.body) {\n                    // if the focus got reverted to the body then the user was likely focused on the unmounted element\n                    setTimeout(() => state.activeNode?.focus(), 0);\n                }\n            }\n\n            // update the nodes list\n            return { ...state };\n        }\n\n        case Type.SetFocus: {\n            // if the node doesn't change just return the same object reference to skip a re-render\n            if (state.activeNode === action.payload.node) return state;\n            // update active node\n            state.activeNode = action.payload.node;\n            return { ...state };\n        }\n\n        case Type.Update: {\n            state.nodes.sort(nodeSorter);\n            return { ...state };\n        }\n\n        default:\n            return state;\n    }\n};\n\ninterface IProps {\n    handleLoop?: boolean;\n    handleHomeEnd?: boolean;\n    handleUpDown?: boolean;\n    handleLeftRight?: boolean;\n    handleInputFields?: boolean;\n    scrollIntoView?: boolean | ScrollIntoViewOptions;\n    children(renderProps: { onKeyDownHandler(ev: React.KeyboardEvent): void; onDragEndHandler(): void }): ReactNode;\n    onKeyDown?(ev: React.KeyboardEvent, state: IState, dispatch: Dispatch<IAction>): void;\n}\n\nexport const findSiblingElement = (\n    nodes: HTMLElement[],\n    startIndex: number,\n    backwards = false,\n    loop = false,\n): HTMLElement | undefined => {\n    if (backwards) {\n        for (let i = startIndex; i < nodes.length && i >= 0; i--) {\n            if (nodes[i]?.offsetParent !== null) {\n                return nodes[i];\n            }\n        }\n        if (loop) {\n            return findSiblingElement(nodes.slice(startIndex + 1), nodes.length - 1, true, false);\n        }\n    } else {\n        for (let i = startIndex; i < nodes.length && i >= 0; i++) {\n            if (nodes[i]?.offsetParent !== null) {\n                return nodes[i];\n            }\n        }\n        if (loop) {\n            return findSiblingElement(nodes.slice(0, startIndex), 0, false, false);\n        }\n    }\n};\n\nexport const RovingTabIndexProvider: React.FC<IProps> = ({\n    children,\n    handleHomeEnd,\n    handleUpDown,\n    handleLeftRight,\n    handleLoop,\n    handleInputFields,\n    scrollIntoView,\n    onKeyDown,\n}) => {\n    const [state, dispatch] = useReducer<IState, [Action]>(reducer, {\n        nodes: [],\n    });\n\n    const context = useMemo<IContext>(() => ({ state, dispatch }), [state]);\n\n    const onKeyDownHandler = useCallback(\n        (ev: React.KeyboardEvent) => {\n            if (onKeyDown) {\n                onKeyDown(ev, context.state, context.dispatch);\n                if (ev.defaultPrevented) {\n                    return;\n                }\n            }\n\n            let handled = false;\n            const action = getKeyBindingsManager().getAccessibilityAction(ev);\n            let focusNode: HTMLElement | undefined;\n            // Don't interfere with input default keydown behaviour\n            // but allow people to move focus from it with Tab.\n            if (!handleInputFields && checkInputableElement(ev.target as HTMLElement)) {\n                switch (action) {\n                    case KeyBindingAction.Tab:\n                        handled = true;\n                        if (context.state.nodes.length > 0) {\n                            const idx = context.state.nodes.indexOf(context.state.activeNode!);\n                            focusNode = findSiblingElement(\n                                context.state.nodes,\n                                idx + (ev.shiftKey ? -1 : 1),\n                                ev.shiftKey,\n                            );\n                        }\n                        break;\n                }\n            } else {\n                // check if we actually have any items\n                switch (action) {\n                    case KeyBindingAction.Home:\n                        if (handleHomeEnd) {\n                            handled = true;\n                            // move focus to first (visible) item\n                            focusNode = findSiblingElement(context.state.nodes, 0);\n                        }\n                        break;\n\n                    case KeyBindingAction.End:\n                        if (handleHomeEnd) {\n                            handled = true;\n                            // move focus to last (visible) item\n                            focusNode = findSiblingElement(context.state.nodes, context.state.nodes.length - 1, true);\n                        }\n                        break;\n\n                    case KeyBindingAction.ArrowDown:\n                    case KeyBindingAction.ArrowRight:\n                        if (\n                            (action === KeyBindingAction.ArrowDown && handleUpDown) ||\n                            (action === KeyBindingAction.ArrowRight && handleLeftRight)\n                        ) {\n                            handled = true;\n                            if (context.state.nodes.length > 0) {\n                                const idx = context.state.nodes.indexOf(context.state.activeNode!);\n                                focusNode = findSiblingElement(context.state.nodes, idx + 1, false, handleLoop);\n                            }\n                        }\n                        break;\n\n                    case KeyBindingAction.ArrowUp:\n                    case KeyBindingAction.ArrowLeft:\n                        if (\n                            (action === KeyBindingAction.ArrowUp && handleUpDown) ||\n                            (action === KeyBindingAction.ArrowLeft && handleLeftRight)\n                        ) {\n                            handled = true;\n                            if (context.state.nodes.length > 0) {\n                                const idx = context.state.nodes.indexOf(context.state.activeNode!);\n                                focusNode = findSiblingElement(context.state.nodes, idx - 1, true, handleLoop);\n                            }\n                        }\n                        break;\n                }\n            }\n\n            if (handled) {\n                ev.preventDefault();\n                ev.stopPropagation();\n            }\n\n            if (focusNode) {\n                focusNode?.focus();\n                // programmatic focus doesn't fire the onFocus handler, so we must do the do ourselves\n                dispatch({\n                    type: Type.SetFocus,\n                    payload: {\n                        node: focusNode,\n                    },\n                });\n                if (scrollIntoView) {\n                    focusNode?.scrollIntoView(scrollIntoView);\n                }\n            }\n        },\n        [\n            context,\n            onKeyDown,\n            handleHomeEnd,\n            handleUpDown,\n            handleLeftRight,\n            handleLoop,\n            handleInputFields,\n            scrollIntoView,\n        ],\n    );\n\n    const onDragEndHandler = useCallback(() => {\n        dispatch({\n            type: Type.Update,\n        });\n    }, []);\n\n    return (\n        <RovingTabIndexContext.Provider value={context}>\n            {children({ onKeyDownHandler, onDragEndHandler })}\n        </RovingTabIndexContext.Provider>\n    );\n};\n\n/**\n * Hook to register a roving tab index.\n *\n * inputRef is an optional argument; when passed this ref points to the DOM element\n * to which the callback ref is attached.\n *\n * Returns:\n * onFocus should be called when the index gained focus in any manner.\n * isActive should be used to set tabIndex in a manner such as `tabIndex={isActive ? 0 : -1}`.\n * ref is a callback ref that should be passed to a DOM node which will be used for DOM compareDocumentPosition.\n * nodeRef is a ref that points to the DOM element to which the ref mentioned above is attached.\n *\n * nodeRef = inputRef when inputRef argument is provided.\n */\nexport const useRovingTabIndex = <T extends HTMLElement>(\n    inputRef?: RefObject<T | null>,\n): [FocusHandler, boolean, RefCallback<T>, RefObject<T | null>] => {\n    const context = useContext(RovingTabIndexContext);\n\n    let nodeRef = useRef<T | null>(null);\n\n    if (inputRef) {\n        // if we are given a ref, use it instead of ours\n        nodeRef = inputRef;\n    }\n\n    const ref = useCallback((node: T | null) => {\n        if (node) {\n            nodeRef.current = node;\n            context.dispatch({\n                type: Type.Register,\n                payload: { node },\n            });\n        } else {\n            context.dispatch({\n                type: Type.Unregister,\n                payload: { node: nodeRef.current! },\n            });\n            nodeRef.current = null;\n        }\n    }, []); // eslint-disable-line react-hooks/exhaustive-deps\n\n    const onFocus = useCallback(() => {\n        if (!nodeRef.current) {\n            console.warn(\"useRovingTabIndex.onFocus called but the react ref does not point to any DOM element!\");\n            return;\n        }\n        context.dispatch({\n            type: Type.SetFocus,\n            payload: { node: nodeRef.current },\n        });\n    }, []); // eslint-disable-line react-hooks/exhaustive-deps\n\n    // eslint-disable-next-line react-compiler/react-compiler\n    const isActive = context.state.activeNode === nodeRef.current;\n    return [onFocus, isActive, ref, nodeRef];\n};\n\n// re-export the semantic helper components for simplicity\nexport { RovingTabIndexWrapper } from \"./roving/RovingTabIndexWrapper\";\nexport { RovingAccessibleButton } from \"./roving/RovingAccessibleButton\";\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type Ref, type JSX } from \"react\";\n\nimport { RovingTabIndexProvider } from \"./RovingTabIndex\";\nimport { getKeyBindingsManager } from \"../KeyBindingsManager\";\nimport { KeyBindingAction } from \"./KeyboardShortcuts\";\n\ninterface IProps extends Omit<React.HTMLProps<HTMLDivElement>, \"onKeyDown\"> {\n    ref?: Ref<HTMLDivElement>;\n}\n\n// This component implements the Toolbar design pattern from the WAI-ARIA Authoring Practices guidelines.\n// https://www.w3.org/TR/wai-aria-practices-1.1/#toolbar\n// All buttons passed in children must use RovingTabIndex to set `onFocus`, `isActive`, `ref`\nconst Toolbar = ({ children, ref, ...props }: IProps): JSX.Element => {\n    const onKeyDown = (ev: React.KeyboardEvent): void => {\n        const target = ev.target as HTMLElement;\n        // Don't interfere with input default keydown behaviour\n        if (target.tagName === \"INPUT\") return;\n\n        let handled = true;\n\n        // HOME and END are handled by RovingTabIndexProvider\n        const action = getKeyBindingsManager().getAccessibilityAction(ev);\n        switch (action) {\n            case KeyBindingAction.ArrowUp:\n            case KeyBindingAction.ArrowDown:\n                if (target.hasAttribute(\"aria-haspopup\")) {\n                    target.click();\n                }\n                break;\n\n            default:\n                handled = false;\n        }\n\n        if (handled) {\n            ev.preventDefault();\n            ev.stopPropagation();\n        }\n    };\n\n    // We handle both up/down and left/right as is allowed in the above WAI ARIA best practices\n    return (\n        <RovingTabIndexProvider handleHomeEnd handleLeftRight handleUpDown onKeyDown={onKeyDown}>\n            {({ onKeyDownHandler }) => (\n                <div {...props} onKeyDown={onKeyDownHandler} role=\"toolbar\" ref={ref}>\n                    {children}\n                </div>\n            )}\n        </RovingTabIndexProvider>\n    );\n};\n\nexport default Toolbar;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type Ref, type JSX } from \"react\";\n\nimport AccessibleButton, { type ButtonProps } from \"../../components/views/elements/AccessibleButton\";\n\ntype Props<T extends keyof HTMLElementTagNameMap> = ButtonProps<T> & {\n    label?: string;\n    // whether the context menu is currently open\n    isExpanded: boolean;\n    ref?: Ref<HTMLElementTagNameMap[T]>;\n};\n\n// Semantic component for representing the AccessibleButton which launches a <ContextMenu />\nexport const ContextMenuButton = function <T extends keyof HTMLElementTagNameMap>({\n    label,\n    isExpanded,\n    children,\n    onClick,\n    onContextMenu,\n    ref,\n    ...props\n}: Props<T>): JSX.Element {\n    return (\n        <AccessibleButton\n            {...props}\n            onClick={onClick}\n            onContextMenu={onContextMenu ?? onClick ?? undefined}\n            aria-label={label}\n            aria-haspopup={true}\n            aria-expanded={isExpanded}\n            ref={ref}\n        >\n            {children}\n        </AccessibleButton>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\n\nimport AccessibleButton, { type ButtonProps } from \"../../components/views/elements/AccessibleButton\";\n\ntype Props<T extends keyof HTMLElementTagNameMap> = ButtonProps<T> & {\n    // whether the context menu is currently open\n    isExpanded: boolean;\n};\n\n// Semantic component for representing the AccessibleButton which launches a <ContextMenu />\nexport const ContextMenuTooltipButton = function <T extends keyof HTMLElementTagNameMap>({\n    isExpanded,\n    children,\n    onClick,\n    onContextMenu,\n    ref,\n    ...props\n}: Props<T>): JSX.Element {\n    return (\n        <AccessibleButton\n            {...props}\n            onClick={onClick}\n            onContextMenu={onContextMenu ?? onClick ?? undefined}\n            aria-haspopup={true}\n            aria-expanded={isExpanded}\n            disableTooltip={isExpanded}\n            ref={ref}\n        >\n            {children}\n        </AccessibleButton>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { RovingAccessibleButton } from \"../RovingTabIndex\";\n\ninterface IProps extends React.ComponentProps<typeof RovingAccessibleButton> {\n    label?: string;\n    active: boolean;\n}\n\n// Semantic component for representing a role=menuitemradio\nexport const MenuItemRadio: React.FC<IProps> = ({ children, label, active, disabled, ...props }) => {\n    return (\n        <RovingAccessibleButton\n            {...props}\n            role=\"menuitemradio\"\n            aria-checked={active}\n            aria-disabled={disabled}\n            disabled={disabled}\n            aria-label={label}\n        >\n            {children}\n        </RovingAccessibleButton>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { asyncAction } from \"./actionCreators\";\nimport Modal from \"../Modal\";\nimport * as Rooms from \"../Rooms\";\nimport { _t } from \"../languageHandler\";\nimport { type AsyncActionPayload } from \"../dispatcher/payloads\";\nimport RoomListStore from \"../stores/room-list/RoomListStore\";\nimport { SortAlgorithm } from \"../stores/room-list/algorithms/models\";\nimport { DefaultTagID, type TagID } from \"../stores/room-list/models\";\nimport ErrorDialog from \"../components/views/dialogs/ErrorDialog\";\n\nexport default class RoomListActions {\n    /**\n     * Creates an action thunk that will do an asynchronous request to\n     * tag room.\n     *\n     * @param {MatrixClient} matrixClient the matrix client to set the\n     *                                    account data on.\n     * @param {Room} room the room to tag.\n     * @param {string} oldTag the tag to remove (unless oldTag ==== newTag)\n     * @param {string} newTag the tag with which to tag the room.\n     * @param {?number} oldIndex the previous position of the room in the\n     *                           list of rooms.\n     * @param {?number} newIndex the new position of the room in the list\n     *                           of rooms.\n     * @returns {AsyncActionPayload} an async action payload\n     * @see asyncAction\n     */\n    public static tagRoom(\n        matrixClient: MatrixClient,\n        room: Room,\n        oldTag: TagID | null,\n        newTag: TagID | null,\n        newIndex: number,\n    ): AsyncActionPayload {\n        let metaData: Parameters<MatrixClient[\"setRoomTag\"]>[2] | undefined;\n\n        // Is the tag ordered manually?\n        const store = RoomListStore.instance;\n        if (newTag && store.getTagSorting(newTag) === SortAlgorithm.Manual) {\n            const newList = [...store.orderedLists[newTag]];\n\n            newList.sort((a, b) => a.tags[newTag].order - b.tags[newTag].order);\n\n            const indexBefore = newIndex - 1;\n            const indexAfter = newIndex;\n\n            const prevOrder = indexBefore <= 0 ? 0 : newList[indexBefore].tags[newTag].order;\n            const nextOrder = indexAfter >= newList.length ? 1 : newList[indexAfter].tags[newTag].order;\n\n            metaData = {\n                order: (prevOrder + nextOrder) / 2.0,\n            };\n        }\n\n        return asyncAction(\n            \"RoomListActions.tagRoom\",\n            () => {\n                const promises: Promise<any>[] = [];\n                const roomId = room.roomId;\n\n                // Evil hack to get DMs behaving\n                if (\n                    (oldTag === undefined && newTag === DefaultTagID.DM) ||\n                    (oldTag === DefaultTagID.DM && newTag === undefined)\n                ) {\n                    return Rooms.guessAndSetDMRoom(room, newTag === DefaultTagID.DM).catch((err) => {\n                        logger.error(\"Failed to set DM tag \" + err);\n                        Modal.createDialog(ErrorDialog, {\n                            title: _t(\"room_list|failed_set_dm_tag\"),\n                            description: err?.message ?? _t(\"invite|failed_generic\"),\n                        });\n                    });\n                }\n\n                const hasChangedSubLists = oldTag !== newTag;\n\n                // More evilness: We will still be dealing with moving to favourites/low prio,\n                // but we avoid ever doing a request with TAG_DM.\n                //\n                // if we moved lists, remove the old tag\n                if (oldTag && oldTag !== DefaultTagID.DM && hasChangedSubLists) {\n                    const promiseToDelete = matrixClient.deleteRoomTag(roomId, oldTag).catch(function (err) {\n                        logger.error(\"Failed to remove tag \" + oldTag + \" from room: \" + err);\n                        Modal.createDialog(ErrorDialog, {\n                            title: _t(\"room_list|failed_remove_tag\", { tagName: oldTag }),\n                            description: err?.message ?? _t(\"invite|failed_generic\"),\n                        });\n                    });\n\n                    promises.push(promiseToDelete);\n                }\n\n                // if we moved lists or the ordering changed, add the new tag\n                if (newTag && newTag !== DefaultTagID.DM && (hasChangedSubLists || metaData)) {\n                    const promiseToAdd = matrixClient.setRoomTag(roomId, newTag, metaData).catch(function (err) {\n                        logger.error(\"Failed to add tag \" + newTag + \" to room: \" + err);\n                        Modal.createDialog(ErrorDialog, {\n                            title: _t(\"room_list|failed_add_tag\", { tagName: newTag }),\n                            description: err?.message ?? _t(\"invite|failed_generic\"),\n                        });\n\n                        throw err;\n                    });\n\n                    promises.push(promiseToAdd);\n                }\n\n                return Promise.all(promises);\n            },\n            () => {\n                // For an optimistic update\n                return {\n                    room,\n                    oldTag,\n                    newTag,\n                    metaData,\n                };\n            },\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type AsyncActionFn, AsyncActionPayload } from \"../dispatcher/payloads\";\n\n/**\n * Create an action thunk that will dispatch actions indicating the current\n * status of the Promise returned by fn.\n *\n * @param {string} id the id to give the dispatched actions. This is given a\n *                    suffix determining whether it is pending, successful or\n *                    a failure.\n * @param {function} fn a function that returns a Promise.\n * @param {function?} pendingFn a function that returns an object to assign\n *                              to the `request` key of the ${id}.pending\n *                              payload.\n * @returns {AsyncActionPayload} an async action payload. Includes a function\n *                     that uses its single argument as a dispatch function\n *                     to dispatch the following actions:\n *                         `${id}.pending` and either\n *                         `${id}.success` or\n *                         `${id}.failure`.\n *\n *                     The shape of each are:\n *                     { action: '${id}.pending', request }\n *                     { action: '${id}.success', result }\n *                     { action: '${id}.failure', err }\n *\n *                     where `request` is returned by `pendingFn` and\n *                     result is the result of the promise returned by\n *                     `fn`.\n */\nexport function asyncAction(id: string, fn: () => Promise<any>, pendingFn: () => any | null): AsyncActionPayload {\n    const helper: AsyncActionFn = (dispatch) => {\n        dispatch({\n            action: id + \".pending\",\n            request: typeof pendingFn === \"function\" ? pendingFn() : undefined,\n        });\n        fn()\n            .then((result) => {\n                dispatch({ action: id + \".success\", result });\n            })\n            .catch((err) => {\n                dispatch({ action: id + \".failure\", err });\n            });\n    };\n    return new AsyncActionPayload(helper);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { createAudioContext } from \"./compat\";\n\nconst formatMap = {\n    mp3: \"audio/mpeg\",\n    ogg: \"audio/ogg\",\n};\n\nexport class BackgroundAudio {\n    private audioContext = createAudioContext();\n    private sounds: Record<string, AudioBuffer> = {};\n\n    public async pickFormatAndPlay<F extends Array<keyof typeof formatMap>>(\n        urlPrefix: string,\n        formats: F,\n        loop = false,\n    ): Promise<AudioBufferSourceNode> {\n        const format = this.pickFormat(...formats);\n        if (!format) {\n            console.log(\"Browser doesn't support any of the formats\", formats);\n            // Will probably never happen. If happened, format=\"\" and will fail to load audio. Who cares...\n        }\n\n        return this.play(`${urlPrefix}.${format}`, loop);\n    }\n\n    public async play(url: string, loop = false): Promise<AudioBufferSourceNode> {\n        if (!this.sounds.hasOwnProperty(url)) {\n            // No cache, fetch it\n            const response = await fetch(url);\n            if (response.status != 200) {\n                logger.warn(\"Failed to fetch error audio\");\n            }\n            const buffer = await response.arrayBuffer();\n            const sound = await this.audioContext.decodeAudioData(buffer);\n            this.sounds[url] = sound;\n        }\n        const source = this.audioContext.createBufferSource();\n        source.buffer = this.sounds[url];\n        source.loop = loop;\n        source.connect(this.audioContext.destination);\n\n        await this.audioContext.resume();\n        source.onended = () => {\n            this.audioContext.suspend();\n        };\n\n        source.start();\n        return source;\n    }\n\n    private pickFormat<F extends Array<keyof typeof formatMap>>(...formats: F): F[number] | null {\n        // Detect supported formats\n        const audioElement = document.createElement(\"audio\");\n\n        for (const format of formats) {\n            if (audioElement.canPlayType(formatMap[format])) {\n                return format;\n            }\n        }\n        return null;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { SimpleObservable } from \"matrix-widget-api\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { type IDestroyable } from \"../utils/IDestroyable\";\n\n/**\n * Tracks accurate human-perceptible time for an audio clip, as informed\n * by managed playback. This clock is tightly coupled with the operation\n * of the Playback class, making assumptions about how the provided\n * AudioContext will be used (suspended/resumed to preserve time, etc).\n *\n * But why do we need a clock? The AudioContext exposes time information,\n * and so does the audio buffer, but not in a way that is useful for humans\n * to perceive. The audio buffer time is often lagged behind the context\n * time due to internal processing delays of the audio API. Additionally,\n * the context's time is tracked from when it was first initialized/started,\n * not related to positioning within the clip. However, the context time\n * is the most accurate time we can use to determine position within the\n * clip if we're fast enough to track the pauses and stops.\n *\n * As a result, we track every play, pause, stop, and seek event from the\n * Playback class (kinda: it calls us, which is close enough to the same\n * thing). These events are then tracked on the AudioContext time scale,\n * with assumptions that code execution will result in negligible desync\n * of the clock, or at least no perceptible difference in time. It's\n * extremely important that the calling code, and the clock's own code,\n * is extremely fast between the event happening and the clock time being\n * tracked - anything more than a dozen milliseconds is likely to stack up\n * poorly, leading to clock desync.\n *\n * Clock desync can be dangerous for the stability of the playback controls:\n * if the clock thinks the user is somewhere else in the clip, it could\n * inform the playback of the wrong place in time, leading to dead air in\n * the output or, if severe enough, a clock that won't stop running while\n * the audio is paused/stopped. Other examples include the clip stopping at\n * 90% time due to playback ending, the clip playing from the wrong spot\n * relative to the time, and negative clock time.\n *\n * Note that the clip duration is fed to the clock: this is to ensure that\n * we have the most accurate time possible to present.\n */\nexport class PlaybackClock implements IDestroyable {\n    private clipStart = 0;\n    private stopped = true;\n    private lastCheck = 0;\n    private observable = new SimpleObservable<number[]>();\n    private timerId?: number;\n    private clipDuration = 0;\n    private placeholderDuration = 0;\n\n    public constructor(private context: AudioContext) {}\n\n    public get durationSeconds(): number {\n        return this.clipDuration || this.placeholderDuration;\n    }\n\n    public set durationSeconds(val: number) {\n        this.clipDuration = val;\n        this.observable.update([this.timeSeconds, this.clipDuration]);\n    }\n\n    public get timeSeconds(): number {\n        // The modulo is to ensure that we're only looking at the most recent clip\n        // time, as the context is long-running and multiple plays might not be\n        // informed to us (if the control is looping, for example). By taking the\n        // remainder of the division operation, we're assuming that playback is\n        // incomplete or stopped, thus giving an accurate position within the active\n        // clip segment.\n        return (this.context.currentTime - this.clipStart) % this.clipDuration || 0;\n    }\n\n    public get liveData(): SimpleObservable<number[]> {\n        return this.observable;\n    }\n\n    private checkTime = (force = false): void => {\n        const now = this.timeSeconds; // calculated dynamically\n        if (this.lastCheck !== now || force) {\n            this.observable.update([now, this.durationSeconds]);\n            this.lastCheck = now;\n        }\n    };\n\n    /**\n     * Populates default information about the audio clip from the event body.\n     * The placeholders will be overridden once known.\n     * @param {MatrixEvent} event The event to use for placeholders.\n     */\n    public populatePlaceholdersFrom(event: MatrixEvent): void {\n        const durationMs = Number(event.getContent()[\"info\"]?.[\"duration\"]);\n        if (Number.isFinite(durationMs)) this.placeholderDuration = durationMs / 1000;\n    }\n\n    /**\n     * Mark the time in the audio context where the clip starts/has been loaded.\n     * This is to ensure the clock isn't skewed into thinking it is ~0.5s into\n     * a clip when the duration is set.\n     */\n    public flagLoadTime(): void {\n        this.clipStart = this.context.currentTime;\n    }\n\n    public flagStart(): void {\n        if (this.stopped) {\n            this.clipStart = this.context.currentTime;\n            this.stopped = false;\n        }\n\n        if (!this.timerId) {\n            // 100ms interval to make sure the time is as accurate as possible without being overly insane\n            this.timerId = window.setInterval(this.checkTime, 100);\n        }\n    }\n\n    public flagStop(): void {\n        this.stopped = true;\n\n        // Reset the clock time now so that the update going out will trigger components\n        // to check their seek/position information (alongside the clock).\n        this.clipStart = this.context.currentTime;\n    }\n\n    public syncTo(contextTime: number, clipTime: number): void {\n        this.clipStart = contextTime - clipTime;\n        this.stopped = false; // count as a mid-stream pause (if we were stopped)\n        this.checkTime(true);\n    }\n\n    public destroy(): void {\n        this.observable.close();\n        if (this.timerId) clearInterval(this.timerId);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Request, type Response } from \"./workers/playback.worker\";\nimport { WorkerManager } from \"./WorkerManager\";\nimport playbackWorkerFactory from \"./workers/playbackWorkerFactory\";\n\nexport class PlaybackEncoder {\n    private static internalInstance = new PlaybackEncoder();\n\n    public static get instance(): PlaybackEncoder {\n        return PlaybackEncoder.internalInstance;\n    }\n\n    private readonly worker = new WorkerManager<Request, Response>(playbackWorkerFactory());\n\n    public getPlaybackWaveform(input: Float32Array): Promise<number[]> {\n        return this.worker.call({ data: Array.from(input) }).then((resp) => resp.waveform);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport default function factory(options?: WorkerOptions | undefined): Worker {\n    return new Worker(\n        /* webpackChunkName: \"playback.worker\" */ new URL(\"./playback.worker.ts\", import.meta.url),\n        options,\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport EventEmitter from \"events\";\nimport { SimpleObservable } from \"matrix-widget-api\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { clamp } from \"@element-hq/web-shared-components\";\n\nimport { UPDATE_EVENT } from \"../stores/AsyncStore\";\nimport { arrayFastResample } from \"../utils/arrays\";\nimport { type IDestroyable } from \"../utils/IDestroyable\";\nimport { PlaybackClock } from \"./PlaybackClock\";\nimport { createAudioContext, decodeOgg } from \"./compat\";\nimport { DEFAULT_WAVEFORM, PLAYBACK_WAVEFORM_SAMPLES } from \"./consts\";\nimport { PlaybackEncoder } from \"../PlaybackEncoder\";\n\nexport enum PlaybackState {\n    Preparing = \"preparing\", // preparing to decode\n    Decoding = \"decoding\",\n    Stopped = \"stopped\", // no progress on timeline\n    Paused = \"paused\", // some progress on timeline\n    Playing = \"playing\", // active progress through timeline\n}\n\nconst THUMBNAIL_WAVEFORM_SAMPLES = 100; // arbitrary: [30,120]\n\nexport interface PlaybackInterface {\n    readonly currentState: PlaybackState;\n    readonly liveData: SimpleObservable<number[]>;\n    readonly timeSeconds: number;\n    readonly durationSeconds: number;\n    skipTo(timeSeconds: number): Promise<void>;\n}\n\nexport class Playback extends EventEmitter implements IDestroyable, PlaybackInterface {\n    /**\n     * Stable waveform for representing a thumbnail of the media. Values are\n     * guaranteed to be between zero and one, inclusive.\n     */\n    public readonly thumbnailWaveform: number[];\n\n    private readonly context: AudioContext;\n    private source?: AudioBufferSourceNode | MediaElementAudioSourceNode;\n    private state = PlaybackState.Decoding;\n    private audioBuf?: AudioBuffer;\n    private element?: HTMLAudioElement;\n    private resampledWaveform: number[];\n    private waveformObservable = new SimpleObservable<number[]>();\n    private readonly clock: PlaybackClock;\n    private readonly fileSize: number;\n\n    /**\n     * Creates a new playback instance from a buffer.\n     * @param {ArrayBuffer} buf The buffer containing the sound sample.\n     * @param {number[]} seedWaveform Optional seed waveform to present until the proper waveform\n     * can be calculated. Contains values between zero and one, inclusive.\n     */\n    public constructor(\n        private buf: ArrayBuffer,\n        seedWaveform = DEFAULT_WAVEFORM,\n    ) {\n        super();\n        // Capture the file size early as reading the buffer will result in a 0-length buffer left behind\n        this.fileSize = this.buf.byteLength;\n        this.context = createAudioContext();\n        this.resampledWaveform = arrayFastResample(seedWaveform ?? DEFAULT_WAVEFORM, PLAYBACK_WAVEFORM_SAMPLES);\n        this.thumbnailWaveform = arrayFastResample(seedWaveform ?? DEFAULT_WAVEFORM, THUMBNAIL_WAVEFORM_SAMPLES);\n        this.waveformObservable.update(this.resampledWaveform);\n        this.clock = new PlaybackClock(this.context);\n    }\n\n    /**\n     * Size of the audio clip in bytes. May be zero if unknown. This is updated\n     * when the playback goes through phase changes.\n     */\n    public get sizeBytes(): number {\n        return this.fileSize;\n    }\n\n    /**\n     * Stable waveform for the playback. Values are guaranteed to be between\n     * zero and one, inclusive.\n     */\n    public get waveform(): number[] {\n        return this.resampledWaveform;\n    }\n\n    public get waveformData(): SimpleObservable<number[]> {\n        return this.waveformObservable;\n    }\n\n    public get clockInfo(): PlaybackClock {\n        return this.clock;\n    }\n\n    public get liveData(): SimpleObservable<number[]> {\n        return this.clock.liveData;\n    }\n\n    public get timeSeconds(): number {\n        return this.clock.timeSeconds;\n    }\n\n    public get durationSeconds(): number {\n        return this.clock.durationSeconds;\n    }\n\n    public get currentState(): PlaybackState {\n        return this.state;\n    }\n\n    public get isPlaying(): boolean {\n        return this.currentState === PlaybackState.Playing;\n    }\n\n    public emit(event: PlaybackState, ...args: any[]): boolean {\n        this.state = event;\n        super.emit(event, ...args);\n        super.emit(UPDATE_EVENT, event, ...args);\n        return true; // we don't ever care if the event had listeners, so just return \"yes\"\n    }\n\n    public destroy(): void {\n        // Dev note: It's critical that we call stop() during cleanup to ensure that downstream callers\n        // are aware of the final clock position before the user triggered an unload.\n        // noinspection JSIgnoredPromiseFromCall - not concerned about being called async here\n        this.stop();\n        this.removeAllListeners();\n        this.clock.destroy();\n        this.waveformObservable.close();\n        if (this.element) {\n            URL.revokeObjectURL(this.element.src);\n            this.element.remove();\n        }\n    }\n\n    public async prepare(): Promise<void> {\n        // don't attempt to decode the media again\n        // AudioContext.decodeAudioData detaches the array buffer `this.buf`\n        // meaning it cannot be re-read\n        if (this.state !== PlaybackState.Decoding) {\n            return;\n        }\n\n        this.state = PlaybackState.Preparing;\n\n        // The point where we use an audio element is fairly arbitrary, though we don't want\n        // it to be too low. As of writing, voice messages want to show a waveform but audio\n        // messages do not. Using an audio element means we can't show a waveform preview, so\n        // we try to target the difference between a voice message file and large audio file.\n        // Overall, the point of this is to avoid memory-related issues due to storing a massive\n        // audio buffer in memory, as that can balloon to far greater than the input buffer's\n        // byte length.\n        if (this.buf.byteLength > 5 * 1024 * 1024) {\n            // 5mb\n            logger.log(\"Audio file too large: processing through <audio /> element\");\n            this.element = document.createElement(\"AUDIO\") as HTMLAudioElement;\n            const deferred = Promise.withResolvers<unknown>();\n            this.element.onloadeddata = deferred.resolve;\n            this.element.onerror = deferred.reject;\n            this.element.src = URL.createObjectURL(new Blob([this.buf]));\n            await deferred.promise; // make sure the audio element is ready for us\n        } else {\n            try {\n                this.audioBuf = await this.context.decodeAudioData(this.buf);\n            } catch (e) {\n                logger.error(\"Error decoding recording:\", e);\n                logger.warn(\"Trying to re-encode to WAV instead...\");\n\n                try {\n                    // This error handler is largely for Safari, which doesn't support Opus/Ogg very well.\n                    const wav = await decodeOgg(this.buf);\n                    this.audioBuf = await this.context.decodeAudioData(wav);\n                } catch (e) {\n                    logger.error(\"Error decoding recording:\", e);\n                    throw e;\n                }\n            }\n\n            // Update the waveform to the real waveform once we have channel data to use. We don't\n            // exactly trust the user-provided waveform to be accurate...\n            this.resampledWaveform = await PlaybackEncoder.instance.getPlaybackWaveform(\n                this.audioBuf.getChannelData(0),\n            );\n        }\n\n        this.waveformObservable.update(this.resampledWaveform);\n\n        this.clock.flagLoadTime(); // must happen first because setting the duration fires a clock update\n        this.clock.durationSeconds = this.element?.duration ?? this.audioBuf!.duration;\n\n        // Signal that we're not decoding anymore. This is done last to ensure the clock is updated for\n        // when the downstream callers try to use it.\n        this.emit(PlaybackState.Stopped); // signal that we're not decoding anymore\n    }\n\n    private onPlaybackEnd = async (): Promise<void> => {\n        await this.context.suspend();\n        this.emit(PlaybackState.Stopped);\n        this.clock.flagStop();\n    };\n\n    public async play(): Promise<void> {\n        // We can't restart a buffer source, so we need to create a new one if we hit the end\n        if (this.state === PlaybackState.Stopped) {\n            this.disconnectSource();\n            this.makeNewSourceBuffer();\n            if (this.element) {\n                await this.element.play();\n            } else {\n                (this.source as AudioBufferSourceNode).start();\n            }\n        }\n\n        // We use the context suspend/resume functions because it allows us to pause a source\n        // node, but that still doesn't help us when the source node runs out (see above).\n        await this.context.resume();\n        this.clock.flagStart();\n        this.emit(PlaybackState.Playing);\n    }\n\n    private disconnectSource(): void {\n        if (this.element) return; // leave connected, we can (and must) re-use it\n        this.source?.disconnect();\n        this.source?.removeEventListener(\"ended\", this.onPlaybackEnd);\n    }\n\n    private makeNewSourceBuffer(): void {\n        if (this.element && this.source) return; // leave connected, we can (and must) re-use it\n\n        if (this.element) {\n            this.source = this.context.createMediaElementSource(this.element);\n        } else {\n            this.source = this.context.createBufferSource();\n            this.source.buffer = this.audioBuf ?? null;\n        }\n\n        this.source.addEventListener(\"ended\", this.onPlaybackEnd);\n        this.source.connect(this.context.destination);\n    }\n\n    public async pause(): Promise<void> {\n        await this.context.suspend();\n        this.emit(PlaybackState.Paused);\n    }\n\n    public stop(): Promise<void> {\n        return this.onPlaybackEnd();\n    }\n\n    public async toggle(): Promise<void> {\n        if (this.isPlaying) await this.pause();\n        else await this.play();\n    }\n\n    public async skipTo(timeSeconds: number): Promise<void> {\n        // Dev note: this function talks a lot about clock desyncs. There is a clock running\n        // independently to the audio context and buffer so that accurate human-perceptible\n        // time can be exposed. The PlaybackClock class has more information, but the short\n        // version is that we need to line up the useful time (clip position) with the context\n        // time, and avoid as many deviations as possible as otherwise the user could see the\n        // wrong time, and we stop playback at the wrong time, etc.\n\n        timeSeconds = clamp(timeSeconds, 0, this.clock.durationSeconds);\n\n        // Track playing state so we don't cause seeking to start playing the track.\n        const isPlaying = this.isPlaying;\n\n        if (isPlaying) {\n            // Pause first so we can get an accurate measurement of time\n            await this.context.suspend();\n        }\n\n        // We can't simply tell the context/buffer to jump to a time, so we have to\n        // start a whole new buffer and start it from the new time offset.\n        const now = this.context.currentTime;\n        this.disconnectSource();\n        this.makeNewSourceBuffer();\n\n        // We have to resync the clock because it can get confused about where we're\n        // at in the audio clip.\n        this.clock.syncTo(now, timeSeconds);\n\n        // Always start the source to queue it up. We have to do this now (and pause\n        // quickly if we're not supposed to be playing) as otherwise the clock can desync\n        // when it comes time to the user hitting play. After a couple jumps, the user\n        // will have desynced the clock enough to be about 10-15 seconds off, while this\n        // keeps it as close to perfect as humans can perceive.\n        if (this.element) {\n            this.element.currentTime = timeSeconds;\n        } else {\n            (this.source as AudioBufferSourceNode).start(now, timeSeconds);\n        }\n\n        // Dev note: it's critical that the code gap between `this.source.start()` and\n        // `this.pause()` is as small as possible: we do not want to delay *anything*\n        // as that could cause a clock desync, or a buggy feeling as a single note plays\n        // during seeking.\n\n        if (isPlaying) {\n            // If we were playing before, continue the context so the clock doesn't desync.\n            await this.context.resume();\n        } else {\n            // As mentioned above, we'll have to pause the clip if we weren't supposed to\n            // be playing it just yet. If we didn't have this, the audio clip plays but all\n            // the states will be wrong: clock won't advance, pause state doesn't match the\n            // blaring noise leaving the user's speakers, etc.\n            //\n            // Also as mentioned, if the code gap is small enough then this should be\n            // executed immediately after the start time, leaving no feasible time for the\n            // user's speakers to play any sound.\n            await this.pause();\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { Playback } from \"./Playback\";\nimport { type PlaybackManager } from \"./PlaybackManager\";\nimport { DEFAULT_WAVEFORM } from \"./consts\";\n\n/**\n * A managed playback is a Playback instance that is guided by a PlaybackManager.\n */\nexport class ManagedPlayback extends Playback {\n    public constructor(\n        private manager: PlaybackManager,\n        buf: ArrayBuffer,\n        seedWaveform = DEFAULT_WAVEFORM,\n    ) {\n        super(buf, seedWaveform);\n    }\n\n    public async play(): Promise<void> {\n        this.manager.pauseAllExcept(this);\n        return super.play();\n    }\n\n    public destroy(): void {\n        this.manager.destroyPlaybackInstance(this);\n        super.destroy();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Playback, PlaybackState } from \"./Playback\";\nimport { ManagedPlayback } from \"./ManagedPlayback\";\nimport { DEFAULT_WAVEFORM } from \"./consts\";\n\n/**\n * Handles management of playback instances to ensure certain functionality, like\n * one playback operating at any one time.\n */\nexport class PlaybackManager {\n    private static internalInstance: PlaybackManager;\n\n    private instances: ManagedPlayback[] = [];\n\n    public static get instance(): PlaybackManager {\n        if (!PlaybackManager.internalInstance) {\n            PlaybackManager.internalInstance = new PlaybackManager();\n        }\n        return PlaybackManager.internalInstance;\n    }\n\n    /**\n     * Pauses all other playback instances. If no playback is provided, all playing\n     * instances are paused.\n     * @param playback Optional. The playback to leave untouched.\n     */\n    public pauseAllExcept(playback?: Playback): void {\n        this.instances\n            .filter((p) => p !== playback && p.currentState === PlaybackState.Playing)\n            .forEach((p) => p.pause());\n    }\n\n    public destroyPlaybackInstance(playback: ManagedPlayback): void {\n        this.instances = this.instances.filter((p) => p !== playback);\n    }\n\n    public createPlaybackInstance(buf: ArrayBuffer, waveform = DEFAULT_WAVEFORM): Playback {\n        const instance = new ManagedPlayback(this, buf, waveform);\n        this.instances.push(instance);\n        return instance;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { arrayFastClone, arraySeed } from \"./arrays\";\n\n/**\n * An array which is of fixed length and accepts rolling values. Values will\n * be inserted on the left, falling off the right.\n */\nexport class FixedRollingArray<T> {\n    private samples: T[] = [];\n\n    /**\n     * Creates a new fixed rolling array.\n     * @param width The width of the array.\n     * @param padValue The value to seed the array with.\n     */\n    public constructor(\n        private width: number,\n        padValue: T,\n    ) {\n        this.samples = arraySeed(padValue, this.width);\n    }\n\n    /**\n     * The array, as a fixed length.\n     */\n    public get value(): T[] {\n        return this.samples;\n    }\n\n    /**\n     * Pushes a value to the array.\n     * @param value The value to push.\n     */\n    public pushValue(value: T): void {\n        let swap = arrayFastClone(this.samples);\n        swap.splice(0, 0, value);\n        if (swap.length > this.width) {\n            swap = swap.slice(0, this.width);\n        }\n        this.samples = swap;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport Recorder from \"opus-recorder/dist/recorder.min.js\";\nimport encoderPath from \"opus-recorder/dist/encoderWorker.min.js\";\nimport { SimpleObservable } from \"matrix-widget-api\";\nimport EventEmitter from \"events\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { clamp } from \"@element-hq/web-shared-components\";\n\nimport MediaDeviceHandler from \"../MediaDeviceHandler\";\nimport { type IDestroyable } from \"../utils/IDestroyable\";\nimport { Singleflight } from \"../utils/Singleflight\";\nimport { PayloadEvent, WORKLET_NAME } from \"./consts\";\nimport { UPDATE_EVENT } from \"../stores/AsyncStore\";\nimport { createAudioContext } from \"./compat\";\nimport { FixedRollingArray } from \"../utils/FixedRollingArray\";\nimport recorderWorkletFactory from \"./recorderWorkletFactory\";\n\nconst CHANNELS = 1; // stereo isn't important\nexport const SAMPLE_RATE = 48000; // 48khz is what WebRTC uses. 12khz is where we lose quality.\nconst TARGET_MAX_LENGTH = 900; // 15 minutes in seconds. Somewhat arbitrary, though longer == larger files.\nconst TARGET_WARN_TIME_LEFT = 10; // 10 seconds, also somewhat arbitrary.\n\nexport const RECORDING_PLAYBACK_SAMPLES = 44;\n\ninterface RecorderOptions {\n    bitrate: number;\n    encoderApplication: number;\n}\n\nexport const voiceRecorderOptions: RecorderOptions = {\n    bitrate: 24000, // recommended Opus bitrate for high-quality VoIP\n    encoderApplication: 2048, // voice\n};\n\nexport const highQualityRecorderOptions: RecorderOptions = {\n    bitrate: 96000, // recommended Opus bitrate for high-quality music/audio streaming\n    encoderApplication: 2049, // full band audio\n};\n\nexport interface IRecordingUpdate {\n    waveform: number[]; // floating points between 0 (low) and 1 (high).\n    timeSeconds: number; // float\n}\n\nexport enum RecordingState {\n    Started = \"started\",\n    EndingSoon = \"ending_soon\", // emits an object with a single numerical value: secondsLeft\n    Ended = \"ended\",\n    Uploading = \"uploading\",\n    Uploaded = \"uploaded\",\n}\n\nexport class VoiceRecording extends EventEmitter implements IDestroyable {\n    private recorder?: Recorder;\n    private recorderContext?: AudioContext;\n    private recorderSource?: MediaStreamAudioSourceNode;\n    private recorderStream?: MediaStream;\n    private recorderWorklet?: AudioWorkletNode;\n    private recorderProcessor?: ScriptProcessorNode;\n    private recording = false;\n    private observable?: SimpleObservable<IRecordingUpdate>;\n    private targetMaxLength: number | null = TARGET_MAX_LENGTH;\n    public amplitudes: number[] = []; // at each second mark, generated\n    private liveWaveform = new FixedRollingArray(RECORDING_PLAYBACK_SAMPLES, 0);\n    public onDataAvailable?: (data: ArrayBuffer) => void;\n\n    public get contentType(): string {\n        return \"audio/ogg\";\n    }\n\n    public get durationSeconds(): number {\n        if (!this.recorder || !this.recorderContext) throw new Error(\"Duration not available without a recording\");\n        return this.recorderContext.currentTime;\n    }\n\n    public get isRecording(): boolean {\n        return this.recording;\n    }\n\n    public emit(event: string, ...args: any[]): boolean {\n        super.emit(event, ...args);\n        super.emit(UPDATE_EVENT, event, ...args);\n        return true; // we don't ever care if the event had listeners, so just return \"yes\"\n    }\n\n    public disableMaxLength(): void {\n        this.targetMaxLength = null;\n    }\n\n    private shouldRecordInHighQuality(): boolean {\n        // Non-voice use case is suspected when noise suppression is disabled by the user.\n        // When recording complex audio, higher quality is required to avoid audio artifacts.\n        // This is a really arbitrary decision, but it can be refined/replaced at any time.\n        return !MediaDeviceHandler.getAudioNoiseSuppression();\n    }\n\n    private async makeRecorder(): Promise<void> {\n        try {\n            this.recorderStream = await navigator.mediaDevices.getUserMedia({\n                audio: {\n                    channelCount: CHANNELS,\n                    deviceId: MediaDeviceHandler.getAudioInput(),\n                    autoGainControl: { ideal: MediaDeviceHandler.getAudioAutoGainControl() },\n                    echoCancellation: { ideal: MediaDeviceHandler.getAudioEchoCancellation() },\n                    noiseSuppression: { ideal: MediaDeviceHandler.getAudioNoiseSuppression() },\n                },\n            });\n            this.recorderContext = createAudioContext({\n                // latencyHint: \"interactive\", // we don't want a latency hint (this causes data smoothing)\n            });\n            this.recorderSource = this.recorderContext.createMediaStreamSource(this.recorderStream);\n\n            // Connect our inputs and outputs\n            if (this.recorderContext.audioWorklet) {\n                // Set up our worklet. We use this for timing information and waveform analysis: the\n                // web audio API prefers this be done async to avoid holding the main thread with math.\n                await recorderWorkletFactory(this.recorderContext);\n\n                this.recorderWorklet = new AudioWorkletNode(this.recorderContext, WORKLET_NAME);\n                this.recorderSource.connect(this.recorderWorklet);\n                this.recorderWorklet.connect(this.recorderContext.destination);\n\n                // Dev note: we can't use `addEventListener` for some reason. It just doesn't work.\n                this.recorderWorklet.port.onmessage = (ev) => {\n                    switch (ev.data[\"ev\"]) {\n                        case PayloadEvent.Timekeep:\n                            this.processAudioUpdate(ev.data[\"timeSeconds\"]);\n                            break;\n                        case PayloadEvent.AmplitudeMark:\n                            // Sanity check to make sure we're adding about one sample per second\n                            if (ev.data[\"forIndex\"] === this.amplitudes.length) {\n                                this.amplitudes.push(ev.data[\"amplitude\"]);\n                                this.liveWaveform.pushValue(ev.data[\"amplitude\"]);\n                            }\n                            break;\n                    }\n                };\n            } else {\n                // Safari fallback: use a processor node instead, buffered to 1024 bytes of data\n                // like the worklet is.\n                this.recorderProcessor = this.recorderContext.createScriptProcessor(1024, CHANNELS, CHANNELS);\n                this.recorderSource.connect(this.recorderProcessor);\n                this.recorderProcessor.connect(this.recorderContext.destination);\n                this.recorderProcessor.addEventListener(\"audioprocess\", this.onAudioProcess);\n            }\n\n            const recorderOptions = this.shouldRecordInHighQuality()\n                ? highQualityRecorderOptions\n                : voiceRecorderOptions;\n            const { encoderApplication, bitrate } = recorderOptions;\n\n            this.recorder = new Recorder({\n                encoderPath, // magic from webpack\n                encoderSampleRate: SAMPLE_RATE,\n                encoderApplication: encoderApplication,\n                streamPages: true, // this speeds up the encoding process by using CPU over time\n                encoderFrameSize: 20, // ms, arbitrary frame size we send to the encoder\n                numberOfChannels: CHANNELS,\n                sourceNode: this.recorderSource,\n                encoderBitRate: bitrate,\n\n                // We use low values for the following to ease CPU usage - the resulting waveform\n                // is indistinguishable for a voice message. Note that the underlying library will\n                // pick defaults which prefer the highest possible quality, CPU be damned.\n                encoderComplexity: 3, // 0-10, 10 is slow and high quality.\n                resampleQuality: 3, // 0-10, 10 is slow and high quality\n            });\n\n            // not using EventEmitter here because it leads to detached bufferes\n            this.recorder.ondataavailable = (data: ArrayBuffer) => this.onDataAvailable?.(data);\n        } catch (e) {\n            logger.error(\"Error starting recording: \", e);\n            if (e instanceof DOMException) {\n                // Unhelpful DOMExceptions are common - parse them sanely\n                logger.error(`${e.name} (${e.code}): ${e.message}`);\n            }\n\n            // Clean up as best as possible\n            if (this.recorderStream) this.recorderStream.getTracks().forEach((t) => t.stop());\n            if (this.recorderSource) this.recorderSource.disconnect();\n            if (this.recorder) this.recorder.close();\n            if (this.recorderContext) {\n                // noinspection ES6MissingAwait - not important that we wait\n                this.recorderContext.close();\n            }\n\n            throw e; // rethrow so upstream can handle it\n        }\n    }\n\n    public get liveData(): SimpleObservable<IRecordingUpdate> {\n        if (!this.recording || !this.observable) throw new Error(\"No observable when not recording\");\n        return this.observable;\n    }\n\n    public get isSupported(): boolean {\n        return !!Recorder.isRecordingSupported();\n    }\n\n    private onAudioProcess = (ev: AudioProcessingEvent): void => {\n        this.processAudioUpdate(ev.playbackTime);\n\n        // We skip the functionality of the worklet regarding waveform calculations: we\n        // should get that information pretty quick during the playback info.\n    };\n\n    private processAudioUpdate = (timeSeconds: number): void => {\n        if (!this.recording) return;\n\n        this.observable!.update({\n            waveform: this.liveWaveform.value.map((v) => clamp(v, 0, 1)),\n            timeSeconds: timeSeconds,\n        });\n\n        // Now that we've updated the data/waveform, let's do a time check. We don't want to\n        // go horribly over the limit. We also emit a warning state if needed.\n        //\n        // We use the recorder's perspective of time to make sure we don't cut off the last\n        // frame of audio, otherwise we end up with a 14:59 clip (899.68 seconds). This extra\n        // safety can allow us to overshoot the target a bit, but at least when we say 15min\n        // maximum we actually mean it.\n        //\n        // In testing, recorder time and worker time lag by about 400ms, which is roughly the\n        // time needed to encode a sample/frame.\n        //\n\n        if (!this.targetMaxLength) {\n            // skip time checks if max length has been disabled\n            return;\n        }\n\n        const secondsLeft = TARGET_MAX_LENGTH - this.recorderSeconds!;\n        if (secondsLeft < 0) {\n            // go over to make sure we definitely capture that last frame\n            // noinspection JSIgnoredPromiseFromCall - we aren't concerned with it overlapping\n            this.stop();\n        } else if (secondsLeft <= TARGET_WARN_TIME_LEFT) {\n            Singleflight.for(this, \"ending_soon\").do(() => {\n                this.emit(RecordingState.EndingSoon, { secondsLeft });\n                return Singleflight.Void;\n            });\n        }\n    };\n\n    /**\n     * {@link https://github.com/chris-rudmin/opus-recorder#instance-fields ref for recorderSeconds}\n     */\n    public get recorderSeconds(): number | undefined {\n        if (!this.recorder) return undefined;\n        return this.recorder.encodedSamplePosition / 48000;\n    }\n\n    public async start(): Promise<void> {\n        if (this.recording) {\n            throw new Error(\"Recording already in progress\");\n        }\n        if (this.observable) {\n            this.observable.close();\n        }\n        this.observable = new SimpleObservable<IRecordingUpdate>();\n        await this.makeRecorder();\n        await this.recorder?.start();\n        this.recording = true;\n        this.emit(RecordingState.Started);\n    }\n\n    public async stop(): Promise<void> {\n        return Singleflight.for(this, \"stop\").do(async (): Promise<void> => {\n            if (!this.recording) {\n                throw new Error(\"No recording to stop\");\n            }\n\n            // Disconnect the source early to start shutting down resources\n            await this.recorder!.stop(); // stop first to flush the last frame\n            this.recorderSource!.disconnect();\n            if (this.recorderWorklet) this.recorderWorklet.disconnect();\n            if (this.recorderProcessor) {\n                this.recorderProcessor.disconnect();\n                this.recorderProcessor.removeEventListener(\"audioprocess\", this.onAudioProcess);\n            }\n\n            // close the context after the recorder so the recorder doesn't try to\n            // connect anything to the context (this would generate a warning)\n            await this.recorderContext!.close();\n\n            // Now stop all the media tracks so we can release them back to the user/OS\n            this.recorderStream!.getTracks().forEach((t) => t.stop());\n\n            // Finally do our post-processing and clean up\n            this.recording = false;\n            await this.recorder!.close();\n            this.emit(RecordingState.Ended);\n        });\n    }\n\n    public destroy(): void {\n        // noinspection JSIgnoredPromiseFromCall - not concerned about stop() being called async here\n        this.stop();\n        this.removeAllListeners();\n        this.onDataAvailable = undefined;\n        Singleflight.forgetAllFor(this);\n        // noinspection JSIgnoredPromiseFromCall - not concerned about being called async here\n        this.observable?.close();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport mxRecorderWorkletPath from \"./RecorderWorklet\";\n\nexport default function recorderWorkletFactory(context: AudioContext): Promise<void> {\n    // In future we should be using the built-in worklet support in Webpack 5 with the syntax\n    // described in https://github.com/webpack/webpack.js.org/issues/6869:\n    // addModule(/* webpackChunkName: \"recorder.worklet\" */ new URL(\"./RecorderWorklet.ts\", import.meta.url));\n    return context.audioWorklet.addModule(mxRecorderWorkletPath);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// @ts-ignore - we know that this is not a module. We're looking for a path.\nimport decoderWasmPath from \"opus-recorder/dist/decoderWorker.min.wasm\";\nimport wavEncoderPath from \"opus-recorder/dist/waveWorker.min.js\";\nimport decoderPath from \"opus-recorder/dist/decoderWorker.min.js\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { SAMPLE_RATE } from \"./VoiceRecording\";\n\nexport function createAudioContext(opts?: AudioContextOptions): AudioContext {\n    if (window.AudioContext) {\n        const ctx = new AudioContext(opts);\n        // Initialize in suspended state, as Firefox starts using\n        // CPU/battery right away, even if we don't play any sound yet.\n        void ctx.suspend();\n        return ctx;\n    } else {\n        throw new Error(\"Unsupported browser\");\n    }\n}\n\nexport function decodeOgg(audioBuffer: ArrayBuffer): Promise<ArrayBuffer> {\n    // Condensed version of decoder example, using a promise:\n    // https://github.com/chris-rudmin/opus-recorder/blob/master/example/decoder.html\n    return new Promise((resolve) => {\n        // no reject because the workers don't seem to have a fail path\n        logger.log(\"Decoder WASM path: \" + decoderWasmPath); // so we use the variable (avoid tree shake)\n        const typedArray = new Uint8Array(audioBuffer);\n        const decoderWorker = new Worker(decoderPath);\n        const wavWorker = new Worker(wavEncoderPath);\n\n        decoderWorker.postMessage({\n            command: \"init\",\n            decoderSampleRate: SAMPLE_RATE,\n            outputBufferSampleRate: SAMPLE_RATE,\n        });\n\n        wavWorker.postMessage({\n            command: \"init\",\n            wavBitDepth: 24, // standard for 48khz (SAMPLE_RATE)\n            wavSampleRate: SAMPLE_RATE,\n        });\n\n        decoderWorker.onmessage = (ev) => {\n            if (ev.data === null) {\n                // null == done\n                wavWorker.postMessage({ command: \"done\" });\n                return;\n            }\n\n            wavWorker.postMessage(\n                {\n                    command: \"encode\",\n                    buffers: ev.data,\n                },\n                ev.data.map((b: Float32Array) => b.buffer),\n            );\n        };\n\n        wavWorker.onmessage = (ev) => {\n            if (ev.data.message === \"page\") {\n                // The encoding comes through as a single page\n                resolve(new Blob([ev.data.page], { type: \"audio/wav\" }).arrayBuffer());\n            }\n        };\n\n        decoderWorker.postMessage(\n            {\n                command: \"decode\",\n                pages: typedArray,\n            },\n            [typedArray.buffer],\n        );\n    });\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { arraySeed } from \"../utils/arrays\";\n\nexport const WORKLET_NAME = \"mx-voice-worklet\";\n\nexport enum PayloadEvent {\n    Timekeep = \"timekeep\",\n    AmplitudeMark = \"amplitude_mark\",\n}\n\nexport interface IPayload {\n    ev: PayloadEvent;\n}\n\nexport interface ITimingPayload extends IPayload {\n    ev: PayloadEvent.Timekeep;\n    timeSeconds: number;\n}\n\nexport interface IAmplitudePayload extends IPayload {\n    ev: PayloadEvent.AmplitudeMark;\n    forIndex: number;\n    amplitude: number;\n}\n\nexport const PLAYBACK_WAVEFORM_SAMPLES = 39;\nexport const DEFAULT_WAVEFORM = arraySeed(0, PLAYBACK_WAVEFORM_SAMPLES);\n","/*\nCopyright 2017-2024 New Vector Ltd.\nCopyright 2017 Vector Creations Ltd\nCopyright 2016 Aviral Dasgupta\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type React from \"react\";\nimport { TimelineRenderingType } from \"../contexts/RoomContext\";\nimport type { ICompletion, ISelectionRange } from \"./Autocompleter\";\n\nexport interface ICommand {\n    command: RegExpExecArray | null;\n    range: {\n        start: number;\n        end: number;\n    };\n}\n\nexport interface IAutocompleteOptions {\n    commandRegex?: RegExp;\n    forcedCommandRegex?: RegExp;\n    renderingType?: TimelineRenderingType;\n}\n\nexport default abstract class AutocompleteProvider {\n    public commandRegex?: RegExp;\n    public forcedCommandRegex?: RegExp;\n\n    protected renderingType: TimelineRenderingType = TimelineRenderingType.Room;\n\n    protected constructor({ commandRegex, forcedCommandRegex, renderingType }: IAutocompleteOptions) {\n        if (commandRegex) {\n            if (!commandRegex.global) {\n                throw new Error(\"commandRegex must have global flag set\");\n            }\n            this.commandRegex = commandRegex;\n        }\n        if (forcedCommandRegex) {\n            if (!forcedCommandRegex.global) {\n                throw new Error(\"forcedCommandRegex must have global flag set\");\n            }\n            this.forcedCommandRegex = forcedCommandRegex;\n        }\n        if (renderingType) {\n            this.renderingType = renderingType;\n        }\n    }\n\n    public destroy(): void {\n        // stub\n    }\n\n    /**\n     * Of the matched commands in the query, returns the first that contains or is contained by the selection, or null.\n     * @param {string} query The query string\n     * @param {ISelectionRange} selection Selection to search\n     * @param {boolean} force True if the user is forcing completion\n     * @return {object} { command, range } where both objects fields are null if no match\n     */\n    public getCurrentCommand(query: string, selection: ISelectionRange, force = false): Partial<ICommand> {\n        let commandRegex = this.commandRegex;\n\n        if (force && this.shouldForceComplete()) {\n            commandRegex = this.forcedCommandRegex || /\\S+/g;\n        }\n\n        if (!commandRegex) {\n            return {};\n        }\n\n        commandRegex.lastIndex = 0;\n\n        let match: RegExpExecArray | null;\n        while ((match = commandRegex.exec(query)) !== null) {\n            const start = match.index;\n            const end = start + match[0].length;\n            if (selection.start <= end && selection.end >= start) {\n                return {\n                    command: match,\n                    range: {\n                        start,\n                        end,\n                    },\n                };\n            }\n        }\n        return {\n            command: null,\n            range: {\n                start: -1,\n                end: -1,\n            },\n        };\n    }\n\n    public abstract getCompletions(\n        query: string,\n        selection: ISelectionRange,\n        force: boolean,\n        limit: number,\n    ): Promise<ICompletion[]>;\n\n    public abstract getName(): string;\n\n    public abstract renderCompletions(completions: React.ReactNode[]): React.ReactNode | null;\n\n    // Whether we should provide completions even if triggered forcefully, without a sigil.\n    public shouldForceComplete(): boolean {\n        return false;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2017 Vector Creations Ltd\nCopyright 2017 New Vector Ltd\nCopyright 2016 Aviral Dasgupta\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../languageHandler\";\nimport AutocompleteProvider from \"./AutocompleteProvider\";\nimport QueryMatcher from \"./QueryMatcher\";\nimport { TextualCompletion } from \"./Components\";\nimport { type ICompletion, type ISelectionRange } from \"./Autocompleter\";\nimport { type Command, Commands, CommandMap } from \"../slash-commands/SlashCommands\";\nimport { type TimelineRenderingType } from \"../contexts/RoomContext\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\n\nconst COMMAND_RE = /(^\\/\\w*)(?: .*)?/g;\n\nexport default class CommandProvider extends AutocompleteProvider {\n    public matcher: QueryMatcher<Command>;\n    private room: Room;\n    public constructor(room: Room, renderingType?: TimelineRenderingType) {\n        super({ commandRegex: COMMAND_RE, renderingType });\n        this.matcher = new QueryMatcher(Commands, {\n            keys: [\"command\", \"args\", \"description\"],\n            funcs: [({ aliases }) => aliases.join(\" \")], // aliases\n            context: renderingType,\n        });\n        this.room = room;\n    }\n\n    public async getCompletions(\n        query: string,\n        selection: ISelectionRange,\n        force?: boolean,\n        limit = -1,\n    ): Promise<ICompletion[]> {\n        const { command, range } = this.getCurrentCommand(query, selection);\n        if (!command) return [];\n\n        const cli = MatrixClientPeg.get();\n\n        let matches: Command[] = [];\n        // check if the full match differs from the first word (i.e. returns false if the command has args)\n        if (command[0] !== command[1]) {\n            // The input looks like a command with arguments, perform exact match\n            const name = command[1].slice(1); // strip leading `/`\n            if (CommandMap.has(name) && CommandMap.get(name)!.isEnabled(cli, this.room.roomId)) {\n                // some commands, namely `me` don't suit having the usage shown whilst typing their arguments\n                if (CommandMap.get(name)!.hideCompletionAfterSpace) return [];\n                matches = [CommandMap.get(name)!];\n            }\n        } else {\n            if (query === \"/\") {\n                // If they have just entered `/` show everything\n                // We exclude the limit on purpose to have a comprehensive list\n                matches = Commands;\n            } else {\n                // otherwise fuzzy match against all of the fields\n                matches = this.matcher.match(command[1], limit);\n            }\n        }\n\n        return matches\n            .filter((cmd) => {\n                const display = !cmd.renderingTypes || cmd.renderingTypes.includes(this.renderingType);\n                return cmd.isEnabled(cli, this.room.roomId) && display;\n            })\n            .map((result) => {\n                let completion = result.getCommand() + \" \";\n                const usedAlias = result.aliases.find((alias) => `/${alias}` === command[1]);\n                // If the command (or an alias) is the same as the one they entered, we don't want to discard their arguments\n                if (usedAlias || result.getCommand() === command[1]) {\n                    completion = command[0];\n                }\n\n                return {\n                    completion,\n                    type: \"command\",\n                    component: (\n                        <TextualCompletion\n                            title={`/${usedAlias || result.command}`}\n                            subtitle={result.args}\n                            description={_t(result.description)}\n                        />\n                    ),\n                    range: range!,\n                };\n            });\n    }\n\n    public getName(): string {\n        return \"*️⃣ \" + _t(\"composer|autocomplete|command_description\");\n    }\n\n    public renderCompletions(completions: React.ReactNode[]): React.ReactNode {\n        return (\n            <div\n                className=\"mx_Autocomplete_Completion_container_pill\"\n                role=\"presentation\"\n                aria-label={_t(\"composer|autocomplete|command_a11y\")}\n            >\n                {completions}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2016 Aviral Dasgupta\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type Ref, type JSX } from \"react\";\nimport classNames from \"classnames\";\n\n/* These were earlier stateless functional components but had to be converted\nsince we need to use refs/findDOMNode to access the underlying DOM node to focus the correct completion,\nsomething that is not entirely possible with stateless functional components. One could\npresumably wrap them in a <div> before rendering but I think this is the better way to do it.\n */\n\ninterface ITextualCompletionProps {\n    \"title\"?: string;\n    \"subtitle\"?: string;\n    \"description\"?: string;\n    \"className\"?: string;\n    \"aria-selected\"?: boolean;\n    \"ref\"?: Ref<HTMLDivElement>;\n}\n\nexport const TextualCompletion = (props: ITextualCompletionProps): JSX.Element => {\n    const {\n        title,\n        subtitle,\n        description,\n        className,\n        \"aria-selected\": ariaSelectedAttribute,\n        ref,\n        ...restProps\n    } = props;\n    return (\n        <div\n            {...restProps}\n            className={classNames(\"mx_Autocomplete_Completion_block\", className)}\n            role=\"option\"\n            aria-selected={ariaSelectedAttribute}\n            ref={ref}\n        >\n            <span className=\"mx_Autocomplete_Completion_title\">{title}</span>\n            <span className=\"mx_Autocomplete_Completion_subtitle\">{subtitle}</span>\n            <span className=\"mx_Autocomplete_Completion_description\">{description}</span>\n        </div>\n    );\n};\n\ninterface IPillCompletionProps extends ITextualCompletionProps {\n    children?: React.ReactNode;\n}\n\nexport const PillCompletion = (props: IPillCompletionProps): JSX.Element => {\n    const {\n        title,\n        subtitle,\n        description,\n        className,\n        children,\n        \"aria-selected\": ariaSelectedAttribute,\n        ref,\n        ...restProps\n    } = props;\n    return (\n        <div\n            {...restProps}\n            className={classNames(\"mx_Autocomplete_Completion_pill\", className)}\n            role=\"option\"\n            aria-selected={ariaSelectedAttribute}\n            ref={ref}\n        >\n            {children}\n            <span className=\"mx_Autocomplete_Completion_title\">{title}</span>\n            <span className=\"mx_Autocomplete_Completion_subtitle\">{subtitle}</span>\n            <span className=\"mx_Autocomplete_Completion_description\">{description}</span>\n        </div>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2018 New Vector Ltd\nCopyright 2017 Aviral Dasgupta\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { at, uniq } from \"lodash\";\nimport { removeHiddenChars } from \"matrix-js-sdk/src/utils\";\n\nimport { type TimelineRenderingType } from \"../contexts/RoomContext\";\nimport { type Leaves } from \"../@types/common\";\n\ninterface IOptions<T extends object> {\n    keys: Array<Leaves<T>>;\n    funcs?: Array<(o: T) => string | string[]>;\n    shouldMatchWordsOnly?: boolean;\n    // whether to apply unhomoglyph and strip diacritics to fuzz up the search. Defaults to true\n    fuzzy?: boolean;\n    context?: TimelineRenderingType;\n}\n\n/**\n * Simple search matcher that matches any results with the query string anywhere\n * in the search string. Returns matches in the order the query string appears\n * in the search key, earliest first, then in the order the search key appears\n * in the provided array of keys, then in the order the items appeared in the\n * source array.\n *\n * @param {Object[]} objects Initial list of objects. Equivalent to calling\n *     setObjects() after construction\n * @param {Object} options Options object\n * @param {string[]} options.keys List of keys to use as indexes on the objects\n * @param {function[]} options.funcs List of functions that when called with the\n *     object as an arg will return a string to use as an index\n */\nexport default class QueryMatcher<T extends object> {\n    private _options: IOptions<T>;\n    private _items = new Map<string, { object: T; keyWeight: number }[]>();\n\n    public constructor(objects: T[], options: IOptions<T> = { keys: [] }) {\n        this._options = options;\n\n        this.setObjects(objects);\n\n        // By default, we remove any non-alphanumeric characters ([^A-Za-z0-9_]) from the\n        // query and the value being queried before matching\n        if (this._options.shouldMatchWordsOnly === undefined) {\n            this._options.shouldMatchWordsOnly = true;\n        }\n    }\n\n    public setObjects(objects: T[]): void {\n        this._items = new Map();\n\n        for (const object of objects) {\n            // Need to use unsafe coerce here because the objects can have any\n            // type for their values. We assume that those values who's keys have\n            // been specified will be string. Also, we cannot infer all the\n            // types of the keys of the objects at compile.\n            const keyValues = at<string>(<any>object, this._options.keys);\n\n            if (this._options.funcs) {\n                for (const f of this._options.funcs) {\n                    const v = f(object);\n                    if (Array.isArray(v)) {\n                        keyValues.push(...v);\n                    } else {\n                        keyValues.push(v);\n                    }\n                }\n            }\n\n            for (const [index, keyValue] of Object.entries(keyValues)) {\n                if (!keyValue) continue; // skip falsy keyValues\n                const key = this.processQuery(keyValue);\n                if (!this._items.has(key)) {\n                    this._items.set(key, []);\n                }\n                this._items.get(key)!.push({\n                    keyWeight: Number(index),\n                    object,\n                });\n            }\n        }\n    }\n\n    public match(query: string, limit = -1): T[] {\n        query = this.processQuery(query);\n        if (this._options.shouldMatchWordsOnly) {\n            query = query.replace(/[^\\w]/g, \"\");\n        }\n        if (query.length === 0) {\n            return [];\n        }\n        const matches: {\n            index: number;\n            object: T;\n            keyWeight: number;\n        }[] = [];\n        // Iterate through the map & check each key.\n        // ES6 Map iteration order is defined to be insertion order, so results\n        // here will come out in the order they were put in.\n        for (const [key, candidates] of this._items.entries()) {\n            let resultKey = key;\n            if (this._options.shouldMatchWordsOnly) {\n                resultKey = resultKey.replace(/[^\\w]/g, \"\");\n            }\n            const index = resultKey.indexOf(query);\n            if (index !== -1) {\n                matches.push(...candidates.map((candidate) => ({ index, ...candidate })));\n            }\n        }\n\n        // Sort matches by where the query appeared in the search key, then by\n        // where the matched key appeared in the provided array of keys.\n        matches.sort((a, b) => {\n            if (a.index < b.index) {\n                return -1;\n            } else if (a.index === b.index) {\n                if (a.keyWeight < b.keyWeight) {\n                    return -1;\n                } else if (a.keyWeight === b.keyWeight) {\n                    return 0;\n                }\n            }\n\n            return 1;\n        });\n\n        // Now map the keys to the result objects. Also remove any duplicates.\n        const dedupped = uniq(matches.map((match) => match.object));\n        const maxLength = limit === -1 ? dedupped.length : limit;\n\n        return dedupped.slice(0, maxLength);\n    }\n\n    private processQuery(query: string): string {\n        if (this._options.fuzzy !== false) {\n            // lower case both the input and the output for consistency\n            return removeHiddenChars(query.toLowerCase()).toLowerCase();\n        }\n        return query.toLowerCase();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2017, 2018 New Vector Ltd\nCopyright 2017 Vector Creations Ltd\nCopyright 2016 Aviral Dasgupta\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { sortBy } from \"lodash\";\nimport {\n    type MatrixEvent,\n    type Room,\n    RoomEvent,\n    type RoomMember,\n    type RoomState,\n    RoomStateEvent,\n    type IRoomTimelineData,\n} from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport QueryMatcher from \"./QueryMatcher\";\nimport { PillCompletion } from \"./Components\";\nimport AutocompleteProvider from \"./AutocompleteProvider\";\nimport { _t } from \"../languageHandler\";\nimport { makeUserPermalink } from \"../utils/permalinks/Permalinks\";\nimport { type ICompletion, type ISelectionRange } from \"./Autocompleter\";\nimport MemberAvatar from \"../components/views/avatars/MemberAvatar\";\nimport { type TimelineRenderingType } from \"../contexts/RoomContext\";\nimport UserIdentifierCustomisations from \"../customisations/UserIdentifier\";\n\nconst USER_REGEX = /\\B@\\S*/g;\n\n// used when you hit 'tab' - we allow some separator chars at the beginning\n// to allow you to tab-complete /mat into /(matthew)\nconst FORCED_USER_REGEX = /[^/,.():; \\t\\n]\\S*/g;\n\nexport default class UserProvider extends AutocompleteProvider {\n    public matcher: QueryMatcher<RoomMember>;\n    public users?: RoomMember[];\n    public room: Room;\n\n    public constructor(room: Room, renderingType?: TimelineRenderingType) {\n        super({\n            commandRegex: USER_REGEX,\n            forcedCommandRegex: FORCED_USER_REGEX,\n            renderingType,\n        });\n        this.room = room;\n        this.matcher = new QueryMatcher<RoomMember>([], {\n            keys: [\"name\"],\n            funcs: [(obj) => obj.userId.slice(1)], // index by user id minus the leading '@'\n            shouldMatchWordsOnly: false,\n        });\n\n        MatrixClientPeg.safeGet().on(RoomEvent.Timeline, this.onRoomTimeline);\n        MatrixClientPeg.safeGet().on(RoomStateEvent.Update, this.onRoomStateUpdate);\n    }\n\n    public destroy(): void {\n        MatrixClientPeg.get()?.removeListener(RoomEvent.Timeline, this.onRoomTimeline);\n        MatrixClientPeg.get()?.removeListener(RoomStateEvent.Update, this.onRoomStateUpdate);\n    }\n\n    private onRoomTimeline = (\n        ev: MatrixEvent,\n        room: Room | undefined,\n        toStartOfTimeline: boolean | undefined,\n        removed: boolean,\n        data: IRoomTimelineData,\n    ): void => {\n        if (!room) return; // notification timeline, we'll get this event again with a room specific timeline\n        if (removed) return;\n        if (room.roomId !== this.room.roomId) return;\n\n        // ignore events from filtered timelines\n        if (data.timeline.getTimelineSet() !== room.getUnfilteredTimelineSet()) return;\n\n        // ignore anything but real-time updates at the end of the room:\n        // updates from pagination will happen when the paginate completes.\n        if (toStartOfTimeline || !data || !data.liveEvent) return;\n\n        // TODO: lazyload if we have no ev.sender room member?\n        this.onUserSpoke(ev.sender);\n    };\n\n    private onRoomStateUpdate = (state: RoomState): void => {\n        // ignore updates in other rooms\n        if (state.roomId !== this.room.roomId) return;\n\n        // blow away the users cache\n        this.users = undefined;\n    };\n\n    public async getCompletions(\n        rawQuery: string,\n        selection: ISelectionRange,\n        force = false,\n        limit = -1,\n    ): Promise<ICompletion[]> {\n        // lazy-load user list into matcher\n        if (!this.users) this.makeUsers();\n\n        const { command, range } = this.getCurrentCommand(rawQuery, selection, force);\n\n        const fullMatch = command?.[0];\n        // Don't search if the query is a single \"@\"\n        if (fullMatch && fullMatch !== \"@\") {\n            // Don't include the '@' in our search query - it's only used as a way to trigger completion\n            const query = fullMatch.startsWith(\"@\") ? fullMatch.substring(1) : fullMatch;\n            return this.matcher.match(query, limit).map((user) => {\n                const description = UserIdentifierCustomisations.getDisplayUserIdentifier?.(user.userId, {\n                    roomId: this.room.roomId,\n                    withDisplayName: true,\n                });\n                const displayName = user.name || user.userId || \"\";\n                return {\n                    // Length of completion should equal length of text in decorator. draft-js\n                    // relies on the length of the entity === length of the text in the decoration.\n                    completion: user.rawDisplayName,\n                    completionId: user.userId,\n                    type: \"user\",\n                    suffix: selection.beginning && range!.start === 0 ? \": \" : \" \",\n                    href: makeUserPermalink(user.userId),\n                    component: (\n                        <PillCompletion title={displayName} description={description ?? undefined}>\n                            <MemberAvatar member={user} size=\"24px\" />\n                        </PillCompletion>\n                    ),\n                    range: range!,\n                };\n            });\n        }\n        return [];\n    }\n\n    public getName(): string {\n        return _t(\"composer|autocomplete|user_description\");\n    }\n\n    private makeUsers(): void {\n        const events = this.room.getLiveTimeline().getEvents();\n        const lastSpoken: Record<string, number> = {};\n\n        for (const event of events) {\n            lastSpoken[event.getSender()!] = event.getTs();\n        }\n\n        const currentUserId = MatrixClientPeg.safeGet().credentials.userId;\n        this.users = this.room.getJoinedMembers().filter(({ userId }) => userId !== currentUserId);\n        this.users = this.users.concat(this.room.getMembersWithMembership(KnownMembership.Invite));\n\n        this.users = sortBy(this.users, (member) => 1e20 - lastSpoken[member.userId] || 1e20);\n\n        this.matcher.setObjects(this.users);\n    }\n\n    public onUserSpoke(user: RoomMember | null): void {\n        if (!this.users) return;\n        if (!user) return;\n        if (user.userId === MatrixClientPeg.safeGet().getSafeUserId()) return;\n\n        // Move the user that spoke to the front of the array\n        this.users.splice(\n            this.users.findIndex((user2) => user2.userId === user.userId),\n            1,\n        );\n        this.users = [user, ...this.users];\n\n        this.matcher.setObjects(this.users);\n    }\n\n    public renderCompletions(completions: React.ReactNode[]): React.ReactNode {\n        return (\n            <div\n                className=\"mx_Autocomplete_Completion_container_pill\"\n                role=\"presentation\"\n                aria-label={_t(\"composer|autocomplete|user_a11y\")}\n            >\n                {completions}\n            </div>\n        );\n    }\n\n    public shouldForceComplete(): boolean {\n        return true;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EventType } from \"matrix-js-sdk/src/matrix\";\nimport { NamespacedValue } from \"matrix-js-sdk/src/NamespacedValue\";\n\nexport const JitsiCallMemberEventType = \"io.element.video.member\";\n\nexport interface JitsiCallMemberContent {\n    // Connected device IDs\n    devices: string[];\n    // Time at which this state event should be considered stale\n    expires_ts: number;\n}\n\n// Element Call no longer sends this event type; it only exists to support timeline rendering of\n// group calls from a previous iteration of the group VoIP MSCs (MSC3401) which used it.\nexport const ElementCallEventType = new NamespacedValue(null, EventType.GroupCallPrefix);\n\nexport const ElementCallMemberEventType = new NamespacedValue(null, EventType.GroupCallMemberPrefix);\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport classNames from \"classnames\";\nimport React, { type HTMLAttributes, type JSX, type ReactNode, type WheelEvent } from \"react\";\n\ntype DynamicHtmlElementProps<T extends keyof JSX.IntrinsicElements> =\n    JSX.IntrinsicElements[T] extends HTMLAttributes<object> ? DynamicElementProps<T> : DynamicElementProps<\"div\">;\ntype DynamicElementProps<T extends keyof JSX.IntrinsicElements> = Partial<Omit<JSX.IntrinsicElements[T], \"ref\">>;\n\nexport type IProps<T extends keyof JSX.IntrinsicElements> = Omit<DynamicHtmlElementProps<T>, \"onScroll\"> & {\n    element: T;\n    className?: string;\n    onScroll?: (event: Event) => void;\n    onWheel?: (event: WheelEvent) => void;\n    style?: React.CSSProperties;\n    tabIndex?: number;\n    wrappedRef?: (ref: HTMLDivElement | null) => void;\n    children: ReactNode;\n};\n\nexport default class AutoHideScrollbar<T extends keyof JSX.IntrinsicElements> extends React.Component<IProps<T>> {\n    public static defaultProps = {\n        element: \"div\" as keyof HTMLElementTagNameMap,\n    };\n\n    public readonly containerRef = React.createRef<HTMLDivElement>();\n\n    public componentDidMount(): void {\n        if (this.containerRef.current && this.props.onScroll) {\n            // Using the passive option to not block the main thread\n            // https://developer.mozilla.org/en-US/docs/Web/API/EventTarget/addEventListener#improving_scrolling_performance_with_passive_listeners\n            this.containerRef.current.addEventListener(\"scroll\", this.props.onScroll, { passive: true });\n        }\n\n        this.props.wrappedRef?.(this.containerRef.current);\n    }\n\n    public componentWillUnmount(): void {\n        if (this.containerRef.current && this.props.onScroll) {\n            this.containerRef.current.removeEventListener(\"scroll\", this.props.onScroll);\n        }\n\n        this.props.wrappedRef?.(null);\n    }\n\n    public render(): React.ReactNode {\n        // eslint-disable-next-line @typescript-eslint/no-unused-vars\n        const { element, className, onScroll, tabIndex, wrappedRef, children, ...otherProps } = this.props;\n\n        return React.createElement(\n            element,\n            {\n                ...otherProps,\n                ref: this.containerRef,\n                className: classNames(\"mx_AutoHideScrollbar\", className),\n                // Firefox sometimes makes this element focusable due to\n                // overflow:scroll;, so force it out of tab order by default.\n                tabIndex: tabIndex ?? -1,\n            },\n            children,\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { RovingAccessibleButton } from \"../RovingTabIndex\";\n\ninterface IProps extends React.ComponentProps<typeof RovingAccessibleButton> {\n    label?: string;\n}\n\n// Semantic component for representing a role=menuitem\nexport const MenuItem: React.FC<IProps> = ({ children, label, ...props }) => {\n    const ariaLabel = props[\"aria-label\"] || label;\n\n    return (\n        <RovingAccessibleButton {...props} role=\"menuitem\" aria-label={ariaLabel}>\n            {children}\n        </RovingAccessibleButton>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { RovingAccessibleButton } from \"../RovingTabIndex\";\n\ninterface IProps extends React.ComponentProps<typeof RovingAccessibleButton> {\n    label?: string;\n    active: boolean;\n}\n\n// Semantic component for representing a role=menuitemcheckbox\nexport const MenuItemCheckbox: React.FC<IProps> = ({ children, label, active, disabled, ...props }) => {\n    return (\n        <RovingAccessibleButton\n            {...props}\n            role=\"menuitemcheckbox\"\n            aria-checked={active}\n            aria-disabled={disabled}\n            disabled={disabled}\n            aria-label={label}\n        >\n            {children}\n        </RovingAccessibleButton>\n    );\n};\n","/*\nCopyright 2024,2025 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { useRovingTabIndex } from \"../RovingTabIndex\";\nimport StyledCheckbox from \"../../components/views/elements/StyledCheckbox\";\nimport { KeyBindingAction } from \"../KeyboardShortcuts\";\nimport { getKeyBindingsManager } from \"../../KeyBindingsManager\";\n\ninterface IProps extends React.ComponentProps<typeof StyledCheckbox> {\n    onChange(): void; // we handle keyup/down ourselves so lose the ChangeEvent\n    onClose(): void; // gets called after onChange on KeyBindingAction.ActivateSelectedButton\n}\n\n// Semantic component for representing a styled role=menuitemcheckbox\nexport const StyledMenuItemCheckbox: React.FC<IProps> = ({ children, onChange, onClose, ...props }) => {\n    const [onFocus, isActive, ref] = useRovingTabIndex<HTMLInputElement>();\n\n    const onKeyDown = (e: React.KeyboardEvent): void => {\n        let handled = true;\n        const action = getKeyBindingsManager().getAccessibilityAction(e);\n\n        switch (action) {\n            case KeyBindingAction.Space:\n                onChange();\n                break;\n            case KeyBindingAction.Enter:\n                onChange();\n                // Implements https://www.w3.org/TR/wai-aria-practices/#keyboard-interaction-12\n                onClose();\n                break;\n            default:\n                handled = false;\n        }\n\n        if (handled) {\n            e.stopPropagation();\n            e.preventDefault();\n        }\n    };\n    const onKeyUp = (e: React.KeyboardEvent): void => {\n        const action = getKeyBindingsManager().getAccessibilityAction(e);\n        switch (action) {\n            case KeyBindingAction.Space:\n            case KeyBindingAction.Enter:\n                // prevent the input default handler as we handle it on keydown to match\n                // https://www.w3.org/TR/wai-aria-practices/examples/menubar/menubar-2/menubar-2.html\n                e.stopPropagation();\n                e.preventDefault();\n                break;\n        }\n    };\n    return (\n        <StyledCheckbox\n            {...props}\n            role=\"menuitemcheckbox\"\n            onChange={onChange}\n            onKeyDown={onKeyDown}\n            onKeyUp={onKeyUp}\n            onFocus={onFocus}\n            inputRef={ref}\n            tabIndex={isActive ? 0 : -1}\n        >\n            {children}\n        </StyledCheckbox>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { useRovingTabIndex } from \"../RovingTabIndex\";\nimport StyledRadioButton from \"../../components/views/elements/StyledRadioButton\";\nimport { KeyBindingAction } from \"../KeyboardShortcuts\";\nimport { getKeyBindingsManager } from \"../../KeyBindingsManager\";\n\ninterface IProps extends React.ComponentProps<typeof StyledRadioButton> {\n    label?: string;\n    onChange(): void; // we handle keyup/down ourselves so lose the ChangeEvent\n    onClose(): void; // gets called after onChange on KeyBindingAction.Enter\n}\n\n// Semantic component for representing a styled role=menuitemradio\nexport const StyledMenuItemRadio: React.FC<IProps> = ({ children, label, onChange, onClose, ...props }) => {\n    const [onFocus, isActive, ref] = useRovingTabIndex<HTMLInputElement>();\n\n    const onKeyDown = (e: React.KeyboardEvent): void => {\n        let handled = true;\n        const action = getKeyBindingsManager().getAccessibilityAction(e);\n\n        switch (action) {\n            case KeyBindingAction.Space:\n                onChange();\n                break;\n            case KeyBindingAction.Enter:\n                onChange();\n                // Implements https://www.w3.org/TR/wai-aria-practices/#keyboard-interaction-12\n                onClose();\n                break;\n            default:\n                handled = false;\n        }\n\n        if (handled) {\n            e.stopPropagation();\n            e.preventDefault();\n        }\n    };\n    const onKeyUp = (e: React.KeyboardEvent): void => {\n        const action = getKeyBindingsManager().getAccessibilityAction(e);\n        switch (action) {\n            case KeyBindingAction.Enter:\n            case KeyBindingAction.Space:\n                // prevent the input default handler as we handle it on keydown to match\n                // https://www.w3.org/TR/wai-aria-practices/examples/menubar/menubar-2/menubar-2.html\n                e.stopPropagation();\n                e.preventDefault();\n                break;\n        }\n    };\n    return (\n        <StyledRadioButton\n            {...props}\n            role=\"menuitemradio\"\n            aria-label={label}\n            onChange={onChange}\n            onKeyDown={onKeyDown}\n            onKeyUp={onKeyUp}\n            onFocus={onFocus}\n            inputRef={ref}\n            tabIndex={isActive ? 0 : -1}\n        >\n            {children}\n        </StyledRadioButton>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type CSSProperties, type RefObject, type SyntheticEvent, useRef, useState } from \"react\";\nimport ReactDOM from \"react-dom\";\nimport classNames from \"classnames\";\nimport FocusLock from \"react-focus-lock\";\nimport { TooltipProvider } from \"@vector-im/compound-web\";\n\nimport { type Writeable } from \"../../@types/common\";\nimport UIStore from \"../../stores/UIStore\";\nimport { checkInputableElement, RovingTabIndexProvider } from \"../../accessibility/RovingTabIndex\";\nimport { KeyBindingAction } from \"../../accessibility/KeyboardShortcuts\";\nimport { getKeyBindingsManager } from \"../../KeyBindingsManager\";\nimport Modal, { ModalManagerEvent } from \"../../Modal\";\n\n// Shamelessly ripped off Modal.js.  There's probably a better way\n// of doing reusable widgets like dialog boxes & menus where we go and\n// pass in a custom control as the actual body.\n\nconst WINDOW_PADDING = 10;\nconst ContextualMenuContainerId = \"mx_ContextualMenu_Container\";\n\nfunction getOrCreateContainer(): HTMLDivElement {\n    let container = document.getElementById(ContextualMenuContainerId) as HTMLDivElement;\n\n    if (!container) {\n        container = document.createElement(\"div\");\n        container.id = ContextualMenuContainerId;\n        document.body.appendChild(container);\n    }\n\n    return container;\n}\n\nexport interface IPosition {\n    top?: number;\n    bottom?: number;\n    left?: number;\n    right?: number;\n    rightAligned?: boolean;\n    bottomAligned?: boolean;\n}\n\nexport enum ChevronFace {\n    Top = \"top\",\n    Bottom = \"bottom\",\n    Left = \"left\",\n    Right = \"right\",\n    None = \"none\",\n}\n\nexport interface MenuProps extends IPosition {\n    menuWidth?: number;\n    menuHeight?: number;\n\n    chevronOffset?: number;\n    chevronFace?: ChevronFace;\n\n    menuPaddingTop?: number;\n    menuPaddingBottom?: number;\n    menuPaddingLeft?: number;\n    menuPaddingRight?: number;\n\n    zIndex?: number;\n}\n\nexport interface IProps extends MenuProps {\n    // If true, insert an invisible screen-sized element behind the menu that when clicked will close it.\n    hasBackground?: boolean;\n    // whether this context menu should be focus managed. If false it must handle itself\n    managed?: boolean;\n    wrapperClassName?: string;\n    menuClassName?: string;\n\n    // If true, this context menu will be mounted as a child to the parent container. Otherwise\n    // it will be mounted to a container at the root of the DOM.\n    mountAsChild?: boolean;\n\n    // If specified, contents will be wrapped in a FocusLock, this is only needed if the context menu is being rendered\n    // within an existing FocusLock e.g inside a modal.\n    focusLock?: boolean;\n\n    // call onFinished on any interaction with the menu\n    closeOnInteraction?: boolean;\n\n    // Function to be called on menu close\n    onFinished(): void;\n    // on resize callback\n    windowResize?(): void;\n}\n\ninterface IState {\n    contextMenuElem?: HTMLDivElement;\n}\n\n// Generic ContextMenu Portal wrapper\n// all options inside the menu should be of role=menuitem/menuitemcheckbox/menuitemradiobutton and have tabIndex={-1}\n// this will allow the ContextMenu to manage its own focus using arrow keys as per the ARIA guidelines.\nexport default class ContextMenu extends React.PureComponent<React.PropsWithChildren<IProps>, IState> {\n    private readonly initialFocus: HTMLElement;\n\n    public static defaultProps = {\n        hasBackground: true,\n        managed: true,\n    };\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {};\n\n        // persist what had focus when we got initialized so we can return it after\n        this.initialFocus = document.activeElement as HTMLElement;\n    }\n\n    public componentDidMount(): void {\n        Modal.on(ModalManagerEvent.Opened, this.onModalOpen);\n    }\n\n    public componentWillUnmount(): void {\n        Modal.off(ModalManagerEvent.Opened, this.onModalOpen);\n        // return focus to the thing which had it before us\n        this.initialFocus.focus();\n    }\n\n    private onModalOpen = (): void => {\n        this.props.onFinished?.();\n    };\n\n    private collectContextMenuRect = (element: HTMLDivElement): void => {\n        // We don't need to clean up when unmounting, so ignore\n        if (!element) return;\n\n        const first =\n            element.querySelector<HTMLElement>('[role^=\"menuitem\"]') ||\n            element.querySelector<HTMLElement>(\"[tabindex]\");\n\n        if (first) {\n            first.focus();\n        }\n\n        this.setState({\n            contextMenuElem: element,\n        });\n    };\n\n    private onContextMenu = (e: React.MouseEvent): void => {\n        if (this.props.onFinished) {\n            this.props.onFinished();\n\n            e.preventDefault();\n            e.stopPropagation();\n            const x = e.clientX;\n            const y = e.clientY;\n\n            // XXX: This isn't pretty but the only way to allow opening a different context menu on right click whilst\n            // a context menu and its click-guard are up without completely rewriting how the context menus work.\n            setTimeout(() => {\n                const clickEvent = new MouseEvent(\"contextmenu\", {\n                    clientX: x,\n                    clientY: y,\n                    screenX: 0,\n                    screenY: 0,\n                    button: 0, // Left\n                    relatedTarget: null,\n                });\n                document.elementFromPoint(x, y)?.dispatchEvent(clickEvent);\n            }, 0);\n        }\n    };\n\n    private onContextMenuPreventBubbling = (e: React.MouseEvent): void => {\n        // stop propagation so that any context menu handlers don't leak out of this context menu\n        // but do not inhibit the default browser menu\n        e.stopPropagation();\n    };\n\n    // Prevent clicks on the background from going through to the component which opened the menu.\n    private onFinished = (ev: React.MouseEvent): void => {\n        ev.stopPropagation();\n        ev.preventDefault();\n        this.props.onFinished?.();\n    };\n\n    private onClick = (ev: React.MouseEvent): void => {\n        // Don't allow clicks to escape the context menu wrapper\n        ev.stopPropagation();\n\n        if (this.props.closeOnInteraction) {\n            this.props.onFinished?.();\n        }\n    };\n\n    // We now only handle closing the ContextMenu in this keyDown handler.\n    // All of the item/option navigation is delegated to RovingTabIndex.\n    private onKeyDown = (ev: React.KeyboardEvent): void => {\n        ev.stopPropagation(); // prevent keyboard propagating out of the context menu, we're focus-locked\n\n        const action = getKeyBindingsManager().getAccessibilityAction(ev);\n\n        // If someone is managing their own focus, we will only exit for them with Escape.\n        // They are probably using props.focusLock along with this option as well.\n        if (!this.props.managed) {\n            if (action === KeyBindingAction.Escape) {\n                this.props.onFinished();\n            }\n            return;\n        }\n\n        // When an <input> is focused, only handle the Escape key\n        if (checkInputableElement(ev.target as HTMLElement) && action !== KeyBindingAction.Escape) {\n            return;\n        }\n\n        if (\n            [\n                KeyBindingAction.Escape,\n                // You can only navigate the ContextMenu by arrow keys and Home/End (see RovingTabIndex).\n                // Tabbing to the next section of the page, will close the ContextMenu.\n                KeyBindingAction.Tab,\n                // When someone moves left or right along a <Toolbar /> (like the\n                // MessageActionBar), we should close any ContextMenu that is open.\n                KeyBindingAction.ArrowLeft,\n                KeyBindingAction.ArrowRight,\n            ].includes(action!)\n        ) {\n            this.props.onFinished();\n        }\n    };\n\n    protected renderMenu(hasBackground = this.props.hasBackground): JSX.Element {\n        const position: Partial<Writeable<DOMRect>> = {};\n        const {\n            top,\n            bottom,\n            left,\n            right,\n            bottomAligned,\n            rightAligned,\n            menuClassName,\n            menuHeight,\n            menuWidth,\n            menuPaddingLeft,\n            menuPaddingRight,\n            menuPaddingBottom,\n            menuPaddingTop,\n            zIndex,\n            children,\n            focusLock,\n            managed,\n            wrapperClassName,\n            chevronFace: propsChevronFace,\n            chevronOffset: propsChevronOffset,\n            mountAsChild,\n            ...props\n        } = this.props;\n\n        if (top) {\n            position.top = top;\n        } else {\n            position.bottom = bottom;\n        }\n\n        let chevronFace: ChevronFace;\n        if (left) {\n            position.left = left;\n            chevronFace = ChevronFace.Left;\n        } else {\n            position.right = right;\n            chevronFace = ChevronFace.Right;\n        }\n\n        const contextMenuRect = this.state.contextMenuElem ? this.state.contextMenuElem.getBoundingClientRect() : null;\n\n        const chevronOffset: CSSProperties = {};\n        if (propsChevronFace) {\n            chevronFace = propsChevronFace;\n        }\n        const hasChevron = chevronFace && chevronFace !== ChevronFace.None;\n\n        if (chevronFace === ChevronFace.Top || chevronFace === ChevronFace.Bottom) {\n            chevronOffset.left = propsChevronOffset;\n        } else {\n            chevronOffset.top = propsChevronOffset;\n        }\n\n        // If we know the dimensions of the context menu, adjust its position to\n        // keep it within the bounds of the (padded) window\n        const { windowWidth, windowHeight } = UIStore.instance;\n        if (contextMenuRect) {\n            if (position.top !== undefined) {\n                let maxTop = windowHeight - WINDOW_PADDING;\n                if (!bottomAligned) {\n                    maxTop -= contextMenuRect.height;\n                }\n                position.top = Math.min(position.top, maxTop);\n                // Adjust the chevron if necessary\n                if (chevronOffset.top !== undefined) {\n                    chevronOffset.top = propsChevronOffset! + top! - position.top;\n                }\n            } else if (position.bottom !== undefined) {\n                position.bottom = Math.min(position.bottom, windowHeight - contextMenuRect.height - WINDOW_PADDING);\n                if (chevronOffset.top !== undefined) {\n                    chevronOffset.top = propsChevronOffset! + position.bottom - bottom!;\n                }\n            }\n            if (position.left !== undefined) {\n                let maxLeft = windowWidth - WINDOW_PADDING;\n                if (!rightAligned) {\n                    maxLeft -= contextMenuRect.width;\n                }\n                position.left = Math.min(position.left, maxLeft);\n                if (chevronOffset.left !== undefined) {\n                    chevronOffset.left = propsChevronOffset! + left! - position.left;\n                }\n            } else if (position.right !== undefined) {\n                position.right = Math.min(position.right, windowWidth - contextMenuRect.width - WINDOW_PADDING);\n                if (chevronOffset.left !== undefined) {\n                    chevronOffset.left = propsChevronOffset! + position.right - right!;\n                }\n            }\n        }\n\n        let chevron;\n        if (hasChevron) {\n            chevron = <div style={chevronOffset} className={\"mx_ContextualMenu_chevron_\" + chevronFace} />;\n        }\n\n        const menuClasses = classNames(\n            {\n                mx_ContextualMenu: true,\n                /**\n                 * In some cases we may get the number of 0, which still means that we're supposed to properly\n                 * add the specific position class, but as it was falsy things didn't work as intended.\n                 * In addition, defensively check for counter cases where we may get more than one value,\n                 * even if we shouldn't.\n                 */\n                mx_ContextualMenu_left: !hasChevron && position.left !== undefined && !position.right,\n                mx_ContextualMenu_right: !hasChevron && position.right !== undefined && !position.left,\n                mx_ContextualMenu_top: !hasChevron && position.top !== undefined && !position.bottom,\n                mx_ContextualMenu_bottom: !hasChevron && position.bottom !== undefined && !position.top,\n                mx_ContextualMenu_withChevron_left: chevronFace === ChevronFace.Left,\n                mx_ContextualMenu_withChevron_right: chevronFace === ChevronFace.Right,\n                mx_ContextualMenu_withChevron_top: chevronFace === ChevronFace.Top,\n                mx_ContextualMenu_withChevron_bottom: chevronFace === ChevronFace.Bottom,\n                mx_ContextualMenu_rightAligned: rightAligned === true,\n                mx_ContextualMenu_bottomAligned: bottomAligned === true,\n            },\n            menuClassName,\n        );\n\n        const menuStyle: CSSProperties = {};\n        if (menuWidth) {\n            menuStyle.width = menuWidth;\n        }\n\n        if (menuHeight) {\n            menuStyle.height = menuHeight;\n        }\n\n        if (!isNaN(Number(menuPaddingTop))) {\n            menuStyle[\"paddingTop\"] = menuPaddingTop;\n        }\n        if (!isNaN(Number(menuPaddingLeft))) {\n            menuStyle[\"paddingLeft\"] = menuPaddingLeft;\n        }\n        if (!isNaN(Number(menuPaddingBottom))) {\n            menuStyle[\"paddingBottom\"] = menuPaddingBottom;\n        }\n        if (!isNaN(Number(menuPaddingRight))) {\n            menuStyle[\"paddingRight\"] = menuPaddingRight;\n        }\n\n        const wrapperStyle: CSSProperties = {};\n        if (!isNaN(Number(zIndex))) {\n            menuStyle[\"zIndex\"] = zIndex! + 1;\n            wrapperStyle[\"zIndex\"] = zIndex;\n        }\n\n        let background: JSX.Element;\n        if (hasBackground) {\n            background = (\n                <div\n                    className=\"mx_ContextualMenu_background\"\n                    style={wrapperStyle}\n                    onClick={this.onFinished}\n                    onContextMenu={this.onContextMenu}\n                />\n            );\n        }\n\n        let body = (\n            <>\n                {chevron}\n                {children}\n            </>\n        );\n\n        if (focusLock) {\n            body = <FocusLock returnFocus>{body}</FocusLock>;\n        }\n\n        // filter props that are invalid for DOM elements\n        const {\n            hasBackground: _hasBackground, // eslint-disable-line @typescript-eslint/no-unused-vars\n            onFinished: _onFinished, // eslint-disable-line @typescript-eslint/no-unused-vars\n            ...divProps\n        } = props;\n\n        return (\n            <RovingTabIndexProvider handleHomeEnd handleUpDown onKeyDown={this.onKeyDown}>\n                {({ onKeyDownHandler }) => (\n                    <div\n                        className={classNames(\"mx_ContextualMenu_wrapper\", wrapperClassName)}\n                        style={{ ...position, ...wrapperStyle }}\n                        onClick={this.onClick}\n                        onKeyDown={onKeyDownHandler}\n                        onContextMenu={this.onContextMenuPreventBubbling}\n                    >\n                        {background}\n                        <TooltipProvider>\n                            <div\n                                className={menuClasses}\n                                style={menuStyle}\n                                ref={this.collectContextMenuRect}\n                                role={managed ? \"menu\" : undefined}\n                                {...divProps}\n                            >\n                                {body}\n                            </div>\n                        </TooltipProvider>\n                    </div>\n                )}\n            </RovingTabIndexProvider>\n        );\n    }\n\n    public render(): JSX.Element {\n        if (this.props.mountAsChild) {\n            // Render as a child of the current parent\n            return this.renderMenu();\n        } else {\n            // Render as a child of a container at the root of the DOM\n            return ReactDOM.createPortal(this.renderMenu(), getOrCreateContainer());\n        }\n    }\n}\n\nexport type ToRightOf = {\n    left: number;\n    top: number;\n    chevronOffset: number;\n};\n\n// Placement method for <ContextMenu /> to position context menu to right of elementRect with chevronOffset\nexport const toRightOf = (elementRect: Pick<DOMRect, \"right\" | \"top\" | \"height\">, chevronOffset = 12): ToRightOf => {\n    const left = elementRect.right + window.scrollX + 3;\n    let top = elementRect.top + elementRect.height / 2 + window.scrollY;\n    top -= chevronOffset + 8; // where 8 is half the height of the chevron\n    return { left, top, chevronOffset };\n};\n\nexport type ToLeftOf = {\n    chevronOffset: number;\n    right: number;\n    top: number;\n};\n\n// Placement method for <ContextMenu /> to position context menu to left of elementRect with chevronOffset\nexport const toLeftOf = (elementRect: DOMRect, chevronOffset = 12): ToLeftOf => {\n    const right = UIStore.instance.windowWidth - elementRect.left + window.scrollX - 3;\n    let top = elementRect.top + elementRect.height / 2 + window.scrollY;\n    top -= chevronOffset + 8; // where 8 is half the height of the chevron\n    return { right, top, chevronOffset };\n};\n\n/**\n * Placement method for <ContextMenu /> to position context menu of or right of elementRect\n * depending on which side has more space.\n */\nexport const toLeftOrRightOf = (elementRect: DOMRect, chevronOffset = 12): ToRightOf | ToLeftOf => {\n    const spaceToTheLeft = elementRect.left;\n    const spaceToTheRight = UIStore.instance.windowWidth - elementRect.right;\n\n    if (spaceToTheLeft > spaceToTheRight) {\n        return toLeftOf(elementRect, chevronOffset);\n    }\n\n    return toRightOf(elementRect, chevronOffset);\n};\n\n// Placement method for <ContextMenu /> to position context menu right-aligned and flowing to the left of elementRect,\n// and either above or below: wherever there is more space (maybe this should be aboveOrBelowLeftOf?)\nexport const aboveLeftOf = (\n    elementRect: Pick<DOMRect, \"right\" | \"top\" | \"bottom\">,\n    chevronFace = ChevronFace.None,\n    vPadding = 0,\n): MenuProps => {\n    const menuOptions: IPosition & { chevronFace: ChevronFace } = { chevronFace };\n\n    const buttonRight = elementRect.right + window.scrollX;\n    const buttonBottom = elementRect.bottom + window.scrollY;\n    const buttonTop = elementRect.top + window.scrollY;\n    // Align the right edge of the menu to the right edge of the button\n    menuOptions.right = UIStore.instance.windowWidth - buttonRight;\n    // Align the menu vertically on whichever side of the button has more space available.\n    if (buttonBottom < UIStore.instance.windowHeight / 2) {\n        menuOptions.top = buttonBottom + vPadding;\n    } else {\n        menuOptions.bottom = UIStore.instance.windowHeight - buttonTop + vPadding;\n    }\n\n    return menuOptions;\n};\n\n// Placement method for <ContextMenu /> to position context menu right-aligned and flowing to the right of elementRect,\n// and either above or below: wherever there is more space (maybe this should be aboveOrBelowRightOf?)\nexport const aboveRightOf = (\n    elementRect: Pick<DOMRect, \"left\" | \"top\" | \"bottom\">,\n    chevronFace = ChevronFace.None,\n    vPadding = 0,\n): MenuProps => {\n    const menuOptions: IPosition & { chevronFace: ChevronFace } = { chevronFace };\n\n    const buttonLeft = elementRect.left + window.scrollX;\n    const buttonBottom = elementRect.bottom + window.scrollY;\n    const buttonTop = elementRect.top + window.scrollY;\n    // Align the left edge of the menu to the left edge of the button\n    menuOptions.left = buttonLeft;\n    // Align the menu vertically on whichever side of the button has more space available.\n    if (buttonBottom < UIStore.instance.windowHeight / 2) {\n        menuOptions.top = buttonBottom + vPadding;\n    } else {\n        menuOptions.bottom = UIStore.instance.windowHeight - buttonTop + vPadding;\n    }\n\n    return menuOptions;\n};\n\n// Placement method for <ContextMenu /> to position context menu right-aligned and flowing to the left of elementRect\n// and always above elementRect\nexport const alwaysMenuProps = (\n    elementRect: Pick<DOMRect, \"right\" | \"bottom\" | \"top\">,\n    chevronFace = ChevronFace.None,\n    vPadding = 0,\n): IPosition & { chevronFace: ChevronFace } => {\n    const menuOptions: IPosition & { chevronFace: ChevronFace } = { chevronFace };\n\n    const buttonRight = elementRect.right + window.scrollX;\n    const buttonTop = elementRect.top + window.scrollY;\n    // Align the right edge of the menu to the right edge of the button\n    menuOptions.right = UIStore.instance.windowWidth - buttonRight;\n    // Align the menu vertically above the menu\n    menuOptions.bottom = UIStore.instance.windowHeight - buttonTop + vPadding;\n\n    return menuOptions;\n};\n\n// Placement method for <ContextMenu /> to position context menu right-aligned and flowing to the right of elementRect\n// and always above elementRect\nexport const alwaysAboveRightOf = (\n    elementRect: Pick<DOMRect, \"left\" | \"top\">,\n    chevronFace = ChevronFace.None,\n    vPadding = 0,\n): IPosition & { chevronFace: ChevronFace } => {\n    const menuOptions: IPosition & { chevronFace: ChevronFace } = { chevronFace };\n\n    const buttonLeft = elementRect.left + window.scrollX;\n    const buttonTop = elementRect.top + window.scrollY;\n    // Align the left edge of the menu to the left edge of the button\n    menuOptions.left = buttonLeft;\n    // Align the menu vertically above the menu\n    menuOptions.bottom = UIStore.instance.windowHeight - buttonTop + vPadding;\n\n    return menuOptions;\n};\n\ntype ContextMenuTuple<T> = [\n    boolean,\n    RefObject<T | null>,\n    (ev?: SyntheticEvent) => void,\n    (ev?: SyntheticEvent) => void,\n    (val: boolean) => void,\n];\n// eslint-disable-next-line @typescript-eslint/no-unnecessary-type-constraint\nexport const useContextMenu = <T extends HTMLElement = HTMLElement>(\n    inputRef?: RefObject<T | null>,\n): ContextMenuTuple<T> => {\n    let button = useRef<T>(null);\n    if (inputRef) {\n        // if we are given a ref, use it instead of ours\n        button = inputRef;\n    }\n\n    const [isOpen, setIsOpen] = useState(false);\n    const open = (ev?: SyntheticEvent): void => {\n        ev?.preventDefault();\n        ev?.stopPropagation();\n        setIsOpen(true);\n    };\n    const close = (ev?: SyntheticEvent): void => {\n        ev?.preventDefault();\n        ev?.stopPropagation();\n        setIsOpen(false);\n    };\n\n    // eslint-disable-next-line react-compiler/react-compiler\n    return [button.current ? isOpen : false, button, open, close, setIsOpen];\n};\n\n// re-export the semantic helper components for simplicity\nexport { ContextMenuButton } from \"../../accessibility/context_menu/ContextMenuButton\";\nexport { ContextMenuTooltipButton } from \"../../accessibility/context_menu/ContextMenuTooltipButton\";\nexport { MenuItem } from \"../../accessibility/context_menu/MenuItem\";\nexport { MenuItemCheckbox } from \"../../accessibility/context_menu/MenuItemCheckbox\";\nexport { MenuItemRadio } from \"../../accessibility/context_menu/MenuItemRadio\";\nexport { StyledMenuItemCheckbox } from \"../../accessibility/context_menu/StyledMenuItemCheckbox\";\nexport { StyledMenuItemRadio } from \"../../accessibility/context_menu/StyledMenuItemRadio\";\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef } from \"react\";\nimport {\n    AuthType,\n    type IAuthData,\n    type AuthDict,\n    type IInputs,\n    InteractiveAuth,\n    type IStageStatus,\n} from \"matrix-js-sdk/src/interactive-auth\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport getEntryComponentForLoginType, {\n    type ContinueKind,\n    CustomAuthType,\n    type IStageComponent,\n} from \"../views/auth/InteractiveAuthEntryComponents\";\nimport Spinner from \"../views/elements/Spinner\";\n\nexport const ERROR_USER_CANCELLED = new Error(\"User cancelled auth session\");\n\nexport type InteractiveAuthCallback<T> = {\n    (success: true, response: T, extra?: { emailSid?: string; clientSecret?: string }): Promise<void>;\n    (success: false, response: IAuthData | Error): Promise<void>;\n};\n\nexport interface InteractiveAuthProps<T> {\n    // matrix client to use for UI auth requests\n    matrixClient: MatrixClient;\n    // response from initial request. If not supplied, will do a request on mount.\n    authData?: IAuthData;\n    // Inputs provided by the user to the auth process\n    // and used by various stages. As passed to js-sdk\n    // interactive-auth\n    inputs?: IInputs;\n    sessionId?: string;\n    clientSecret?: string;\n    emailSid?: string;\n    // If true, poll to see if the auth flow has been completed out-of-band\n    poll?: boolean;\n    // continueText and continueKind are passed straight through to the AuthEntryComponent.\n    continueText?: string;\n    continueKind?: ContinueKind;\n    // callback\n    makeRequest(auth: AuthDict | null): Promise<T>;\n    // callback called when the auth process has finished,\n    // successfully or unsuccessfully.\n    // @param {boolean} status True if the operation requiring\n    //     auth was completed successfully, false if canceled.\n    // @param {object} result The result of the authenticated call\n    //     if successful, otherwise the error object.\n    // @param {object} extra Additional information about the UI Auth\n    //     process:\n    //      * emailSid {string} If email auth was performed, the sid of\n    //            the auth session.\n    //      * clientSecret {string} The client secret used in auth\n    //            sessions with the ID server.\n    onAuthFinished: InteractiveAuthCallback<T>;\n    // As js-sdk interactive-auth\n    requestEmailToken?(email: string, secret: string, attempt: number, session: string): Promise<{ sid: string }>;\n    // Called when the stage changes, or the stage's phase changes. First\n    // argument is the stage, second is the phase. Some stages do not have\n    // phases and will be counted as 0 (numeric).\n    onStagePhaseChange?(stage: AuthType | CustomAuthType | null, phase: number): void;\n}\n\ninterface IState {\n    authStage?: CustomAuthType | AuthType;\n    stageState?: IStageStatus;\n    busy: boolean;\n    errorText?: string;\n    errorCode?: string;\n    submitButtonEnabled: boolean;\n}\n\nexport default class InteractiveAuthComponent<T> extends React.Component<InteractiveAuthProps<T>, IState> {\n    private readonly authLogic: InteractiveAuth<T>;\n    private readonly stageComponent = createRef<IStageComponent>();\n    private intervalId: number | null = null;\n\n    private unmounted = false;\n\n    public constructor(props: InteractiveAuthProps<T>) {\n        super(props);\n\n        this.state = {\n            busy: false,\n            submitButtonEnabled: false,\n        };\n\n        this.authLogic = new InteractiveAuth<T>({\n            authData: this.props.authData,\n            doRequest: this.requestCallback,\n            busyChanged: this.onBusyChanged,\n            inputs: this.props.inputs,\n            stateUpdated: this.authStateUpdated,\n            matrixClient: this.props.matrixClient,\n            sessionId: this.props.sessionId,\n            clientSecret: this.props.clientSecret,\n            emailSid: this.props.emailSid,\n            requestEmailToken: this.requestEmailToken,\n            supportedStages: [\n                AuthType.Password,\n                AuthType.Recaptcha,\n                AuthType.Email,\n                AuthType.Msisdn,\n                AuthType.Terms,\n                AuthType.RegistrationToken,\n                AuthType.UnstableRegistrationToken,\n                AuthType.Sso,\n                AuthType.SsoUnstable,\n                AuthType.OAuth,\n                CustomAuthType.MasCrossSigningReset,\n            ],\n        });\n    }\n\n    public componentDidMount(): void {\n        this.unmounted = false;\n\n        if (this.props.poll) {\n            this.intervalId = window.setInterval(() => {\n                this.authLogic.poll();\n            }, 2000);\n        }\n\n        this.authLogic\n            .attemptAuth()\n            .then(async (result) => {\n                const extra = {\n                    emailSid: this.authLogic.getEmailSid(),\n                    clientSecret: this.authLogic.getClientSecret(),\n                };\n                await this.props.onAuthFinished(true, result, extra);\n            })\n            .catch(async (error) => {\n                await this.props.onAuthFinished(false, error);\n                logger.error(\"Error during user-interactive auth:\", error);\n                if (this.unmounted) {\n                    return;\n                }\n\n                const msg = error.message || error.toString();\n                this.setState({\n                    errorText: msg,\n                    errorCode: error.errcode,\n                });\n            });\n    }\n\n    public componentWillUnmount(): void {\n        this.unmounted = true;\n\n        if (this.intervalId !== null) {\n            clearInterval(this.intervalId);\n        }\n    }\n\n    private requestEmailToken = async (\n        email: string,\n        secret: string,\n        attempt: number,\n        session: string,\n    ): Promise<{ sid: string }> => {\n        this.setState({\n            busy: true,\n        });\n        try {\n            // We know this method only gets called on flows where requestEmailToken is passed but types don't\n            return await this.props.requestEmailToken!(email, secret, attempt, session);\n        } finally {\n            this.setState({\n                busy: false,\n            });\n        }\n    };\n\n    private authStateUpdated = (stageType: AuthType, stageState: IStageStatus): void => {\n        const oldStage = this.state.authStage;\n        this.setState(\n            {\n                busy: false,\n                authStage: stageType,\n                stageState: stageState,\n                errorText: stageState.error,\n                errorCode: stageState.errcode,\n            },\n            () => {\n                if (oldStage !== stageType) {\n                    this.setFocus();\n                } else if (!stageState.error) {\n                    this.stageComponent.current?.attemptFailed?.();\n                }\n            },\n        );\n    };\n\n    private requestCallback = (auth: AuthDict | null, background: boolean): Promise<T> => {\n        // This wrapper just exists because the js-sdk passes a second\n        // 'busy' param for backwards compat. This throws the tests off\n        // so discard it here.\n        return this.props.makeRequest(auth);\n    };\n\n    private onBusyChanged = (busy: boolean): void => {\n        // if we've started doing stuff, reset the error messages\n        // The JS SDK eagerly reports itself as \"not busy\" right after any\n        // immediate work has completed, but that's not really what we want at\n        // the UI layer, so we ignore this signal and show a spinner until\n        // there's a new screen to show the user. This is implemented by setting\n        // `busy: false` in `authStateUpdated`.\n        // See also https://github.com/vector-im/element-web/issues/12546\n        if (busy) {\n            this.setState({\n                busy: true,\n                errorText: undefined,\n                errorCode: undefined,\n            });\n        }\n\n        // authStateUpdated is not called during sso flows\n        if (!busy && (this.state.authStage === AuthType.Sso || this.state.authStage === AuthType.SsoUnstable)) {\n            this.setState({ busy });\n        }\n    };\n\n    private setFocus(): void {\n        this.stageComponent.current?.focus?.();\n    }\n\n    private submitAuthDict = (authData: AuthDict): void => {\n        this.authLogic.submitAuthDict(authData);\n    };\n\n    private onPhaseChange = (newPhase: number): void => {\n        this.props.onStagePhaseChange?.(this.state.authStage ?? null, newPhase || 0);\n    };\n\n    private onStageCancel = async (): Promise<void> => {\n        await this.props.onAuthFinished(false, ERROR_USER_CANCELLED);\n    };\n\n    private onAuthStageFailed = async (e: Error): Promise<void> => {\n        await this.props.onAuthFinished(false, e);\n    };\n\n    private setEmailSid = (sid: string): void => {\n        this.authLogic.setEmailSid(sid);\n    };\n\n    public render(): React.ReactNode {\n        const stage = this.state.authStage;\n        if (!stage) {\n            if (this.state.busy) {\n                return <Spinner />;\n            } else {\n                return null;\n            }\n        }\n\n        const StageComponent = getEntryComponentForLoginType(stage);\n        return (\n            <StageComponent\n                ref={this.stageComponent as any}\n                loginType={stage}\n                matrixClient={this.props.matrixClient}\n                authSessionId={this.authLogic.getSessionId()}\n                clientSecret={this.authLogic.getClientSecret()}\n                stageParams={this.authLogic.getStageParams(stage)}\n                submitAuthDict={this.submitAuthDict}\n                errorText={this.state.errorText}\n                errorCode={this.state.errorCode}\n                busy={this.state.busy}\n                inputs={this.props.inputs}\n                stageState={this.state.stageState}\n                fail={this.onAuthStageFailed}\n                setEmailSid={this.setEmailSid}\n                onPhaseChange={this.onPhaseChange}\n                requestEmailToken={this.authLogic.requestEmailToken}\n                continueText={this.props.continueText}\n                continueKind={this.props.continueKind}\n                onCancel={this.onStageCancel}\n            />\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EventType, type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { CallEvent, CallState, CallType, type MatrixCall } from \"matrix-js-sdk/src/webrtc/call\";\nimport { EventEmitter } from \"events\";\n\nimport LegacyCallHandler, { LegacyCallHandlerEvent } from \"../../LegacyCallHandler\";\nimport { MatrixClientPeg } from \"../../MatrixClientPeg\";\n\nexport enum LegacyCallEventGrouperEvent {\n    StateChanged = \"state_changed\",\n    SilencedChanged = \"silenced_changed\",\n    LengthChanged = \"length_changed\",\n}\n\nconst CONNECTING_STATES = [\n    CallState.Connecting,\n    CallState.WaitLocalMedia,\n    CallState.CreateOffer,\n    CallState.CreateAnswer,\n];\n\nconst SUPPORTED_STATES = [CallState.Connected, CallState.Ringing, CallState.Ended];\n\nconst isCallEventType = (eventType: string): boolean =>\n    eventType.startsWith(\"m.call.\") || eventType.startsWith(\"org.matrix.call.\");\n\nexport const isCallEvent = (event: MatrixEvent): boolean => isCallEventType(event.getType());\n\nexport function buildLegacyCallEventGroupers(\n    callEventGroupers: Map<string, LegacyCallEventGrouper>,\n    events?: MatrixEvent[],\n): Map<string, LegacyCallEventGrouper> {\n    const newCallEventGroupers = new Map();\n    events?.forEach((ev) => {\n        if (!isCallEvent(ev)) {\n            return;\n        }\n\n        const callId = ev.getContent().call_id;\n        if (!newCallEventGroupers.has(callId)) {\n            if (callEventGroupers.has(callId)) {\n                // reuse the LegacyCallEventGrouper object where possible\n                newCallEventGroupers.set(callId, callEventGroupers.get(callId));\n            } else {\n                newCallEventGroupers.set(callId, new LegacyCallEventGrouper());\n            }\n        }\n        newCallEventGroupers.get(callId).add(ev);\n    });\n    return newCallEventGroupers;\n}\n\nexport default class LegacyCallEventGrouper extends EventEmitter {\n    private events: Set<MatrixEvent> = new Set<MatrixEvent>();\n    private call: MatrixCall | null = null;\n    public state?: CallState;\n\n    public constructor() {\n        super();\n\n        LegacyCallHandler.instance.addListener(LegacyCallHandlerEvent.CallsChanged, this.setCall);\n        LegacyCallHandler.instance.addListener(\n            LegacyCallHandlerEvent.SilencedCallsChanged,\n            this.onSilencedCallsChanged,\n        );\n    }\n\n    private get invite(): MatrixEvent | undefined {\n        return [...this.events].find((event) => event.getType() === EventType.CallInvite);\n    }\n\n    private get hangup(): MatrixEvent | undefined {\n        return [...this.events].find((event) => event.getType() === EventType.CallHangup);\n    }\n\n    private get reject(): MatrixEvent | undefined {\n        return [...this.events].find((event) => event.getType() === EventType.CallReject);\n    }\n\n    private get selectAnswer(): MatrixEvent | undefined {\n        return [...this.events].find((event) => event.getType() === EventType.CallSelectAnswer);\n    }\n\n    public get isVoice(): boolean | undefined {\n        const invite = this.invite;\n        if (!invite) return undefined;\n\n        // FIXME: Find a better way to determine this from the event?\n        if (invite.getContent()?.offer?.sdp?.indexOf(\"m=video\") !== -1) return false;\n        return true;\n    }\n\n    public get hangupReason(): string | null {\n        return this.call?.hangupReason ?? this.hangup?.getContent()?.reason ?? null;\n    }\n\n    public get rejectParty(): string | undefined {\n        return this.reject?.getSender();\n    }\n\n    public get gotRejected(): boolean {\n        return Boolean(this.reject);\n    }\n\n    public get duration(): number | null {\n        if (!this.hangup?.getDate() || !this.selectAnswer?.getDate()) return null;\n        return this.hangup.getDate()!.getTime() - this.selectAnswer.getDate()!.getTime();\n    }\n\n    /**\n     * Returns true if there are only events from the other side - we missed the call\n     */\n    public get callWasMissed(): boolean {\n        return (\n            this.state === CallState.Ended &&\n            ![...this.events].some((event) => event.sender?.userId === MatrixClientPeg.safeGet().getUserId())\n        );\n    }\n\n    private get callId(): string | undefined {\n        return [...this.events][0]?.getContent()?.call_id;\n    }\n\n    private get roomId(): string | undefined {\n        return [...this.events][0]?.getRoomId();\n    }\n\n    private onSilencedCallsChanged = (): void => {\n        const newState = LegacyCallHandler.instance.isCallSilenced(this.callId);\n        this.emit(LegacyCallEventGrouperEvent.SilencedChanged, newState);\n    };\n\n    private onLengthChanged = (length: number): void => {\n        this.emit(LegacyCallEventGrouperEvent.LengthChanged, length);\n    };\n\n    public answerCall = (): void => {\n        const roomId = this.roomId;\n        if (!roomId) return;\n        LegacyCallHandler.instance.answerCall(roomId);\n    };\n\n    public rejectCall = (): void => {\n        const roomId = this.roomId;\n        if (!roomId) return;\n        LegacyCallHandler.instance.hangupOrReject(roomId, true);\n    };\n\n    public callBack = (): void => {\n        const roomId = this.roomId;\n        if (!roomId) return;\n        LegacyCallHandler.instance.placeCall(roomId, this.isVoice ? CallType.Voice : CallType.Video);\n    };\n\n    public toggleSilenced = (): void => {\n        const silenced = LegacyCallHandler.instance.isCallSilenced(this.callId);\n        if (silenced) {\n            LegacyCallHandler.instance.unSilenceCall(this.callId);\n        } else {\n            LegacyCallHandler.instance.silenceCall(this.callId);\n        }\n    };\n\n    private setCallListeners(): void {\n        if (!this.call) return;\n        this.call.addListener(CallEvent.State, this.setState);\n        this.call.addListener(CallEvent.LengthChanged, this.onLengthChanged);\n    }\n\n    private setState = (): void => {\n        if (this.call && CONNECTING_STATES.includes(this.call.state)) {\n            this.state = CallState.Connecting;\n        } else if (this.call && SUPPORTED_STATES.includes(this.call.state)) {\n            this.state = this.call.state;\n        } else {\n            if (this.reject) {\n                this.state = CallState.Ended;\n            } else if (this.hangup) {\n                this.state = CallState.Ended;\n            } else if (this.invite && this.call) {\n                this.state = CallState.Connecting;\n            }\n        }\n        this.emit(LegacyCallEventGrouperEvent.StateChanged, this.state);\n    };\n\n    private setCall = (): void => {\n        const callId = this.callId;\n        if (!callId || this.call) return;\n\n        this.call = LegacyCallHandler.instance.getCallById(callId);\n        this.setCallListeners();\n        this.setState();\n    };\n\n    public add(event: MatrixEvent): void {\n        if (this.events.has(event)) return; // nothing to do\n        this.events.add(event);\n        this.setCall();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef, type CSSProperties, type ReactNode } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport SettingsStore from \"../../settings/SettingsStore\";\nimport Timer from \"../../utils/Timer\";\nimport AutoHideScrollbar from \"./AutoHideScrollbar\";\nimport { getKeyBindingsManager } from \"../../KeyBindingsManager\";\nimport { KeyBindingAction } from \"../../accessibility/KeyboardShortcuts\";\nimport { SDKContext } from \"../../contexts/SDKContext\";\n\n// The amount of extra scroll distance to allow prior to unfilling.\n// See getExcessHeight.\nconst UNPAGINATION_PADDING = 6000;\n// The number of milliseconds to debounce calls to onUnfillRequest,\n// to prevent many scroll events causing many unfilling requests.\nconst UNFILL_REQUEST_DEBOUNCE_MS = 200;\n// updateHeight makes the height a `Math.ceil` multiple of this, so we don't have to update the height too often.\n// It also allows the user to scroll past the pagination spinner a bit, so they don't feel blocked so\n// much while the content loads.\nconst PAGE_SIZE = 400;\n\nconst debuglog = (...args: any[]): void => {\n    if (SettingsStore.getValue(\"debug_scroll_panel\")) {\n        logger.log.call(console, \"ScrollPanel debuglog:\", ...args);\n    }\n};\n\ninterface IProps {\n    /* stickyBottom: if set to true, then once the user hits the bottom of\n     * the list, any new children added to the list will cause the list to\n     * scroll down to show the new element, rather than preserving the\n     * existing view.\n     */\n    stickyBottom?: boolean;\n\n    /* startAtBottom: if set to true, the view is assumed to start\n     * scrolled to the bottom.\n     * XXX: It's likely this is unnecessary and can be derived from\n     * stickyBottom, but I'm adding an extra parameter to ensure\n     * behaviour stays the same for other uses of ScrollPanel.\n     * If so, let's remove this parameter down the line.\n     */\n    startAtBottom?: boolean;\n\n    /* className: classnames to add to the top-level div\n     */\n    className?: string;\n\n    /* style: styles to add to the top-level div\n     */\n    style?: CSSProperties;\n\n    /* fixedChildren: allows for children to be passed which are rendered outside\n     * of the wrapper\n     */\n    fixedChildren?: ReactNode;\n    children?: ReactNode;\n\n    /* onFillRequest(backwards): a callback which is called on scroll when\n     * the user nears the start (backwards = true) or end (backwards =\n     * false) of the list.\n     *\n     * This should return a promise; no more calls will be made until the\n     * promise completes.\n     *\n     * The promise should resolve to true if there is more data to be\n     * retrieved in this direction (in which case onFillRequest may be\n     * called again immediately), or false if there is no more data in this\n     * direction (at this time) - which will stop the pagination cycle until\n     * the user scrolls again.\n     */\n    onFillRequest?(backwards: boolean): Promise<boolean>;\n\n    /* onUnfillRequest(backwards): a callback which is called on scroll when\n     * there are children elements that are far out of view and could be removed\n     * without causing pagination to occur.\n     *\n     * This function should accept a boolean, which is true to indicate the back/top\n     * of the panel and false otherwise, and a scroll token, which refers to the\n     * first element to remove if removing from the front/bottom, and last element\n     * to remove if removing from the back/top.\n     */\n    onUnfillRequest?(backwards: boolean, scrollToken: string): void;\n\n    /* onScroll: a callback which is called whenever any scroll happens.\n     */\n    onScroll?(event: Event): void;\n}\n\n/* This component implements an intelligent scrolling list.\n *\n * It wraps a list of <li> children; when items are added to the start or end\n * of the list, the scroll position is updated so that the user still sees the\n * same position in the list.\n *\n * It also provides a hook which allows parents to provide more list elements\n * when we get close to the start or end of the list.\n *\n * Each child element should have a 'data-scroll-tokens'. This string of\n * comma-separated tokens may contain a single token or many, where many indicates\n * that the element contains elements that have scroll tokens themselves. The first\n * token in 'data-scroll-tokens' is used to serialise the scroll state, and returned\n * as the 'trackedScrollToken' attribute by getScrollState().\n *\n * IMPORTANT: INDIVIDUAL TOKENS WITHIN 'data-scroll-tokens' MUST NOT CONTAIN COMMAS.\n *\n * Some notes about the implementation:\n *\n * The saved 'scrollState' can exist in one of two states:\n *\n *   - stuckAtBottom: (the default, and restored by resetScrollState): the\n *     viewport is scrolled down as far as it can be. When the children are\n *     updated, the scroll position will be updated to ensure it is still at\n *     the bottom.\n *\n *   - fixed, in which the viewport is conceptually tied at a specific scroll\n *     offset.  We don't save the absolute scroll offset, because that would be\n *     affected by window width, zoom level, amount of scrollback, etc. Instead,\n *     we save an identifier for the last fully-visible message, and the number\n *     of pixels the window was scrolled below it - which is hopefully near\n *     enough.\n *\n * The 'stickyBottom' property controls the behaviour when we reach the bottom\n * of the window (either through a user-initiated scroll, or by calling\n * scrollToBottom). If stickyBottom is enabled, the scrollState will enter\n * 'stuckAtBottom' state - ensuring that new additions cause the window to\n * scroll down further. If stickyBottom is disabled, we just save the scroll\n * offset as normal.\n */\n\nexport interface IScrollState {\n    stuckAtBottom?: boolean;\n    trackedNode?: HTMLElement;\n    trackedScrollToken?: string;\n    bottomOffset?: number;\n    pixelOffset?: number;\n}\n\ninterface IPreventShrinkingState {\n    offsetFromBottom: number;\n    offsetNode: HTMLElement;\n}\n\nexport default class ScrollPanel extends React.Component<IProps> {\n    // noinspection JSUnusedLocalSymbols\n    public static defaultProps = {\n        stickyBottom: true,\n        startAtBottom: true,\n        onFillRequest: function (backwards: boolean) {\n            return Promise.resolve(false);\n        },\n        onUnfillRequest: function (backwards: boolean, scrollToken: string) {},\n        onScroll: function () {},\n    };\n\n    private readonly pendingFillRequests: Record<\"b\" | \"f\", boolean | null> = {\n        b: null,\n        f: null,\n    };\n    private readonly itemlist = createRef<HTMLOListElement>();\n    private unmounted = false;\n    private scrollTimeout?: Timer;\n    // Are we currently trying to backfill?\n    private isFilling = false;\n    // Is the current fill request caused by a props update?\n    private isFillingDueToPropsUpdate = false;\n    // Did another request to check the fill state arrive while we were trying to backfill?\n    private fillRequestWhileRunning = false;\n    // Is that next fill request scheduled because of a props update?\n    private pendingFillDueToPropsUpdate = false;\n    private scrollState!: IScrollState;\n    private preventShrinkingState: IPreventShrinkingState | null = null;\n    private unfillDebouncer: number | null = null;\n    private bottomGrowth!: number;\n    private minListHeight!: number;\n    private heightUpdateInProgress = false;\n    public divScroll: HTMLDivElement | null = null;\n\n    public static contextType = SDKContext;\n    declare public context: React.ContextType<typeof SDKContext>;\n\n    public constructor(props: IProps, context: React.ContextType<typeof SDKContext>) {\n        super(props, context);\n\n        this.resetScrollState();\n    }\n\n    public componentDidMount(): void {\n        this.unmounted = false;\n        this.context?.resizeNotifier?.on(\"middlePanelResizedNoisy\", this.onResize);\n        this.checkScroll();\n    }\n\n    public componentDidUpdate(): void {\n        // after adding event tiles, we may need to tweak the scroll (either to\n        // keep at the bottom of the timeline, or to maintain the view after\n        // adding events to the top).\n        //\n        // This will also re-check the fill state, in case the pagination was inadequate\n        this.checkScroll(true);\n        this.updatePreventShrinking();\n    }\n\n    public componentWillUnmount(): void {\n        // set a boolean to say we've been unmounted, which any pending\n        // promises can use to throw away their results.\n        //\n        // (We could use isMounted(), but facebook have deprecated that.)\n        this.unmounted = true;\n\n        this.context?.resizeNotifier?.removeListener(\"middlePanelResizedNoisy\", this.onResize);\n\n        this.divScroll = null;\n    }\n\n    private onScroll = (ev: Event): void => {\n        // skip scroll events caused by resizing\n        if (this.context?.resizeNotifier && this.context.resizeNotifier.isResizing) return;\n        debuglog(\"onScroll called past resize gate; scroll node top:\", this.getScrollNode().scrollTop);\n        this.scrollTimeout?.restart();\n        this.saveScrollState();\n        this.updatePreventShrinking();\n        this.props.onScroll?.(ev);\n        // noinspection JSIgnoredPromiseFromCall\n        this.checkFillState();\n    };\n\n    private onResize = (): void => {\n        debuglog(\"onResize called\");\n        this.checkScroll();\n        // update preventShrinkingState if present\n        if (this.preventShrinkingState) {\n            this.preventShrinking();\n        }\n    };\n\n    // after an update to the contents of the panel, check that the scroll is\n    // where it ought to be, and set off pagination requests if necessary.\n    public checkScroll = (isFromPropsUpdate = false): void => {\n        if (this.unmounted) {\n            return;\n        }\n        // We don't care if these two conditions race - they're different trees.\n        // noinspection JSIgnoredPromiseFromCall\n        this.restoreSavedScrollState();\n        // noinspection JSIgnoredPromiseFromCall\n        this.checkFillState(0, isFromPropsUpdate);\n    };\n\n    // return true if the content is fully scrolled down right now; else false.\n    //\n    // note that this is independent of the 'stuckAtBottom' state - it is simply\n    // about whether the content is scrolled down right now, irrespective of\n    // whether it will stay that way when the children update.\n    public isAtBottom = (): boolean => {\n        const sn = this.getScrollNode();\n        // fractional values (both too big and too small)\n        // for scrollTop happen on certain browsers/platforms\n        // when scrolled all the way down. E.g. Chrome 72 on debian.\n        //\n        // We therefore leave a bit of wiggle-room and assume we're at the\n        // bottom if the unscrolled area is less than one pixel high.\n        //\n        // non-standard DPI settings also seem to have effect here and can\n        // actually lead to scrollTop+clientHeight being *larger* than\n        // scrollHeight. (observed in element-desktop on Ubuntu 20.04)\n        //\n        return sn.scrollHeight - (sn.scrollTop + sn.clientHeight) <= 1;\n    };\n\n    // returns the vertical height in the given direction that can be removed from\n    // the content box (which has a height of scrollHeight, see checkFillState) without\n    // pagination occurring.\n    //\n    // padding* = UNPAGINATION_PADDING\n    //\n    // ### Region determined as excess.\n    //\n    //   .---------.                        -              -\n    //   |#########|                        |              |\n    //   |#########|   -                    |  scrollTop   |\n    //   |         |   | padding*           |              |\n    //   |         |   |                    |              |\n    // .-+---------+-. -  -                 |              |\n    // : |         | :    |                 |              |\n    // : |         | :    |  clientHeight   |              |\n    // : |         | :    |                 |              |\n    // .-+---------+-.    -                 -              |\n    // | |         | |    |                                |\n    // | |         | |    |  clientHeight                  | scrollHeight\n    // | |         | |    |                                |\n    // `-+---------+-'    -                                |\n    // : |         | :    |                                |\n    // : |         | :    |  clientHeight                  |\n    // : |         | :    |                                |\n    // `-+---------+-' -  -                                |\n    //   |         |   | padding*                          |\n    //   |         |   |                                   |\n    //   |#########|   -                                   |\n    //   |#########|                                       |\n    //   `---------'                                       -\n    private getExcessHeight(backwards: boolean): number {\n        const sn = this.getScrollNode();\n        const contentHeight = this.getMessagesHeight();\n        const listHeight = this.getListHeight();\n        const clippedHeight = contentHeight - listHeight;\n        const unclippedScrollTop = sn.scrollTop + clippedHeight;\n\n        if (backwards) {\n            return unclippedScrollTop - sn.clientHeight - UNPAGINATION_PADDING;\n        } else {\n            return contentHeight - (unclippedScrollTop + 2 * sn.clientHeight) - UNPAGINATION_PADDING;\n        }\n    }\n\n    // check the scroll state and send out backfill requests if necessary.\n    public checkFillState = async (depth = 0, isFromPropsUpdate = false): Promise<void> => {\n        if (this.unmounted) {\n            return;\n        }\n\n        const isFirstCall = depth === 0;\n        const sn = this.getScrollNode();\n\n        // if there is less than a screen's worth of messages above or below the\n        // viewport, try to get some more messages.\n        //\n        // scrollTop is the number of pixels between the top of the content and\n        //     the top of the viewport.\n        //\n        // scrollHeight is the total height of the content.\n        //\n        // clientHeight is the height of the viewport (excluding borders,\n        // margins, and scrollbars).\n        //\n        //\n        //   .---------.          -                 -\n        //   |         |          |  scrollTop      |\n        // .-+---------+-.    -   -                 |\n        // | |         | |    |                     |\n        // | |         | |    |  clientHeight       | scrollHeight\n        // | |         | |    |                     |\n        // `-+---------+-'    -                     |\n        //   |         |                            |\n        //   |         |                            |\n        //   `---------'                            -\n        //\n\n        // as filling is async and recursive,\n        // don't allow more than 1 chain of calls concurrently\n        // do make a note when a new request comes in while already running one,\n        // so we can trigger a new chain of calls once done.\n        // However, we make an exception for when we're already filling due to a\n        // props (or children) update, because very often the children include\n        // spinners to say whether we're paginating or not, so this would cause\n        // infinite paginating.\n        if (isFirstCall) {\n            if (this.isFilling && !this.isFillingDueToPropsUpdate) {\n                debuglog(\"isFilling: not entering while request is ongoing, marking for a subsequent request\");\n                this.fillRequestWhileRunning = true;\n                this.pendingFillDueToPropsUpdate = isFromPropsUpdate;\n                return;\n            }\n            debuglog(\"isFilling: setting\");\n            this.isFilling = true;\n            this.isFillingDueToPropsUpdate = isFromPropsUpdate;\n        }\n\n        const itemlist = this.itemlist.current;\n        const firstTile = itemlist?.firstElementChild as HTMLElement | undefined;\n        const fillPromises: Promise<void>[] = [];\n\n        // if scrollTop gets to 1 screen from the top of the first tile,\n        // try backward filling\n        if (!firstTile || sn.scrollTop - firstTile.offsetTop < sn.clientHeight) {\n            // need to back-fill\n            fillPromises.push(this.maybeFill(depth, true));\n        }\n        // if scrollTop gets to 2 screens from the end (so 1 screen below viewport),\n        // try forward filling\n        if (sn.scrollHeight - sn.scrollTop < sn.clientHeight * 2) {\n            // need to forward-fill\n            fillPromises.push(this.maybeFill(depth, false));\n        }\n\n        if (fillPromises.length) {\n            try {\n                await Promise.all(fillPromises);\n            } catch (err) {\n                logger.error(err);\n            }\n        }\n        if (isFirstCall) {\n            debuglog(\"isFilling: clearing\");\n            this.isFilling = false;\n            this.isFillingDueToPropsUpdate = false;\n        }\n\n        if (this.fillRequestWhileRunning) {\n            const refillDueToPropsUpdate = this.pendingFillDueToPropsUpdate;\n            this.fillRequestWhileRunning = false;\n            this.pendingFillDueToPropsUpdate = false;\n            // noinspection ES6MissingAwait\n            this.checkFillState(0, refillDueToPropsUpdate);\n        }\n    };\n\n    // check if unfilling is possible and send an unfill request if necessary\n    private checkUnfillState(backwards: boolean): void {\n        let excessHeight = this.getExcessHeight(backwards);\n        if (excessHeight <= 0 || !this.itemlist.current) {\n            return;\n        }\n\n        const origExcessHeight = excessHeight;\n\n        const tiles = this.itemlist.current.children;\n\n        // The scroll token of the first/last tile to be unpaginated\n        let markerScrollToken: string | null = null;\n\n        // Subtract heights of tiles to simulate the tiles being unpaginated until the\n        // excess height is less than the height of the next tile to subtract. This\n        // prevents excessHeight becoming negative, which could lead to future\n        // pagination.\n        //\n        // If backwards is true, we unpaginate (remove) tiles from the back (top).\n        let tile: HTMLElement;\n        for (let i = 0; i < tiles.length; i++) {\n            tile = tiles[backwards ? i : tiles.length - 1 - i] as HTMLElement;\n            // Subtract height of tile as if it were unpaginated\n            excessHeight -= tile.clientHeight;\n            //If removing the tile would lead to future pagination, break before setting scroll token\n            if (tile.clientHeight > excessHeight) {\n                break;\n            }\n            // The tile may not have a scroll token, so guard it\n            if (tile.dataset.scrollTokens) {\n                markerScrollToken = tile.dataset.scrollTokens.split(\",\")[0];\n            }\n        }\n\n        if (markerScrollToken) {\n            // Use a debouncer to prevent multiple unfill calls in quick succession\n            // This is to make the unfilling process less aggressive\n            if (this.unfillDebouncer) {\n                clearTimeout(this.unfillDebouncer);\n            }\n            this.unfillDebouncer = window.setTimeout(() => {\n                this.unfillDebouncer = null;\n                debuglog(\"unfilling now\", { backwards, origExcessHeight });\n                this.props.onUnfillRequest?.(backwards, markerScrollToken!);\n            }, UNFILL_REQUEST_DEBOUNCE_MS);\n        }\n    }\n\n    // check if there is already a pending fill request. If not, set one off.\n    private maybeFill(depth: number, backwards: boolean): Promise<void> {\n        const dir = backwards ? \"b\" : \"f\";\n        if (this.pendingFillRequests[dir]) {\n            debuglog(\"Already a fill in progress - not starting another; direction=\", dir);\n            return Promise.resolve();\n        }\n\n        debuglog(\"starting fill; direction=\", dir);\n\n        // onFillRequest can end up calling us recursively (via onScroll\n        // events) so make sure we set this before firing off the call.\n        this.pendingFillRequests[dir] = true;\n\n        // wait 1ms before paginating, because otherwise\n        // this will block the scroll event handler for +700ms\n        // if messages are already cached in memory,\n        // This would cause jumping to happen on Chrome/macOS.\n        return new Promise((resolve) => window.setTimeout(resolve, 1))\n            .then(() => {\n                return this.props.onFillRequest?.(backwards);\n            })\n            .finally(() => {\n                this.pendingFillRequests[dir] = false;\n            })\n            .then((hasMoreResults) => {\n                if (this.unmounted) {\n                    return;\n                }\n                // Unpaginate once filling is complete\n                this.checkUnfillState(!backwards);\n\n                debuglog(\"fill complete; hasMoreResults=\", hasMoreResults, \"direction=\", dir);\n                if (hasMoreResults) {\n                    // further pagination requests have been disabled until now, so\n                    // it's time to check the fill state again in case the pagination\n                    // was insufficient.\n                    return this.checkFillState(depth + 1);\n                }\n            });\n    }\n\n    /* get the current scroll state. This returns an object with the following\n     * properties:\n     *\n     * boolean stuckAtBottom: true if we are tracking the bottom of the\n     *   scroll. false if we are tracking a particular child.\n     *\n     * string trackedScrollToken: undefined if stuckAtBottom is true; if it is\n     *   false, the first token in data-scroll-tokens of the child which we are\n     *   tracking.\n     *\n     * number bottomOffset: undefined if stuckAtBottom is true; if it is false,\n     *   the number of pixels the bottom of the tracked child is above the\n     *   bottom of the scroll panel.\n     */\n    public getScrollState = (): IScrollState => this.scrollState;\n\n    /* reset the saved scroll state.\n     *\n     * This is useful if the list is being replaced, and you don't want to\n     * preserve scroll even if new children happen to have the same scroll\n     * tokens as old ones.\n     *\n     * This will cause the viewport to be scrolled down to the bottom on the\n     * next update of the child list. This is different to scrollToBottom(),\n     * which would save the current bottom-most child as the active one (so is\n     * no use if no children exist yet, or if you are about to replace the\n     * child list.)\n     */\n    public resetScrollState = (): void => {\n        this.scrollState = {\n            stuckAtBottom: this.props.startAtBottom,\n        };\n        this.bottomGrowth = 0;\n        this.minListHeight = 0;\n        this.scrollTimeout = new Timer(100);\n        this.heightUpdateInProgress = false;\n    };\n\n    /**\n     * jump to the top of the content.\n     */\n    public scrollToTop = (): void => {\n        this.getScrollNode().scrollTop = 0;\n        this.saveScrollState();\n    };\n\n    /**\n     * jump to the bottom of the content.\n     */\n    public scrollToBottom = (): void => {\n        // the easiest way to make sure that the scroll state is correctly\n        // saved is to do the scroll, then save the updated state. (Calculating\n        // it ourselves is hard, and we can't rely on an onScroll callback\n        // happening, since there may be no user-visible change here).\n        const sn = this.getScrollNode();\n        sn.scrollTop = sn.scrollHeight;\n        this.saveScrollState();\n    };\n\n    /**\n     * Page up/down.\n     *\n     * @param {number} multiple: -1 to page up, +1 to page down\n     */\n    public scrollRelative = (multiple: -1 | 1): void => {\n        const scrollNode = this.getScrollNode();\n        // TODO: Document what magic number 0.9 is doing\n        const delta = multiple * scrollNode.clientHeight * 0.9;\n        scrollNode.scrollBy(0, delta);\n        this.saveScrollState();\n    };\n\n    /**\n     * Scroll up/down in response to a scroll key\n     * @param {object} ev the keyboard event\n     */\n    public handleScrollKey = (ev: React.KeyboardEvent | KeyboardEvent): void => {\n        const roomAction = getKeyBindingsManager().getRoomAction(ev);\n        switch (roomAction) {\n            case KeyBindingAction.ScrollUp:\n                this.scrollRelative(-1);\n                break;\n            case KeyBindingAction.ScrollDown:\n                this.scrollRelative(1);\n                break;\n            case KeyBindingAction.JumpToFirstMessage:\n                this.scrollToTop();\n                break;\n            case KeyBindingAction.JumpToLatestMessage:\n                this.scrollToBottom();\n                break;\n        }\n    };\n\n    /* Scroll the panel to bring the DOM node with the scroll token\n     * `scrollToken` into view.\n     *\n     * offsetBase gives the reference point for the pixelOffset. 0 means the\n     * top of the container, 1 means the bottom, and fractional values mean\n     * somewhere in the middle. If omitted, it defaults to 0.\n     *\n     * pixelOffset gives the number of pixels *above* the offsetBase that the\n     * node (specifically, the bottom of it) will be positioned. If omitted, it\n     * defaults to 0.\n     */\n    public scrollToToken = (scrollToken: string, pixelOffset = 0, offsetBase = 0): void => {\n        // set the trackedScrollToken, so we can get the node through getTrackedNode\n        this.scrollState = {\n            stuckAtBottom: false,\n            trackedScrollToken: scrollToken,\n        };\n        const trackedNode = this.getTrackedNode();\n        const scrollNode = this.getScrollNode();\n        if (trackedNode) {\n            // set the scrollTop to the position we want.\n            // note though, that this might not succeed if the combination of offsetBase and pixelOffset\n            // would position the trackedNode towards the top of the viewport.\n            // This because when setting the scrollTop only 10 or so events might be loaded,\n            // not giving enough content below the trackedNode to scroll downwards\n            // enough, so it ends up in the top of the viewport.\n            debuglog(\"scrollToken: setting scrollTop\", { offsetBase, pixelOffset, offsetTop: trackedNode.offsetTop });\n            scrollNode.scrollTop = trackedNode.offsetTop - scrollNode.clientHeight * offsetBase + pixelOffset;\n            this.saveScrollState();\n        }\n    };\n\n    private saveScrollState(): void {\n        if (this.props.stickyBottom && this.isAtBottom()) {\n            this.scrollState = { stuckAtBottom: true };\n            debuglog(\"saved stuckAtBottom state\");\n            return;\n        }\n\n        const scrollNode = this.getScrollNode();\n        const viewportBottom = scrollNode.scrollHeight - (scrollNode.scrollTop + scrollNode.clientHeight);\n\n        const itemlist = this.itemlist.current;\n        if (!itemlist) return;\n        const messages = itemlist.children;\n        let node: HTMLElement | null = null;\n\n        // TODO: do a binary search here, as items are sorted by offsetTop\n        // loop backwards, from bottom-most message (as that is the most common case)\n        for (let i = messages.length - 1; i >= 0; --i) {\n            const htmlMessage = messages[i] as HTMLElement;\n            if (!htmlMessage.dataset?.scrollTokens) {\n                // dataset is only specified on HTMLElements\n                continue;\n            }\n            node = htmlMessage;\n            // break at the first message (coming from the bottom)\n            // that has it's offsetTop above the bottom of the viewport.\n            if (this.topFromBottom(node) > viewportBottom) {\n                // Use this node as the scrollToken\n                break;\n            }\n        }\n\n        if (!node) {\n            debuglog(\"unable to save scroll state: found no children in the viewport\");\n            return;\n        }\n        const scrollToken = node!.dataset.scrollTokens?.split(\",\")[0];\n        debuglog(\"saving anchored scroll state to message\", scrollToken);\n        const bottomOffset = this.topFromBottom(node);\n        this.scrollState = {\n            stuckAtBottom: false,\n            trackedNode: node,\n            trackedScrollToken: scrollToken,\n            bottomOffset: bottomOffset,\n            pixelOffset: bottomOffset - viewportBottom, //needed for restoring the scroll position when coming back to the room\n        };\n    }\n\n    private async restoreSavedScrollState(): Promise<void> {\n        const scrollState = this.scrollState;\n\n        if (scrollState.stuckAtBottom) {\n            const sn = this.getScrollNode();\n            if (sn.scrollTop !== sn.scrollHeight) {\n                sn.scrollTop = sn.scrollHeight;\n            }\n        } else if (scrollState.trackedScrollToken) {\n            const itemlist = this.itemlist.current;\n            const trackedNode = this.getTrackedNode();\n            if (trackedNode) {\n                const newBottomOffset = this.topFromBottom(trackedNode);\n                const bottomDiff = newBottomOffset - (scrollState.bottomOffset ?? 0);\n                this.bottomGrowth += bottomDiff;\n                scrollState.bottomOffset = newBottomOffset;\n                const newHeight = `${this.getListHeight()}px`;\n                if (itemlist && itemlist.style.height !== newHeight) {\n                    itemlist.style.height = newHeight;\n                }\n                debuglog(\"balancing height because messages below viewport grew by\", bottomDiff);\n            }\n        }\n        if (!this.heightUpdateInProgress) {\n            this.heightUpdateInProgress = true;\n            try {\n                await this.updateHeight();\n            } finally {\n                this.heightUpdateInProgress = false;\n            }\n        } else {\n            debuglog(\"not updating height because request already in progress\");\n        }\n    }\n\n    // need a better name that also indicates this will change scrollTop? Rebalance height? Reveal content?\n    private async updateHeight(): Promise<void> {\n        // wait until user has stopped scrolling\n        if (this.scrollTimeout?.isRunning()) {\n            debuglog(\"updateHeight waiting for scrolling to end ... \");\n            await this.scrollTimeout.finished();\n            debuglog(\"updateHeight actually running now\");\n        } else {\n            debuglog(\"updateHeight running without delay\");\n        }\n\n        // We might have unmounted since the timer finished, so abort if so.\n        if (this.unmounted) {\n            debuglog(\"updateHeight: abort due to unmount\");\n            return;\n        }\n\n        const sn = this.getScrollNode();\n        const itemlist = this.itemlist.current;\n        const contentHeight = this.getMessagesHeight();\n        // Only round to the nearest page when we're basing the height off the content, not off the scrollNode height\n        // otherwise it'll cause too much overscroll which makes it possible to entirely scroll content off-screen.\n        if (contentHeight < sn.clientHeight) {\n            this.minListHeight = sn.clientHeight;\n        } else {\n            this.minListHeight = Math.ceil(contentHeight / PAGE_SIZE) * PAGE_SIZE;\n        }\n        this.bottomGrowth = 0;\n        const newHeight = `${this.getListHeight()}px`;\n\n        const scrollState = this.scrollState;\n        if (scrollState.stuckAtBottom) {\n            if (itemlist && itemlist.style.height !== newHeight) {\n                itemlist.style.height = newHeight;\n            }\n            if (sn.scrollTop !== sn.scrollHeight) {\n                sn.scrollTop = sn.scrollHeight;\n            }\n            debuglog(\"updateHeight to\", newHeight);\n        } else if (scrollState.trackedScrollToken) {\n            const trackedNode = this.getTrackedNode();\n            // if the timeline has been reloaded\n            // this can be called before scrollToBottom or whatever has been called\n            // so don't do anything if the node has disappeared from\n            // the currently filled piece of the timeline\n            if (trackedNode) {\n                const oldTop = trackedNode.offsetTop;\n                if (itemlist && itemlist.style.height !== newHeight) {\n                    itemlist.style.height = newHeight;\n                }\n                const newTop = trackedNode.offsetTop;\n                const topDiff = newTop - oldTop;\n                // important to scroll by a relative amount as\n                // reading scrollTop and then setting it might\n                // yield out of date values and cause a jump\n                // when setting it\n                sn.scrollBy(0, topDiff);\n                debuglog(\"updateHeight to\", { newHeight, topDiff });\n            }\n        }\n    }\n\n    private getTrackedNode(): HTMLElement | undefined {\n        const scrollState = this.scrollState;\n        const trackedNode = scrollState.trackedNode;\n\n        if (!trackedNode?.parentElement && this.itemlist.current) {\n            let node: HTMLElement | undefined = undefined;\n            const messages = this.itemlist.current.children;\n            const scrollToken = scrollState.trackedScrollToken;\n\n            for (let i = messages.length - 1; i >= 0; --i) {\n                const m = messages[i] as HTMLElement;\n                // 'data-scroll-tokens' is a DOMString of comma-separated scroll tokens\n                // There might only be one scroll token\n                if (scrollToken && m.dataset.scrollTokens?.split(\",\").includes(scrollToken!)) {\n                    node = m;\n                    break;\n                }\n            }\n            if (node) {\n                debuglog(\"had to find tracked node again for token:\", scrollState.trackedScrollToken);\n            }\n            scrollState.trackedNode = node;\n        }\n\n        if (!scrollState.trackedNode) {\n            debuglog(\"No node with token:\", scrollState.trackedScrollToken);\n            return;\n        }\n\n        return scrollState.trackedNode;\n    }\n\n    private getListHeight(): number {\n        return this.bottomGrowth + this.minListHeight;\n    }\n\n    private getMessagesHeight(): number {\n        const itemlist = this.itemlist.current;\n        const lastNode = itemlist?.lastElementChild as HTMLElement;\n        const lastNodeBottom = lastNode ? lastNode.offsetTop + lastNode.clientHeight : 0;\n        const firstNodeTop = (itemlist?.firstElementChild as HTMLElement)?.offsetTop ?? 0;\n        // 18 is itemlist padding\n        return lastNodeBottom - firstNodeTop + 18 * 2;\n    }\n\n    private topFromBottom(node: HTMLElement): number {\n        if (!this.itemlist.current) return -1;\n        // current capped height - distance from top = distance from bottom of container to top of tracked element\n        return this.itemlist.current.clientHeight - node.offsetTop;\n    }\n\n    /* get the DOM node which has the scrollTop property we care about for our\n     * message panel.\n     */\n    private getScrollNode(): HTMLDivElement {\n        if (this.unmounted) {\n            // this shouldn't happen, but when it does, turn the NPE into\n            // something more meaningful.\n            throw new Error(\"ScrollPanel.getScrollNode called when unmounted\");\n        }\n\n        if (!this.divScroll) {\n            // Likewise, we should have the ref by this point, but if not\n            // turn the NPE into something meaningful.\n            throw new Error(\"ScrollPanel.getScrollNode called before AutoHideScrollbar ref collected\");\n        }\n\n        return this.divScroll;\n    }\n\n    private collectScroll = (divScroll: HTMLDivElement | null): void => {\n        this.divScroll = divScroll;\n    };\n\n    /**\n    Mark the bottom offset of the last tile, so we can balance it out when\n    anything below it changes, by calling updatePreventShrinking, to keep\n    the same minimum bottom offset, effectively preventing the timeline to shrink.\n    */\n    public preventShrinking = (): void => {\n        const messageList = this.itemlist.current;\n        const tiles = messageList?.children;\n        if (!tiles) {\n            return;\n        }\n        let lastTileNode;\n        for (let i = tiles.length - 1; i >= 0; i--) {\n            const node = tiles[i] as HTMLElement;\n            if (node.dataset.scrollTokens) {\n                lastTileNode = node;\n                break;\n            }\n        }\n        if (!lastTileNode) {\n            return;\n        }\n        this.clearPreventShrinking();\n        const offsetFromBottom = messageList.clientHeight - (lastTileNode.offsetTop + lastTileNode.clientHeight);\n        this.preventShrinkingState = {\n            offsetFromBottom: offsetFromBottom,\n            offsetNode: lastTileNode,\n        };\n        debuglog(\"prevent shrinking, last tile \", offsetFromBottom, \"px from bottom\");\n    };\n\n    /** Clear shrinking prevention. Used internally, and when the timeline is reloaded. */\n    public clearPreventShrinking = (): void => {\n        const messageList = this.itemlist.current;\n        const balanceElement = messageList && messageList.parentElement;\n        if (balanceElement) balanceElement.style.removeProperty(\"paddingBottom\");\n        this.preventShrinkingState = null;\n        debuglog(\"prevent shrinking cleared\");\n    };\n\n    /**\n    update the container padding to balance\n    the bottom offset of the last tile since\n    preventShrinking was called.\n    Clears the prevent-shrinking state ones the offset\n    from the bottom of the marked tile grows larger than\n    what it was when marking.\n    */\n    public updatePreventShrinking = (): void => {\n        if (this.preventShrinkingState && this.itemlist.current) {\n            const sn = this.getScrollNode();\n            const scrollState = this.scrollState;\n            const messageList = this.itemlist.current;\n            const { offsetNode, offsetFromBottom } = this.preventShrinkingState;\n            // element used to set paddingBottom to balance the typing notifs disappearing\n            const balanceElement = messageList.parentElement;\n            // if the offsetNode got unmounted, clear\n            let shouldClear = !offsetNode.parentElement;\n            // also if 200px from bottom\n            if (!shouldClear && !scrollState.stuckAtBottom) {\n                const spaceBelowViewport = sn.scrollHeight - (sn.scrollTop + sn.clientHeight);\n                shouldClear = spaceBelowViewport >= 200;\n            }\n            // try updating if not clearing\n            if (!shouldClear) {\n                const currentOffset = messageList.clientHeight - (offsetNode.offsetTop + offsetNode.clientHeight);\n                const offsetDiff = offsetFromBottom - currentOffset;\n                if (offsetDiff > 0 && balanceElement) {\n                    balanceElement.style.paddingBottom = `${offsetDiff}px`;\n                    debuglog(\"update prevent shrinking \", offsetDiff, \"px from bottom\");\n                } else if (offsetDiff < 0) {\n                    shouldClear = true;\n                }\n            }\n            if (shouldClear) {\n                this.clearPreventShrinking();\n            }\n        }\n    };\n\n    public render(): ReactNode {\n        // TODO: the classnames on the div and ol could do with being updated to\n        // reflect the fact that we don't necessarily contain a list of messages.\n        // it's not obvious why we have a separate div and ol anyway.\n\n        // give the <ol> an explicit role=list because Safari+VoiceOver seems to think an ordered-list with\n        // list-style-type: none; is no longer a list\n        return (\n            <AutoHideScrollbar\n                wrappedRef={this.collectScroll}\n                onScroll={this.onScroll}\n                className={`mx_ScrollPanel ${this.props.className}`}\n                style={this.props.style}\n            >\n                {this.props.fixedChildren}\n                <div className=\"mx_RoomView_messageListWrapper\">\n                    <ol ref={this.itemlist} className=\"mx_RoomView_MessageList\" aria-live=\"polite\">\n                        {this.props.children}\n                    </ol>\n                </div>\n            </AutoHideScrollbar>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef, type HTMLProps } from \"react\";\nimport { throttle } from \"lodash\";\nimport classNames from \"classnames\";\nimport { CloseIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport AccessibleButton from \"../../components/views/elements/AccessibleButton\";\nimport { getKeyBindingsManager } from \"../../KeyBindingsManager\";\nimport { KeyBindingAction } from \"../../accessibility/KeyboardShortcuts\";\n\ninterface IProps extends HTMLProps<HTMLInputElement> {\n    onSearch: (query: string) => void;\n    onCleared?: (source?: string) => void;\n    onKeyDown?: (ev: React.KeyboardEvent) => void;\n    onFocus?: (ev: React.FocusEvent) => void;\n    onBlur?: (ev: React.FocusEvent) => void;\n    className?: string;\n    placeholder: string;\n    blurredPlaceholder?: string;\n    autoFocus?: boolean;\n    initialValue?: string;\n    collapsed?: boolean;\n}\n\ninterface IState {\n    searchTerm: string;\n    blurred: boolean;\n}\n\nexport default class SearchBox extends React.Component<IProps, IState> {\n    private search = createRef<HTMLInputElement>();\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            searchTerm: props.initialValue || \"\",\n            blurred: true,\n        };\n    }\n\n    private onChange = (): void => {\n        if (!this.search.current) return;\n        this.setState({ searchTerm: this.search.current.value });\n        this.onSearch();\n    };\n\n    private onSearch = throttle(\n        (): void => {\n            this.props.onSearch(this.search.current?.value ?? \"\");\n        },\n        200,\n        { trailing: true, leading: true },\n    );\n\n    private onKeyDown = (ev: React.KeyboardEvent): void => {\n        const action = getKeyBindingsManager().getAccessibilityAction(ev);\n        switch (action) {\n            case KeyBindingAction.Escape:\n                this.clearSearch(\"keyboard\");\n                break;\n        }\n        if (this.props.onKeyDown) this.props.onKeyDown(ev);\n    };\n\n    private onFocus = (ev: React.FocusEvent): void => {\n        this.setState({ blurred: false });\n        (ev.target as HTMLInputElement).select();\n        if (this.props.onFocus) {\n            this.props.onFocus(ev);\n        }\n    };\n\n    private onBlur = (ev: React.FocusEvent): void => {\n        this.setState({ blurred: true });\n        if (this.props.onBlur) {\n            this.props.onBlur(ev);\n        }\n    };\n\n    private clearSearch(source?: string): void {\n        if (this.search.current) this.search.current.value = \"\";\n        this.onChange();\n        this.props.onCleared?.(source);\n    }\n\n    public render(): React.ReactNode {\n        /* eslint @typescript-eslint/no-unused-vars: [\"error\", { \"ignoreRestSiblings\": true }] */\n        const {\n            onSearch,\n            onCleared,\n            onKeyDown,\n            onFocus,\n            onBlur,\n            className = \"\",\n            placeholder,\n            blurredPlaceholder,\n            autoFocus,\n            initialValue,\n            collapsed,\n            ...props\n        } = this.props;\n\n        // check for collapsed here and\n        // not at parent so we keep\n        // searchTerm in our state\n        // when collapsing and expanding\n        if (collapsed) {\n            return null;\n        }\n        const clearButton =\n            !this.state.blurred || this.state.searchTerm ? (\n                <AccessibleButton\n                    key=\"button\"\n                    tabIndex={-1}\n                    className=\"mx_SearchBox_closeButton\"\n                    onClick={() => {\n                        this.clearSearch(\"button\");\n                    }}\n                >\n                    <CloseIcon />\n                </AccessibleButton>\n            ) : undefined;\n\n        // show a shorter placeholder when blurred, if requested\n        // this is used for the room filter field that has\n        // the explore button next to it when blurred\n        return (\n            <div className={classNames(\"mx_SearchBox\", \"mx_textinput\", { mx_SearchBox_blurred: this.state.blurred })}>\n                <input\n                    {...props}\n                    key=\"searchfield\"\n                    type=\"text\"\n                    ref={this.search}\n                    className={\"mx_textinput_icon mx_textinput_search \" + className}\n                    value={this.state.searchTerm}\n                    onFocus={this.onFocus}\n                    onChange={this.onChange}\n                    onKeyDown={this.onKeyDown}\n                    onBlur={this.onBlur}\n                    placeholder={this.state.blurred ? blurredPlaceholder || placeholder : placeholder}\n                    autoComplete=\"off\"\n                    autoFocus={this.props.autoFocus}\n                    data-testid=\"searchbox-input\"\n                />\n                {clearButton}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2025 Element Creations Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\n\nimport AccessibleButton from \"../views/elements/AccessibleButton\";\n\nconst SpacePillButton: React.FC<{\n    title: string;\n    icon: JSX.Element;\n    description: string;\n    onClick(): void;\n}> = ({ title, icon, description, onClick }) => {\n    return (\n        <AccessibleButton className=\"mx_SpacePillButton\" onClick={onClick}>\n            {icon}\n            {title}\n            <div>{description}</div>\n        </AccessibleButton>\n    );\n};\n\nexport default SpacePillButton;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 , 2024 The Matrix.org Foundation C.I.C.\nCopyright 2019 New Vector Ltd\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport classNames from \"classnames\";\n\nimport { _t } from \"../../languageHandler\";\nimport AutoHideScrollbar from \"./AutoHideScrollbar\";\nimport { PosthogScreenTracker, type ScreenName } from \"../../PosthogTrackers\";\nimport { type NonEmptyArray } from \"../../@types/common\";\nimport { RovingAccessibleButton, RovingTabIndexProvider } from \"../../accessibility/RovingTabIndex\";\nimport { useWindowWidth } from \"../../hooks/useWindowWidth\";\n\n/**\n * Represents a tab for the TabbedView.\n */\nexport class Tab<T extends string> {\n    /**\n     * Creates a new tab.\n     * @param {string} id The tab's ID.\n     * @param {string} label The untranslated tab label.\n     * @param {string|JSX.Element} icon An SVG element to use for the tab icon.\n     * @param {JSX.Element} body The JSX for the tab container.\n     * @param {string} screenName The screen name to report to Posthog.\n     * @param {string} labelClassName Additional class to add to the tab label.\n     */\n    public constructor(\n        public readonly id: T,\n        public readonly label: TranslationKey,\n        public readonly icon: JSX.Element | null,\n        public readonly body: JSX.Element,\n        public readonly screenName?: ScreenName,\n        public readonly labelClassName?: string,\n    ) {}\n}\n\nexport function useActiveTabWithDefault<T extends string>(\n    tabs: NonEmptyArray<Tab<string>>,\n    defaultTabID: T,\n    initialTabID?: T,\n): [T, (tabId: T) => void] {\n    const [activeTabId, setActiveTabId] = React.useState(\n        initialTabID && tabs.some((t) => t.id === initialTabID) ? initialTabID : defaultTabID,\n    );\n\n    return [activeTabId, setActiveTabId];\n}\n\nexport enum TabLocation {\n    LEFT = \"left\",\n    TOP = \"top\",\n}\n\ninterface ITabPanelProps<T extends string> {\n    tab: Tab<T>;\n}\n\nfunction domIDForTabID(tabId: string): string {\n    return `mx_tabpanel_${tabId}`;\n}\n\nfunction TabPanel<T extends string>({ tab }: ITabPanelProps<T>): JSX.Element {\n    return (\n        <div\n            className=\"mx_TabbedView_tabPanel\"\n            key={tab.id}\n            id={domIDForTabID(tab.id)}\n            aria-labelledby={`${domIDForTabID(tab.id)}_label`}\n        >\n            <AutoHideScrollbar className=\"mx_TabbedView_tabPanelContent\">{tab.body}</AutoHideScrollbar>\n        </div>\n    );\n}\n\ninterface ITabLabelProps<T extends string> {\n    tab: Tab<T>;\n    isActive: boolean;\n    showToolip: boolean;\n    onClick: () => void;\n}\n\nfunction TabLabel<T extends string>({ tab, isActive, showToolip, onClick }: ITabLabelProps<T>): JSX.Element {\n    const classes = classNames(\"mx_TabbedView_tabLabel\", tab.labelClassName, {\n        mx_TabbedView_tabLabel_active: isActive,\n    });\n\n    let tabIcon: JSX.Element | undefined;\n    if (tab.icon) {\n        tabIcon = tab.icon;\n    }\n\n    const id = domIDForTabID(tab.id);\n\n    const label = _t(tab.label);\n    return (\n        <RovingAccessibleButton\n            className={classes}\n            onClick={onClick}\n            data-testid={`settings-tab-${tab.id}`}\n            role=\"tab\"\n            aria-selected={isActive}\n            aria-controls={id}\n            element=\"li\"\n            title={showToolip ? label : undefined}\n        >\n            {tabIcon}\n            <span className=\"mx_TabbedView_tabLabel_text\" id={`${id}_label`}>\n                {label}\n            </span>\n        </RovingAccessibleButton>\n    );\n}\n\ninterface IProps<T extends string> {\n    // An array of objects representign tabs that the tabbed view will display.\n    tabs: NonEmptyArray<Tab<T>>;\n    // The ID of the tab to show\n    activeTabId: T;\n    // The location of the tabs, dictating the layout of the TabbedView.\n    tabLocation?: TabLocation;\n    // A callback that is called when the active tab should change\n    onChange: (tabId: T) => void;\n    // The screen name to report to Posthog.\n    screenName?: ScreenName;\n    /**\n     * If true, the layout of the tabbed view will be responsive to the viewport size (eg, just showing icons\n     * instead of names of tabs).\n     * Only applies if `tabLocation === TabLocation.LEFT`.\n     * Default: false.\n     */\n    responsive?: boolean;\n}\n\n/**\n * A tabbed view component. Given objects representing content with titles, displays\n * them in a tabbed view where the user can select which one of the items to view at once.\n */\nexport default function TabbedView<T extends string>(props: IProps<T>): JSX.Element {\n    const tabLocation = props.tabLocation ?? TabLocation.LEFT;\n\n    const getTabById = (id: T): Tab<T> | undefined => {\n        return props.tabs.find((tab) => tab.id === id);\n    };\n\n    const windowWidth = useWindowWidth();\n\n    const labels = props.tabs.map((tab) => (\n        <TabLabel\n            key={\"tab_label_\" + tab.id}\n            tab={tab}\n            isActive={tab.id === props.activeTabId}\n            onClick={() => props.onChange(tab.id)}\n            // This should be the same as the the CSS breakpoint at which the tab labels are hidden\n            showToolip={windowWidth < 1024 && tabLocation == TabLocation.LEFT}\n        />\n    ));\n    const tab = getTabById(props.activeTabId);\n    const panel = tab ? <TabPanel tab={tab} /> : null;\n\n    const tabbedViewClasses = classNames({\n        mx_TabbedView: true,\n        mx_TabbedView_tabsOnLeft: tabLocation == TabLocation.LEFT,\n        mx_TabbedView_tabsOnTop: tabLocation == TabLocation.TOP,\n        mx_TabbedView_responsive: props.responsive,\n    });\n\n    const screenName = tab?.screenName ?? props.screenName;\n\n    return (\n        <div className={tabbedViewClasses}>\n            {screenName && <PosthogScreenTracker screenName={screenName} />}\n            <RovingTabIndexProvider\n                handleLoop\n                handleHomeEnd\n                handleLeftRight={tabLocation == TabLocation.TOP}\n                handleUpDown={tabLocation == TabLocation.LEFT}\n            >\n                {({ onKeyDownHandler }) => (\n                    <ul\n                        className=\"mx_TabbedView_tabLabels\"\n                        role=\"tablist\"\n                        aria-orientation={tabLocation == TabLocation.LEFT ? \"vertical\" : \"horizontal\"}\n                        onKeyDown={onKeyDownHandler}\n                    >\n                        {labels}\n                    </ul>\n                )}\n            </RovingTabIndexProvider>\n            {panel}\n        </div>\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport UIStore, { UI_EVENTS } from \"../stores/UIStore\";\n\n/**\n * Hook that gets the width of the viewport using UIStore\n *\n * @returns the current window width\n */\nexport const useWindowWidth = (): number => {\n    const [width, setWidth] = React.useState(UIStore.instance.windowWidth);\n\n    React.useEffect(() => {\n        UIStore.instance.on(UI_EVENTS.Resize, () => {\n            setWidth(UIStore.instance.windowWidth);\n        });\n\n        return () => {\n            UIStore.instance.removeListener(UI_EVENTS.Resize, () => {\n                setWidth(UIStore.instance.windowWidth);\n            });\n        };\n    }, []);\n\n    return width;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2015, 2016 , 2019, 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport SyntaxHighlight from \"../views/elements/SyntaxHighlight\";\nimport { _t } from \"../../languageHandler\";\nimport MatrixClientContext from \"../../contexts/MatrixClientContext\";\nimport { canEditContent } from \"../../utils/EventUtils\";\nimport { MatrixClientPeg } from \"../../MatrixClientPeg\";\nimport BaseDialog from \"../views/dialogs/BaseDialog\";\nimport { DevtoolsContext } from \"../views/dialogs/devtools/BaseTool\";\nimport { StateEventEditor } from \"../views/dialogs/devtools/RoomState\";\nimport { stringify, TimelineEventEditor } from \"../views/dialogs/devtools/Event\";\nimport CopyableText from \"../views/elements/CopyableText\";\n\ninterface IProps {\n    mxEvent: MatrixEvent; // the MatrixEvent associated with the context menu\n    ignoreEdits?: boolean;\n    onFinished(): void;\n}\n\ninterface IState {\n    isEditing: boolean;\n}\n\nexport default class ViewSource extends React.Component<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            isEditing: false,\n        };\n    }\n\n    private onBack = (): void => {\n        // TODO: refresh the \"Event ID:\" modal header\n        this.setState({ isEditing: false });\n    };\n\n    private onEdit(): void {\n        this.setState({ isEditing: true });\n    }\n\n    // returns the dialog body for viewing the event source\n    private viewSourceContent(): JSX.Element {\n        let mxEvent = this.props.mxEvent.replacingEvent() || this.props.mxEvent; // show the replacing event, not the original, if it is an edit\n        if (this.props.ignoreEdits) {\n            mxEvent = this.props.mxEvent;\n        }\n\n        const isEncrypted = mxEvent.isEncrypted();\n        // @ts-ignore\n        const decryptedEventSource = mxEvent.clearEvent; // FIXME: clearEvent is private\n        const originalEventSource = mxEvent.event;\n        const copyOriginalFunc = (): string => {\n            return stringify(originalEventSource);\n        };\n        if (isEncrypted) {\n            const copyDecryptedFunc = (): string => {\n                return stringify(decryptedEventSource || {});\n            };\n            return (\n                <>\n                    <details open className=\"mx_ViewSource_details\">\n                        <summary>\n                            <span className=\"mx_ViewSource_heading\">\n                                {_t(\"devtools|view_source_decrypted_event_source\")}\n                            </span>\n                        </summary>\n                        {decryptedEventSource ? (\n                            <CopyableText getTextToCopy={copyDecryptedFunc}>\n                                <SyntaxHighlight language=\"json\">{stringify(decryptedEventSource)}</SyntaxHighlight>\n                            </CopyableText>\n                        ) : (\n                            <div>{_t(\"devtools|view_source_decrypted_event_source_unavailable\")}</div>\n                        )}\n                    </details>\n                    <details className=\"mx_ViewSource_details\">\n                        <summary>\n                            <span className=\"mx_ViewSource_heading\">{_t(\"devtools|original_event_source\")}</span>\n                        </summary>\n                        <CopyableText getTextToCopy={copyOriginalFunc}>\n                            <SyntaxHighlight language=\"json\">{stringify(originalEventSource)}</SyntaxHighlight>\n                        </CopyableText>\n                    </details>\n                </>\n            );\n        } else {\n            return (\n                <>\n                    <div className=\"mx_ViewSource_heading\">{_t(\"devtools|original_event_source\")}</div>\n                    <CopyableText getTextToCopy={copyOriginalFunc}>\n                        <SyntaxHighlight language=\"json\">{stringify(originalEventSource)}</SyntaxHighlight>\n                    </CopyableText>\n                </>\n            );\n        }\n    }\n\n    // returns the SendCustomEvent component prefilled with the correct details\n    private editSourceContent(): JSX.Element {\n        const mxEvent = this.props.mxEvent.replacingEvent() || this.props.mxEvent; // show the replacing event, not the original, if it is an edit\n\n        const isStateEvent = mxEvent.isState();\n        const roomId = mxEvent.getRoomId();\n\n        if (isStateEvent) {\n            return (\n                <MatrixClientContext.Consumer>\n                    {(cli) => (\n                        <DevtoolsContext.Provider value={{ room: cli.getRoom(roomId)! }}>\n                            <StateEventEditor onBack={this.onBack} mxEvent={mxEvent} />\n                        </DevtoolsContext.Provider>\n                    )}\n                </MatrixClientContext.Consumer>\n            );\n        }\n\n        return (\n            <MatrixClientContext.Consumer>\n                {(cli) => (\n                    <DevtoolsContext.Provider value={{ room: cli.getRoom(roomId)! }}>\n                        <TimelineEventEditor onBack={this.onBack} mxEvent={mxEvent} />\n                    </DevtoolsContext.Provider>\n                )}\n            </MatrixClientContext.Consumer>\n        );\n    }\n\n    private canSendStateEvent(mxEvent: MatrixEvent): boolean {\n        const cli = MatrixClientPeg.safeGet();\n        const room = cli.getRoom(mxEvent.getRoomId());\n        return !!room?.currentState.mayClientSendStateEvent(mxEvent.getType(), cli);\n    }\n\n    public render(): React.ReactNode {\n        const mxEvent = this.props.mxEvent.replacingEvent() || this.props.mxEvent; // show the replacing event, not the original, if it is an edit\n\n        const isEditing = this.state.isEditing;\n        const roomId = mxEvent.getRoomId()!;\n        const eventId = mxEvent.getId()!;\n        const canEdit = mxEvent.isState()\n            ? this.canSendStateEvent(mxEvent)\n            : canEditContent(MatrixClientPeg.safeGet(), this.props.mxEvent);\n        return (\n            <BaseDialog className=\"mx_ViewSource\" onFinished={this.props.onFinished} title={_t(\"action|view_source\")}>\n                <div className=\"mx_ViewSource_header\">\n                    <CopyableText getTextToCopy={() => roomId} border={false}>\n                        {_t(\"devtools|room_id\", { roomId })}\n                    </CopyableText>\n                    <CopyableText getTextToCopy={() => eventId} border={false}>\n                        {_t(\"devtools|event_id\", { eventId })}\n                    </CopyableText>\n                    {mxEvent.threadRootId && (\n                        <CopyableText getTextToCopy={() => mxEvent.threadRootId!} border={false}>\n                            {_t(\"devtools|thread_root_id\", {\n                                threadRootId: mxEvent.threadRootId,\n                            })}\n                        </CopyableText>\n                    )}\n                </div>\n                {isEditing ? this.editSourceContent() : this.viewSourceContent()}\n                {!isEditing && canEdit && (\n                    <div className=\"mx_Dialog_buttons\">\n                        <button onClick={() => this.onEdit()}>{_t(\"action|edit\")}</button>\n                    </div>\n                )}\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { createContext, type Dispatch, type Reducer, type ReducerState } from \"react\";\n\nimport type { AuthHeaderReducer } from \"./AuthHeaderProvider\";\n\ntype ReducerAction<R extends Reducer<any, any>> = R extends Reducer<any, infer A> ? A : never;\n\ninterface AuthHeaderContextType {\n    state: ReducerState<AuthHeaderReducer>;\n    dispatch: Dispatch<ReducerAction<AuthHeaderReducer>>;\n}\n\nexport const AuthHeaderContext = createContext<AuthHeaderContextType | undefined>(undefined);\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { isEqual } from \"lodash\";\nimport React, { type JSX, type ComponentProps, type PropsWithChildren, type Reducer, useReducer } from \"react\";\n\nimport { AuthHeaderContext } from \"./AuthHeaderContext\";\nimport { type AuthHeaderModifier } from \"./AuthHeaderModifier\";\n\nexport enum AuthHeaderActionType {\n    Add,\n    Remove,\n}\n\ninterface AuthHeaderAction {\n    type: AuthHeaderActionType;\n    value: ComponentProps<typeof AuthHeaderModifier>;\n}\n\nexport type AuthHeaderReducer = Reducer<ComponentProps<typeof AuthHeaderModifier>[], AuthHeaderAction>;\n\nexport function AuthHeaderProvider({ children }: PropsWithChildren): JSX.Element {\n    const [state, dispatch] = useReducer<ComponentProps<typeof AuthHeaderModifier>[], [AuthHeaderAction]>(\n        (state: ComponentProps<typeof AuthHeaderModifier>[], action: AuthHeaderAction) => {\n            switch (action.type) {\n                case AuthHeaderActionType.Add:\n                    return [action.value, ...state];\n                case AuthHeaderActionType.Remove:\n                    return state.length && isEqual(state[0], action.value) ? state.slice(1) : state;\n            }\n        },\n        [] as ComponentProps<typeof AuthHeaderModifier>[],\n    );\n    return <AuthHeaderContext.Provider value={{ state, dispatch }}>{children}</AuthHeaderContext.Provider>;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type HTMLAttributes, type ReactNode } from \"react\";\nimport { PlayPauseButton as SharedPlayPauseButton } from \"@element-hq/web-shared-components\";\n\nimport { type Playback, PlaybackState } from \"../../../audio/Playback\";\n\ntype Props = HTMLAttributes<HTMLButtonElement> & {\n    // Playback instance to manipulate. Cannot change during the component lifecycle.\n    playback: Playback;\n\n    // The playback phase to render. Able to change during the component lifecycle.\n    playbackPhase: PlaybackState;\n};\n\n/**\n * Displays a play/pause button (activating the play/pause function of the recorder)\n * to be displayed in reference to a recording.\n */\nexport default class PlayPauseButton extends React.PureComponent<Props> {\n    private onClick = (): void => {\n        void this.toggleState();\n    };\n\n    public async toggleState(): Promise<void> {\n        await this.props.playback.toggle();\n    }\n\n    public render(): ReactNode {\n        const { playback, playbackPhase, ...restProps } = this.props;\n\n        return (\n            <SharedPlayPauseButton\n                data-testid=\"play-pause-button\"\n                className=\"mx_PlayPauseButton\"\n                togglePlay={this.onClick}\n                playing={playback.isPlaying}\n                disabled={playbackPhase === PlaybackState.Decoding}\n                {...restProps}\n            />\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { Clock } from \"@element-hq/web-shared-components\";\n\nimport { type Playback, PlaybackState } from \"../../../audio/Playback\";\nimport { UPDATE_EVENT } from \"../../../stores/AsyncStore\";\n\ninterface IProps {\n    playback: Playback;\n\n    // The default number of seconds to show when the playback has completed or\n    // has not started. Not used during playback, even when paused. Defaults to\n    // clip duration length.\n    defaultDisplaySeconds?: number;\n}\n\ninterface IState {\n    seconds: number;\n    durationSeconds: number;\n    playbackPhase: PlaybackState;\n}\n\n/**\n * A clock for a playback of a recording.\n */\nexport default class PlaybackClock extends React.PureComponent<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            seconds: this.props.playback.clockInfo.timeSeconds,\n            // we track the duration on state because we won't really know what the clip duration\n            // is until the first time update, and as a PureComponent we are trying to dedupe state\n            // updates as much as possible. This is just the easiest way to avoid a forceUpdate() or\n            // member property to track \"did we get a duration\".\n            durationSeconds: this.props.playback.clockInfo.durationSeconds,\n            playbackPhase: PlaybackState.Stopped, // assume not started, so full clock\n        };\n    }\n\n    public componentDidMount(): void {\n        this.props.playback.on(UPDATE_EVENT, this.onPlaybackUpdate);\n        this.props.playback.clockInfo.liveData.onUpdate(this.onTimeUpdate);\n    }\n\n    private onPlaybackUpdate = (ev: PlaybackState): void => {\n        // Convert Decoding -> Stopped because we don't care about the distinction here\n        if (ev === PlaybackState.Decoding) ev = PlaybackState.Stopped;\n        this.setState({ playbackPhase: ev });\n    };\n\n    private onTimeUpdate = (time: number[]): void => {\n        this.setState({ seconds: time[0], durationSeconds: time[1] });\n    };\n\n    public render(): React.ReactNode {\n        let seconds = this.state.seconds;\n        if (this.state.playbackPhase === PlaybackState.Stopped) {\n            if (Number.isFinite(this.props.defaultDisplaySeconds)) {\n                seconds = this.props.defaultDisplaySeconds ?? this.props.playback.durationSeconds;\n            } else {\n                seconds = this.state.durationSeconds;\n            }\n        }\n        return <Clock seconds={seconds} role=\"timer\" />;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021, 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef, type ReactNode } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { type Playback, type PlaybackState } from \"../../../audio/Playback\";\nimport { UPDATE_EVENT } from \"../../../stores/AsyncStore\";\nimport { _t } from \"../../../languageHandler\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport type LegacySeekBar from \"./LegacySeekBar\";\nimport type PlayPauseButton from \"./PlayPauseButton\";\n\nexport interface IProps {\n    // Playback instance to render. Cannot change during component lifecycle: create\n    // an all-new component instead.\n    playback: Playback;\n\n    mediaName?: string;\n}\n\ninterface IState {\n    playbackPhase: PlaybackState;\n    error?: boolean;\n}\n\nexport default abstract class AudioPlayerBase<T extends IProps = IProps> extends React.PureComponent<T, IState> {\n    protected seekRef = createRef<LegacySeekBar>();\n    protected playPauseRef = createRef<PlayPauseButton>();\n\n    public constructor(props: T) {\n        super(props);\n\n        // Playback instances can be reused in the composer\n        this.state = {\n            playbackPhase: this.props.playback.currentState,\n        };\n    }\n\n    public componentDidMount(): void {\n        // We don't need to de-register: the class handles this for us internally\n        this.props.playback.on(UPDATE_EVENT, this.onPlaybackUpdate);\n\n        // Don't wait for the promise to complete - it will emit a progress update when it\n        // is done, and it's not meant to take long anyhow.\n        this.props.playback.prepare().catch((e) => {\n            logger.error(\"Error processing audio file:\", e);\n            this.setState({ error: true });\n        });\n    }\n\n    protected onKeyDown = (ev: React.KeyboardEvent): void => {\n        let handled = true;\n        const action = getKeyBindingsManager().getAccessibilityAction(ev);\n\n        switch (action) {\n            case KeyBindingAction.Space:\n                this.playPauseRef.current?.toggleState();\n                break;\n            case KeyBindingAction.ArrowLeft:\n                this.seekRef.current?.left();\n                break;\n            case KeyBindingAction.ArrowRight:\n                this.seekRef.current?.right();\n                break;\n            default:\n                handled = false;\n                break;\n        }\n\n        // stopPropagation() prevents the FocusComposer catch-all from triggering,\n        // but we need to do it on key down instead of press (even though the user\n        // interaction is typically on press).\n        if (handled) {\n            ev.stopPropagation();\n        }\n    };\n\n    private onPlaybackUpdate = (ev: PlaybackState): void => {\n        this.setState({ playbackPhase: ev });\n    };\n\n    protected abstract renderComponent(): ReactNode;\n\n    public render(): ReactNode {\n        return (\n            <>\n                {this.renderComponent()}\n                {this.state.error && (\n                    <div className=\"text-warning\">{_t(\"timeline|m.audio|error_downloading_audio\")}</div>\n                )}\n            </>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEvent, type CSSProperties, type ReactNode } from \"react\";\nimport { percentageOf } from \"@element-hq/web-shared-components\";\n\nimport { type PlaybackInterface } from \"../../../audio/Playback\";\nimport { MarkedExecution } from \"../../../utils/MarkedExecution\";\nimport { _t } from \"../../../languageHandler\";\n\ninterface IProps {\n    // Playback instance to render. Cannot change during component lifecycle: create\n    // an all-new component instead.\n    playback: PlaybackInterface;\n\n    // Tab index for the underlying component. Useful if the seek bar is in a managed state.\n    // Defaults to zero.\n    tabIndex?: number;\n\n    disabled?: boolean;\n}\n\ninterface IState {\n    percentage: number;\n}\n\ninterface ISeekCSS extends CSSProperties {\n    \"--fillTo\": number;\n}\n\nconst ARROW_SKIP_SECONDS = 5; // arbitrary\n\n/**\n * @deprecated Use {@link SeekBar} instead.\n */\nexport default class LegacySeekBar extends React.PureComponent<IProps, IState> {\n    // We use an animation frame request to avoid overly spamming prop updates, even if we aren't\n    // really using anything demanding on the CSS front.\n\n    private animationFrameFn: MarkedExecution = new MarkedExecution(\n        () => this.doUpdate(),\n        () => requestAnimationFrame(() => this.animationFrameFn.trigger()),\n    );\n\n    public static defaultProps = {\n        tabIndex: 0,\n        disabled: false,\n    };\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            percentage: percentageOf(this.props.playback.timeSeconds, 0, this.props.playback.durationSeconds),\n        };\n    }\n\n    public componentDidMount(): void {\n        // We don't need to de-register: the class handles this for us internally\n        this.props.playback.liveData.onUpdate(() => this.animationFrameFn.mark());\n    }\n\n    private doUpdate(): void {\n        this.setState({\n            percentage: percentageOf(this.props.playback.timeSeconds, 0, this.props.playback.durationSeconds),\n        });\n    }\n\n    public left(): void {\n        // noinspection JSIgnoredPromiseFromCall\n        this.props.playback.skipTo(this.props.playback.timeSeconds - ARROW_SKIP_SECONDS);\n    }\n\n    public right(): void {\n        // noinspection JSIgnoredPromiseFromCall\n        this.props.playback.skipTo(this.props.playback.timeSeconds + ARROW_SKIP_SECONDS);\n    }\n\n    private onChange = (ev: ChangeEvent<HTMLInputElement>): void => {\n        // Thankfully, onChange is only called when the user changes the value, not when we\n        // change the value on the component. We can use this as a reliable \"skip to X\" function.\n        //\n        // noinspection JSIgnoredPromiseFromCall\n        this.props.playback.skipTo(Number(ev.target.value) * this.props.playback.durationSeconds);\n    };\n\n    private onMouseDown = (event: React.MouseEvent<Element, MouseEvent>): void => {\n        // do not propagate mouse down events, because these should be handled by the seekbar\n        event.stopPropagation();\n    };\n\n    public render(): ReactNode {\n        // We use a range input to avoid having to re-invent accessibility handling on\n        // a custom set of divs.\n        return (\n            <input\n                type=\"range\"\n                className=\"mx_SeekBar\"\n                tabIndex={this.props.tabIndex}\n                onChange={this.onChange}\n                onMouseDown={this.onMouseDown}\n                min={0}\n                max={1}\n                value={this.state.percentage}\n                step={0.001}\n                style={{ \"--fillTo\": this.state.percentage } as ISeekCSS}\n                disabled={this.props.disabled}\n                aria-label={_t(\"a11y|seek_bar_label\")}\n            />\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { percentageOf } from \"@element-hq/web-shared-components\";\n\nimport { arraySeed, arrayTrimFill } from \"../../../utils/arrays\";\nimport Waveform from \"./Waveform\";\nimport { type Playback } from \"../../../audio/Playback\";\nimport { PLAYBACK_WAVEFORM_SAMPLES } from \"../../../audio/consts\";\n\ninterface IProps {\n    playback: Playback;\n}\n\ninterface IState {\n    heights: number[];\n    progress: number;\n}\n\n/**\n * A waveform which shows the waveform of a previously recorded recording\n */\nexport default class PlaybackWaveform extends React.PureComponent<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            heights: this.toHeights(this.props.playback.waveform),\n            progress: 0, // default no progress\n        };\n    }\n\n    public componentDidMount(): void {\n        this.props.playback.waveformData.onUpdate(this.onWaveformUpdate);\n        this.props.playback.clockInfo.liveData.onUpdate(this.onTimeUpdate);\n    }\n\n    private toHeights(waveform: number[]): number[] {\n        const seed = arraySeed(0, PLAYBACK_WAVEFORM_SAMPLES);\n        return arrayTrimFill(waveform, PLAYBACK_WAVEFORM_SAMPLES, seed);\n    }\n\n    private onWaveformUpdate = (waveform: number[]): void => {\n        this.setState({ heights: this.toHeights(waveform) });\n    };\n\n    private onTimeUpdate = (time: number[]): void => {\n        // Track percentages to a general precision to avoid over-waking the component.\n        const progress = Number(percentageOf(time[0], 0, time[1]).toFixed(3));\n        this.setState({ progress });\n    };\n\n    public render(): React.ReactNode {\n        return <Waveform relHeights={this.state.heights} progress={this.state.progress} />;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021, 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode } from \"react\";\n\nimport PlayPauseButton from \"./PlayPauseButton\";\nimport PlaybackClock from \"./PlaybackClock\";\nimport AudioPlayerBase, { type IProps as IAudioPlayerBaseProps } from \"./AudioPlayerBase\";\nimport LegacySeekBar from \"./LegacySeekBar\";\nimport PlaybackWaveform from \"./PlaybackWaveform\";\nimport { PlaybackState } from \"../../../audio/Playback\";\n\nexport enum PlaybackLayout {\n    /**\n     * Clock on the left side of a waveform, without seek bar.\n     */\n    Composer,\n\n    /**\n     * Clock on the right side of a waveform, with an added seek bar.\n     */\n    Timeline,\n}\n\ninterface IProps extends IAudioPlayerBaseProps {\n    layout?: PlaybackLayout; // Defaults to Timeline layout\n}\n\nexport default class RecordingPlayback extends AudioPlayerBase<IProps> {\n    // This component is rendered in two ways: the composer and timeline. They have different\n    // rendering properties (specifically the difference of a waveform or not).\n\n    private renderComposerLook(): ReactNode {\n        return (\n            <>\n                <PlaybackClock playback={this.props.playback} />\n                <PlaybackWaveform playback={this.props.playback} />\n            </>\n        );\n    }\n\n    private renderTimelineLook(): ReactNode {\n        return (\n            <>\n                <div className=\"mx_RecordingPlayback_timelineLayoutMiddle\">\n                    <PlaybackWaveform playback={this.props.playback} />\n                    <LegacySeekBar\n                        playback={this.props.playback}\n                        tabIndex={0} // allow keyboard users to fall into the seek bar\n                        disabled={this.state.playbackPhase === PlaybackState.Decoding}\n                        ref={this.seekRef}\n                    />\n                </div>\n                <PlaybackClock playback={this.props.playback} />\n            </>\n        );\n    }\n\n    protected renderComponent(): ReactNode {\n        let body: ReactNode;\n        switch (this.props.layout) {\n            case PlaybackLayout.Composer:\n                body = this.renderComposerLook();\n                break;\n            case PlaybackLayout.Timeline: // default is timeline, fall through.\n            default:\n                body = this.renderTimelineLook();\n                break;\n        }\n\n        return (\n            <div\n                className=\"mx_MediaBody mx_VoiceMessagePrimaryContainer\"\n                onKeyDown={this.onKeyDown}\n                data-testid=\"recording-playback\"\n            >\n                <PlayPauseButton\n                    playback={this.props.playback}\n                    playbackPhase={this.state.playbackPhase}\n                    ref={this.playPauseRef}\n                />\n                {body}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type CSSProperties } from \"react\";\nimport classNames from \"classnames\";\n\ninterface WaveformCSSProperties extends CSSProperties {\n    \"--barHeight\": number;\n}\n\ninterface IProps {\n    relHeights: number[]; // relative heights (0-1)\n    progress: number; // percent complete, 0-1, default 100%\n}\n\n/**\n * A simple waveform component. This renders bars (centered vertically) for each\n * height provided in the component properties. Updating the properties will update\n * the rendered waveform.\n *\n * For CSS purposes, a mx_Waveform_bar_100pct class is added when the bar should be\n * \"filled\", as a demonstration of the progress property.\n */\nexport default class Waveform extends React.PureComponent<IProps> {\n    public static defaultProps = {\n        progress: 1,\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <div className=\"mx_Waveform\">\n                {this.props.relHeights.map((h, i) => {\n                    const progress = this.props.progress;\n                    const isCompleteBar = i / this.props.relHeights.length <= progress && progress > 0;\n                    const classes = classNames({\n                        mx_Waveform_bar: true,\n                        mx_Waveform_bar_100pct: isCompleteBar,\n                    });\n                    return (\n                        <span\n                            key={i}\n                            style={\n                                {\n                                    \"--barHeight\": h,\n                                } as WaveformCSSProperties\n                            }\n                            className={classes}\n                        />\n                    );\n                })}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ReactNode, useContext, useEffect } from \"react\";\n\nimport { AuthHeaderContext } from \"./AuthHeaderContext\";\nimport { AuthHeaderActionType } from \"./AuthHeaderProvider\";\n\ninterface Props {\n    title: ReactNode;\n    icon?: ReactNode;\n    hideServerPicker?: boolean;\n}\n\nexport function AuthHeaderModifier(props: Props): null {\n    const context = useContext(AuthHeaderContext);\n    const dispatch = context?.dispatch ?? null;\n    useEffect(() => {\n        if (!dispatch) {\n            return;\n        }\n        dispatch({ type: AuthHeaderActionType.Add, value: props });\n        return () => dispatch({ type: AuthHeaderActionType.Remove, value: props });\n    }, [props, dispatch]);\n    return null;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, createRef } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { _t } from \"../../../languageHandler\";\n\nconst DIV_ID = \"mx_recaptcha\";\n\ninterface ICaptchaFormProps {\n    sitePublicKey: string;\n    onCaptchaResponse: (response: string) => void;\n}\n\ninterface ICaptchaFormState {\n    errorText?: string;\n}\n\n/**\n * A pure UI component which displays a captcha form.\n */\nexport default class CaptchaForm extends React.Component<ICaptchaFormProps, ICaptchaFormState> {\n    public static defaultProps = {\n        onCaptchaResponse: () => {},\n    };\n\n    private captchaWidgetId?: string;\n    private recaptchaContainer = createRef<HTMLDivElement>();\n\n    public constructor(props: ICaptchaFormProps) {\n        super(props);\n\n        this.state = {\n            errorText: undefined,\n        };\n    }\n\n    public componentDidMount(): void {\n        // Just putting a script tag into the returned jsx doesn't work, annoyingly,\n        // so we do this instead.\n        if (this.isRecaptchaReady()) {\n            // already loaded\n            this.onCaptchaLoaded();\n        } else {\n            logger.log(\"Loading recaptcha script...\");\n            window.mxOnRecaptchaLoaded = () => {\n                this.onCaptchaLoaded();\n            };\n            const scriptTag = document.createElement(\"script\");\n            scriptTag.setAttribute(\n                \"src\",\n                `https://www.recaptcha.net/recaptcha/api.js?onload=mxOnRecaptchaLoaded&render=explicit`,\n            );\n            this.recaptchaContainer.current?.appendChild(scriptTag);\n        }\n    }\n\n    public componentWillUnmount(): void {\n        this.resetRecaptcha();\n        // Resettting the captcha does not clear the challenge overlay from the body in android webviews.\n        // Search for an iframe with the challenge src and remove it's topmost ancestor from the body.\n        // TODO: Remove this when the \"mobile_register\" page is retired.\n        const iframes = document.querySelectorAll(\"iframe\");\n        for (const iframe of iframes) {\n            if (iframe.src.includes(\"https://www.recaptcha.net/recaptcha/api2/bframe\")) {\n                let parentBeforeBody: HTMLElement | null = iframe;\n                do {\n                    parentBeforeBody = parentBeforeBody.parentElement;\n                } while (parentBeforeBody?.parentElement && parentBeforeBody.parentElement != document.body);\n                parentBeforeBody?.remove();\n            }\n        }\n    }\n\n    // Borrowed directly from: https://github.com/codeep/react-recaptcha-google/commit/e118fa5670fa268426969323b2e7fe77698376ba\n    private isRecaptchaReady(): boolean {\n        return (\n            typeof window !== \"undefined\" &&\n            typeof global.grecaptcha !== \"undefined\" &&\n            typeof global.grecaptcha.render === \"function\"\n        );\n    }\n\n    private renderRecaptcha(divId: string): void {\n        if (!this.isRecaptchaReady()) {\n            logger.error(\"grecaptcha not loaded!\");\n            throw new Error(\"Recaptcha did not load successfully\");\n        }\n\n        const publicKey = this.props.sitePublicKey;\n        if (!publicKey) {\n            logger.error(\"No public key for recaptcha!\");\n            throw new Error(\"This server has not supplied enough information for Recaptcha authentication\");\n        }\n\n        logger.info(`Rendering to ${divId}`);\n        this.captchaWidgetId = global.grecaptcha?.render(divId, {\n            sitekey: publicKey,\n            callback: this.props.onCaptchaResponse,\n        });\n    }\n\n    private resetRecaptcha(): void {\n        if (this.captchaWidgetId) {\n            global?.grecaptcha?.reset(this.captchaWidgetId);\n        }\n    }\n\n    private onCaptchaLoaded(): void {\n        logger.log(\"Loaded recaptcha script.\");\n        try {\n            this.renderRecaptcha(DIV_ID);\n            // clear error if re-rendered\n            this.setState({\n                errorText: undefined,\n            });\n        } catch (e) {\n            this.setState({\n                errorText: e instanceof Error ? e.message : String(e),\n            });\n        }\n    }\n\n    public render(): React.ReactNode {\n        let error: JSX.Element | undefined;\n        if (this.state.errorText) {\n            error = <div className=\"error\">{this.state.errorText}</div>;\n        }\n\n        return (\n            <div ref={this.recaptchaContainer}>\n                <p>{_t(\"auth|captcha_description\")}</p>\n                <div id={DIV_ID} />\n                {error}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2016-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport classNames from \"classnames\";\nimport { type InternationalisedPolicy, type Terms, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { AuthType, type AuthDict, type IInputs, type IStageStatus } from \"matrix-js-sdk/src/interactive-auth\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport React, { type JSX, type ChangeEvent, createRef, type FormEvent, Fragment } from \"react\";\nimport { Button } from \"@vector-im/compound-web\";\nimport PopOutIcon from \"@vector-im/compound-design-tokens/assets/web/icons/pop-out\";\nimport UserProfileSolidIcon from \"@vector-im/compound-design-tokens/assets/web/icons/user-profile-solid\";\n\nimport EmailPromptIcon from \"../../../../res/img/element-icons/email-prompt.svg\";\nimport { _t } from \"../../../languageHandler\";\nimport { AuthHeaderModifier } from \"../../structures/auth/header/AuthHeaderModifier\";\nimport AccessibleButton, { type AccessibleButtonKind, type ButtonEvent } from \"../elements/AccessibleButton\";\nimport Field from \"../elements/Field\";\nimport Spinner from \"../elements/Spinner\";\nimport CaptchaForm from \"./CaptchaForm\";\nimport { pickBestPolicyLanguage } from \"../../../Terms.ts\";\nimport { EncryptionCardButtons } from \"../settings/encryption/EncryptionCardButtons.tsx\";\nimport { EncryptionCard } from \"../settings/encryption/EncryptionCard.tsx\";\n\n/* This file contains a collection of components which are used by the\n * InteractiveAuth to prompt the user to enter the information needed\n * for an auth stage. (The intention is that they could also be used for other\n * components, such as the registration flow).\n *\n * Call getEntryComponentForLoginType() to get a component suitable for a\n * particular login type. Each component requires the same properties:\n *\n * matrixClient:           A matrix client. May be a different one to the one\n *                         currently being used generally (eg. to register with\n *                         one HS whilst being a guest on another).\n * loginType:              the login type of the auth stage being attempted\n * authSessionId:          session id from the server\n * clientSecret:           The client secret in use for identity server auth sessions\n * stageParams:            params from the server for the stage being attempted\n * errorText:              error message from a previous attempt to authenticate\n * submitAuthDict:         a function which will be called with the new auth dict\n * busy:                   a boolean indicating whether the auth logic is doing something\n *                         the user needs to wait for.\n * inputs:                 Object of inputs provided by the user, as in js-sdk\n *                         interactive-auth\n * stageState:             Stage-specific object used for communicating state information\n *                         to the UI from the state-specific auth logic.\n *                         Defined keys for stages are:\n *                             m.login.email.identity:\n *                              * emailSid: string representing the sid of the active\n *                                          verification session from the identity server,\n *                                          or null if no session is active.\n * fail:                   a function which should be called with an error object if an\n *                         error occurred during the auth stage. This will cause the auth\n *                         session to be failed and the process to go back to the start.\n * setEmailSid:            m.login.email.identity only: a function to be called with the\n *                         email sid after a token is requested.\n * onPhaseChange:          A function which is called when the stage's phase changes. If\n *                         the stage has no phases, call this with DEFAULT_PHASE. Takes\n *                         one argument, the phase, and is always defined/required.\n * continueText:           For stages which have a continue button, the text to use.\n * continueKind:           For stages which have a continue button, the style of button to\n *                         use. For example, 'danger' or 'primary'.\n * onCancel                A function with no arguments which is called by the stage if the\n *                         user knowingly cancelled/dismissed the authentication attempt.\n *\n * Each component may also provide the following functions (beyond the standard React ones):\n *    focus: set the input focus appropriately in the form.\n */\n\nexport const DEFAULT_PHASE = 0;\n\ninterface IAuthEntryProps {\n    matrixClient: MatrixClient;\n    loginType: string;\n    authSessionId?: string;\n    errorText?: string;\n    errorCode?: string;\n    // Is the auth logic currently waiting for something to happen?\n    busy?: boolean;\n    onPhaseChange: (phase: number) => void;\n    submitAuthDict: (auth: AuthDict) => void;\n    requestEmailToken?: () => Promise<void>;\n    fail: (error: Error) => void;\n    clientSecret: string;\n}\n\ninterface IPasswordAuthEntryState {\n    password: string;\n}\n\nexport class PasswordAuthEntry extends React.Component<IAuthEntryProps, IPasswordAuthEntryState> {\n    public static LOGIN_TYPE = AuthType.Password;\n\n    public constructor(props: IAuthEntryProps) {\n        super(props);\n\n        this.state = {\n            password: \"\",\n        };\n    }\n\n    public componentDidMount(): void {\n        this.props.onPhaseChange(DEFAULT_PHASE);\n    }\n\n    private onSubmit = (e: FormEvent): void => {\n        e.preventDefault();\n        if (this.props.busy) return;\n\n        this.props.submitAuthDict({\n            type: AuthType.Password,\n            identifier: {\n                type: \"m.id.user\",\n                user: this.props.matrixClient.credentials.userId,\n            },\n            password: this.state.password,\n        });\n    };\n\n    private onPasswordFieldChange = (ev: ChangeEvent<HTMLInputElement>): void => {\n        // enable the submit button iff the password is non-empty\n        this.setState({\n            password: ev.target.value,\n        });\n    };\n\n    public render(): React.ReactNode {\n        const passwordBoxClass = classNames({\n            error: this.props.errorText,\n        });\n\n        let submitButtonOrSpinner;\n        if (this.props.busy) {\n            submitButtonOrSpinner = <Spinner />;\n        } else {\n            submitButtonOrSpinner = (\n                <input\n                    type=\"submit\"\n                    className=\"mx_Dialog_primary\"\n                    disabled={!this.state.password}\n                    value={_t(\"action|continue\")}\n                />\n            );\n        }\n\n        let errorSection;\n        if (this.props.errorText) {\n            errorSection = (\n                <div className=\"error\" role=\"alert\">\n                    {this.props.errorText}\n                </div>\n            );\n        }\n\n        return (\n            <div>\n                <p>{_t(\"auth|uia|password_prompt\")}</p>\n                <form onSubmit={this.onSubmit} className=\"mx_InteractiveAuthEntryComponents_passwordSection\">\n                    <Field\n                        className={passwordBoxClass}\n                        type=\"password\"\n                        name=\"passwordField\"\n                        label={_t(\"common|password\")}\n                        autoFocus={true}\n                        value={this.state.password}\n                        onChange={this.onPasswordFieldChange}\n                    />\n                    {errorSection}\n                    <div className=\"mx_button_row\">{submitButtonOrSpinner}</div>\n                </form>\n            </div>\n        );\n    }\n}\n\n/* eslint-disable camelcase */\ninterface IRecaptchaAuthEntryProps extends IAuthEntryProps {\n    stageParams?: {\n        public_key?: string;\n    };\n}\n/* eslint-enable camelcase */\n\nexport class RecaptchaAuthEntry extends React.Component<IRecaptchaAuthEntryProps> {\n    public static LOGIN_TYPE = AuthType.Recaptcha;\n\n    public componentDidMount(): void {\n        this.props.onPhaseChange(DEFAULT_PHASE);\n    }\n\n    private onCaptchaResponse = (response: string): void => {\n        this.props.submitAuthDict({\n            type: AuthType.Recaptcha,\n            response: response,\n        });\n    };\n\n    public render(): React.ReactNode {\n        if (this.props.busy) {\n            return <Spinner />;\n        }\n\n        let errorText = this.props.errorText;\n\n        let sitePublicKey: string | undefined;\n        if (!this.props.stageParams || !this.props.stageParams.public_key) {\n            errorText = _t(\"auth|uia|recaptcha_missing_params\");\n        } else {\n            sitePublicKey = this.props.stageParams.public_key;\n        }\n\n        let errorSection: JSX.Element | undefined;\n        if (errorText) {\n            errorSection = (\n                <div className=\"error\" role=\"alert\">\n                    {errorText}\n                </div>\n            );\n        }\n\n        return (\n            <div>\n                {sitePublicKey && (\n                    <CaptchaForm sitePublicKey={sitePublicKey} onCaptchaResponse={this.onCaptchaResponse} />\n                )}\n                {errorSection}\n            </div>\n        );\n    }\n}\n\ninterface ITermsAuthEntryProps extends IAuthEntryProps {\n    stageParams?: Partial<Terms>;\n}\n\ninterface LocalisedPolicyWithId extends InternationalisedPolicy {\n    id: string;\n}\n\ninterface ITermsAuthEntryState {\n    policies: LocalisedPolicyWithId[];\n    toggledPolicies: {\n        [policy: string]: boolean;\n    };\n    errorText?: string;\n}\n\nexport class TermsAuthEntry extends React.Component<ITermsAuthEntryProps, ITermsAuthEntryState> {\n    public static LOGIN_TYPE = AuthType.Terms;\n\n    public constructor(props: ITermsAuthEntryProps) {\n        super(props);\n\n        // example stageParams:\n        //\n        // {\n        //     \"policies\": {\n        //         \"privacy_policy\": {\n        //             \"version\": \"1.0\",\n        //             \"en\": {\n        //                 \"name\": \"Privacy Policy\",\n        //                 \"url\": \"https://example.org/privacy-1.0-en.html\",\n        //             },\n        //             \"fr\": {\n        //                 \"name\": \"Politique de confidentialité\",\n        //                 \"url\": \"https://example.org/privacy-1.0-fr.html\",\n        //             },\n        //         },\n        //         \"other_policy\": { ... },\n        //     }\n        // }\n\n        const allPolicies = this.props.stageParams?.policies || {};\n        const initToggles: Record<string, boolean> = {};\n        const pickedPolicies: {\n            id: string;\n            name: string;\n            url: string;\n        }[] = [];\n        for (const policyId of Object.keys(allPolicies)) {\n            const policy = allPolicies[policyId];\n            const langPolicy = pickBestPolicyLanguage(policy);\n            if (!langPolicy) throw new Error(\"Failed to find a policy to show the user\");\n\n            initToggles[policyId] = false;\n\n            pickedPolicies.push({\n                id: policyId,\n                name: langPolicy.name,\n                url: langPolicy.url,\n            });\n        }\n\n        this.state = {\n            toggledPolicies: initToggles,\n            policies: pickedPolicies,\n        };\n    }\n\n    public componentDidMount(): void {\n        this.props.onPhaseChange(DEFAULT_PHASE);\n    }\n\n    private togglePolicy(policyId: string): void {\n        const newToggles: Record<string, boolean> = {};\n        for (const policy of this.state.policies) {\n            let checked = this.state.toggledPolicies[policy.id];\n            if (policy.id === policyId) checked = !checked;\n\n            newToggles[policy.id] = checked;\n        }\n        this.setState({ toggledPolicies: newToggles });\n    }\n\n    private trySubmit = (): void => {\n        let allChecked = true;\n        for (const policy of this.state.policies) {\n            const checked = this.state.toggledPolicies[policy.id];\n            allChecked = allChecked && checked;\n        }\n\n        if (allChecked) {\n            this.props.submitAuthDict({ type: AuthType.Terms });\n        } else {\n            this.setState({ errorText: _t(\"auth|uia|terms_invalid\") });\n        }\n    };\n\n    public render(): React.ReactNode {\n        if (this.props.busy) {\n            return <Spinner />;\n        }\n\n        const checkboxes: JSX.Element[] = [];\n        let allChecked = true;\n        for (const policy of this.state.policies) {\n            const checked = this.state.toggledPolicies[policy.id];\n            allChecked = allChecked && checked;\n\n            checkboxes.push(\n                // XXX: replace with StyledCheckbox\n                <label key={\"policy_checkbox_\" + policy.id} className=\"mx_InteractiveAuthEntryComponents_termsPolicy\">\n                    <input type=\"checkbox\" onChange={() => this.togglePolicy(policy.id)} checked={checked} />\n                    <a href={policy.url} target=\"_blank\" rel=\"noreferrer noopener\">\n                        {policy.name}\n                    </a>\n                </label>,\n            );\n        }\n\n        let errorSection;\n        if (this.props.errorText || this.state.errorText) {\n            errorSection = (\n                <div className=\"error\" role=\"alert\">\n                    {this.props.errorText || this.state.errorText}\n                </div>\n            );\n        }\n\n        return (\n            <div className=\"mx_InteractiveAuthEntryComponents\">\n                <p>{_t(\"auth|uia|terms\")}</p>\n                {checkboxes}\n                {errorSection}\n                <AccessibleButton\n                    kind=\"primary\"\n                    className=\"mx_InteractiveAuthEntryComponents_termsSubmit\"\n                    onClick={this.trySubmit}\n                    disabled={!allChecked}\n                >\n                    {_t(\"action|accept\")}\n                </AccessibleButton>\n            </div>\n        );\n    }\n}\n\ninterface IEmailIdentityAuthEntryProps extends IAuthEntryProps {\n    inputs?: {\n        emailAddress?: string;\n    };\n    stageState?: {\n        emailSid?: string;\n    };\n}\n\ninterface IEmailIdentityAuthEntryState {\n    requested: boolean;\n    requesting: boolean;\n}\n\nexport class EmailIdentityAuthEntry extends React.Component<\n    IEmailIdentityAuthEntryProps,\n    IEmailIdentityAuthEntryState\n> {\n    public static LOGIN_TYPE = AuthType.Email;\n\n    public constructor(props: IEmailIdentityAuthEntryProps) {\n        super(props);\n\n        this.state = {\n            requested: false,\n            requesting: false,\n        };\n    }\n\n    public componentDidMount(): void {\n        this.props.onPhaseChange(DEFAULT_PHASE);\n    }\n\n    public render(): React.ReactNode {\n        let errorSection;\n        // ignore the error when errcode is M_UNAUTHORIZED as we expect that error until the link is clicked.\n        if (this.props.errorText && this.props.errorCode !== \"M_UNAUTHORIZED\") {\n            errorSection = (\n                <div className=\"error\" role=\"alert\">\n                    {this.props.errorText}\n                </div>\n            );\n        }\n\n        // This component is now only displayed once the token has been requested,\n        // so we know the email has been sent. It can also get loaded after the user\n        // has clicked the validation link if the server takes a while to propagate\n        // the validation internally. If we're in the session spawned from clicking\n        // the validation link, we won't know the email address, so if we don't have it,\n        // assume that the link has been clicked and the server will realise when we poll.\n        // We only have a session ID if the user has clicked the link in their email,\n        // so show a loading state instead of \"an email has been sent to...\" because\n        // that's confusing when you've already read that email.\n        if (this.props.inputs?.emailAddress === undefined || this.props.stageState?.emailSid) {\n            if (errorSection) {\n                return errorSection;\n            }\n            return <Spinner />;\n        } else {\n            return (\n                <div className=\"mx_InteractiveAuthEntryComponents_emailWrapper\">\n                    <AuthHeaderModifier\n                        title={_t(\"auth|uia|email_auth_header\")}\n                        icon={<img src={EmailPromptIcon} role=\"presentation\" alt=\"\" width={16} />}\n                        hideServerPicker={true}\n                    />\n                    <p>\n                        {_t(\"auth|uia|email\", {\n                            emailAddress: <strong>{this.props.inputs.emailAddress}</strong>,\n                        })}\n                    </p>\n                    {this.state.requesting ? (\n                        <p className=\"secondary\">\n                            {_t(\n                                \"auth|uia|email_resend_prompt\",\n                                {},\n                                {\n                                    a: (text: string) => (\n                                        <Fragment>\n                                            <AccessibleButton kind=\"link_inline\" onClick={null} disabled>\n                                                {text} <Spinner size={14} />\n                                            </AccessibleButton>\n                                        </Fragment>\n                                    ),\n                                },\n                            )}\n                        </p>\n                    ) : (\n                        <p className=\"secondary\">\n                            {_t(\n                                \"auth|uia|email_resend_prompt\",\n                                {},\n                                {\n                                    a: (text: string) => (\n                                        <AccessibleButton\n                                            kind=\"link_inline\"\n                                            title={\n                                                this.state.requested ? _t(\"auth|uia|email_resent\") : _t(\"action|resend\")\n                                            }\n                                            onTooltipOpenChange={\n                                                this.state.requested\n                                                    ? (open) => {\n                                                          if (!open) this.setState({ requested: false });\n                                                      }\n                                                    : undefined\n                                            }\n                                            onClick={async (): Promise<void> => {\n                                                this.setState({ requesting: true });\n                                                try {\n                                                    await this.props.requestEmailToken?.();\n                                                } catch (e) {\n                                                    logger.warn(\"Email token request failed: \", e);\n                                                } finally {\n                                                    this.setState({ requested: true, requesting: false });\n                                                }\n                                            }}\n                                        >\n                                            {text}\n                                        </AccessibleButton>\n                                    ),\n                                },\n                            )}\n                        </p>\n                    )}\n                    {errorSection}\n                </div>\n            );\n        }\n    }\n}\n\ninterface IMsisdnAuthEntryProps extends IAuthEntryProps {\n    inputs?: {\n        phoneCountry?: string;\n        phoneNumber?: string;\n    };\n}\n\ninterface IMsisdnAuthEntryState {\n    token: string;\n    requestingToken: boolean;\n    errorText: string | null;\n}\n\nexport class MsisdnAuthEntry extends React.Component<IMsisdnAuthEntryProps, IMsisdnAuthEntryState> {\n    public static LOGIN_TYPE = AuthType.Msisdn;\n\n    private submitUrl?: string;\n    private sid?: string;\n    private msisdn?: string;\n\n    public constructor(props: IMsisdnAuthEntryProps) {\n        super(props);\n\n        this.state = {\n            token: \"\",\n            requestingToken: false,\n            errorText: \"\",\n        };\n    }\n\n    public componentDidMount(): void {\n        this.props.onPhaseChange(DEFAULT_PHASE);\n\n        this.setState({ requestingToken: true });\n        this.requestMsisdnToken()\n            .catch((e) => {\n                this.props.fail(e);\n            })\n            .finally(() => {\n                this.setState({ requestingToken: false });\n            });\n    }\n\n    /*\n     * Requests a verification token by SMS.\n     */\n    private requestMsisdnToken(): Promise<void> {\n        return this.props.matrixClient\n            .requestRegisterMsisdnToken(\n                this.props.inputs?.phoneCountry ?? \"\",\n                this.props.inputs?.phoneNumber ?? \"\",\n                this.props.clientSecret,\n                1, // TODO: Multiple send attempts?\n            )\n            .then((result) => {\n                this.submitUrl = result.submit_url;\n                this.sid = result.sid;\n                this.msisdn = result.msisdn;\n            });\n    }\n\n    private onTokenChange = (e: ChangeEvent<HTMLInputElement>): void => {\n        this.setState({\n            token: e.target.value,\n        });\n    };\n\n    private onFormSubmit = async (e: FormEvent): Promise<void> => {\n        e.preventDefault();\n        if (this.state.token == \"\") return;\n\n        this.setState({\n            errorText: null,\n        });\n\n        try {\n            let result: { success: boolean };\n            if (this.submitUrl && this.sid) {\n                result = await this.props.matrixClient.submitMsisdnTokenOtherUrl(\n                    this.submitUrl,\n                    this.sid,\n                    this.props.clientSecret,\n                    this.state.token,\n                );\n            } else {\n                throw new Error(\"The registration with MSISDN flow is misconfigured\");\n            }\n            if (result.success) {\n                const creds = {\n                    sid: this.sid,\n                    client_secret: this.props.clientSecret,\n                };\n                this.props.submitAuthDict({\n                    type: AuthType.Msisdn,\n                    threepid_creds: creds,\n                });\n            } else {\n                this.setState({\n                    errorText: _t(\"auth|uia|msisdn_token_incorrect\"),\n                });\n            }\n        } catch (e) {\n            this.props.fail(e instanceof Error ? e : new Error(\"Failed to submit msisdn token\"));\n            logger.log(\"Failed to submit msisdn token\");\n        }\n    };\n\n    public render(): React.ReactNode {\n        if (this.state.requestingToken) {\n            return <Spinner />;\n        } else {\n            const enableSubmit = Boolean(this.state.token);\n            const submitClasses = classNames({\n                mx_InteractiveAuthEntryComponents_msisdnSubmit: true,\n                mx_GeneralButton: true,\n            });\n            let errorSection;\n            if (this.state.errorText) {\n                errorSection = (\n                    <div className=\"error\" role=\"alert\">\n                        {this.state.errorText}\n                    </div>\n                );\n            }\n            return (\n                <div>\n                    <p>{_t(\"auth|uia|msisdn\", { msisdn: <i>{this.msisdn}</i> })}</p>\n                    <p>{_t(\"auth|uia|msisdn_token_prompt\")}</p>\n                    <div className=\"mx_InteractiveAuthEntryComponents_msisdnWrapper\">\n                        <form onSubmit={this.onFormSubmit}>\n                            <input\n                                type=\"text\"\n                                className=\"mx_InteractiveAuthEntryComponents_msisdnEntry\"\n                                value={this.state.token}\n                                onChange={this.onTokenChange}\n                                aria-label={_t(\"auth|uia|code\")}\n                            />\n                            <br />\n                            <input\n                                type=\"submit\"\n                                value={_t(\"action|submit\")}\n                                className={submitClasses}\n                                disabled={!enableSubmit}\n                            />\n                        </form>\n                        {errorSection}\n                    </div>\n                </div>\n            );\n        }\n    }\n}\n\ninterface IRegistrationTokenAuthEntryState {\n    registrationToken: string;\n}\n\nexport class RegistrationTokenAuthEntry extends React.Component<IAuthEntryProps, IRegistrationTokenAuthEntryState> {\n    public static readonly LOGIN_TYPE = AuthType.RegistrationToken;\n\n    public constructor(props: IAuthEntryProps) {\n        super(props);\n\n        this.state = {\n            registrationToken: \"\",\n        };\n    }\n\n    public componentDidMount(): void {\n        this.props.onPhaseChange(DEFAULT_PHASE);\n    }\n\n    private onSubmit = (e: FormEvent): void => {\n        e.preventDefault();\n        if (this.props.busy) return;\n\n        this.props.submitAuthDict({\n            // Could be AuthType.RegistrationToken or AuthType.UnstableRegistrationToken\n            type: this.props.loginType,\n            token: this.state.registrationToken,\n        });\n    };\n\n    private onRegistrationTokenFieldChange = (ev: ChangeEvent<HTMLInputElement>): void => {\n        // enable the submit button if the registration token is non-empty\n        this.setState({\n            registrationToken: ev.target.value,\n        });\n    };\n\n    public render(): React.ReactNode {\n        const registrationTokenBoxClass = classNames({\n            error: this.props.errorText,\n        });\n\n        let submitButtonOrSpinner;\n        if (this.props.busy) {\n            submitButtonOrSpinner = <Spinner />;\n        } else {\n            submitButtonOrSpinner = (\n                <AccessibleButton onClick={this.onSubmit} kind=\"primary\" disabled={!this.state.registrationToken}>\n                    {_t(\"action|continue\")}\n                </AccessibleButton>\n            );\n        }\n\n        let errorSection;\n        if (this.props.errorText) {\n            errorSection = (\n                <div className=\"error\" role=\"alert\">\n                    {this.props.errorText}\n                </div>\n            );\n        }\n\n        return (\n            <div>\n                <p>{_t(\"auth|uia|registration_token_prompt\")}</p>\n                <form onSubmit={this.onSubmit} className=\"mx_InteractiveAuthEntryComponents_registrationTokenSection\">\n                    <Field\n                        className={registrationTokenBoxClass}\n                        type=\"text\"\n                        name=\"registrationTokenField\"\n                        label={_t(\"auth|uia|registration_token_label\")}\n                        autoFocus={true}\n                        value={this.state.registrationToken}\n                        onChange={this.onRegistrationTokenFieldChange}\n                    />\n                    {errorSection}\n                    <div className=\"mx_button_row\">{submitButtonOrSpinner}</div>\n                </form>\n            </div>\n        );\n    }\n}\n\n// Subset of AccessibleButtonKind which can be specified for the continue button\nexport type ContinueKind = Extract<AccessibleButtonKind, \"primary\" | \"danger\">;\n\ninterface ISSOAuthEntryProps extends IAuthEntryProps {\n    continueText?: string;\n    continueKind?: ContinueKind;\n    onCancel?: () => void;\n}\n\ninterface ISSOAuthEntryState {\n    phase: number;\n    attemptFailed: boolean;\n}\n\nexport class SSOAuthEntry extends React.Component<ISSOAuthEntryProps, ISSOAuthEntryState> {\n    public static LOGIN_TYPE = AuthType.Sso;\n    public static UNSTABLE_LOGIN_TYPE = AuthType.SsoUnstable;\n\n    public static PHASE_PREAUTH = 1; // button to start SSO\n    public static PHASE_POSTAUTH = 2; // button to confirm SSO completed\n\n    private ssoUrl: string;\n    private popupWindow: Window | null;\n\n    public constructor(props: ISSOAuthEntryProps) {\n        super(props);\n\n        if (!this.props.authSessionId) throw new Error(\"This UIA flow requires an authSessionId\");\n\n        // We actually send the user through fallback auth so we don't have to\n        // deal with a redirect back to us, losing application context.\n        this.ssoUrl = props.matrixClient.getFallbackAuthUrl(this.props.loginType, this.props.authSessionId);\n\n        this.popupWindow = null;\n\n        this.state = {\n            phase: SSOAuthEntry.PHASE_PREAUTH,\n            attemptFailed: false,\n        };\n    }\n\n    public componentDidMount(): void {\n        window.addEventListener(\"message\", this.onReceiveMessage);\n        this.props.onPhaseChange(SSOAuthEntry.PHASE_PREAUTH);\n    }\n\n    public componentWillUnmount(): void {\n        window.removeEventListener(\"message\", this.onReceiveMessage);\n        if (this.popupWindow) {\n            this.popupWindow.close();\n            this.popupWindow = null;\n        }\n    }\n\n    public attemptFailed = (): void => {\n        this.setState({\n            attemptFailed: true,\n        });\n    };\n\n    private onReceiveMessage = (event: MessageEvent): void => {\n        if (event.data === \"authDone\" && event.source === this.popupWindow) {\n            if (this.popupWindow) {\n                this.popupWindow.close();\n                this.popupWindow = null;\n            }\n        }\n    };\n\n    private onStartAuthClick = (): void => {\n        // Note: We don't use PlatformPeg's startSsoAuth functions because we almost\n        // certainly will need to open the thing in a new tab to avoid losing application\n        // context.\n\n        this.popupWindow = window.open(this.ssoUrl, \"_blank\");\n        this.setState({ phase: SSOAuthEntry.PHASE_POSTAUTH });\n        this.props.onPhaseChange(SSOAuthEntry.PHASE_POSTAUTH);\n    };\n\n    private onConfirmClick = (): void => {\n        this.props.submitAuthDict({});\n    };\n\n    public render(): React.ReactNode {\n        let continueButton: JSX.Element;\n\n        const cancelButton = (\n            <AccessibleButton\n                onClick={this.props.onCancel ?? null}\n                kind={this.props.continueKind ? `${this.props.continueKind}_outline` : \"primary_outline\"}\n            >\n                {_t(\"action|cancel\")}\n            </AccessibleButton>\n        );\n        if (this.state.phase === SSOAuthEntry.PHASE_PREAUTH) {\n            continueButton = (\n                <AccessibleButton onClick={this.onStartAuthClick} kind={this.props.continueKind || \"primary\"}>\n                    {this.props.continueText || _t(\"auth|sso\")}\n                </AccessibleButton>\n            );\n        } else {\n            continueButton = (\n                <AccessibleButton onClick={this.onConfirmClick} kind={this.props.continueKind || \"primary\"}>\n                    {this.props.continueText || _t(\"action|confirm\")}\n                </AccessibleButton>\n            );\n        }\n\n        let errorSection;\n        if (this.props.errorText) {\n            errorSection = (\n                <div className=\"error\" role=\"alert\">\n                    {this.props.errorText}\n                </div>\n            );\n        } else if (this.state.attemptFailed) {\n            errorSection = (\n                <div className=\"error\" role=\"alert\">\n                    {_t(\"auth|uia|sso_failed\")}\n                </div>\n            );\n        }\n\n        return (\n            <Fragment>\n                {errorSection}\n                <div className=\"mx_InteractiveAuthEntryComponents_sso_buttons\">\n                    {this.props.busy ? (\n                        <Spinner size={24} />\n                    ) : (\n                        <>\n                            {cancelButton}\n                            {continueButton}\n                        </>\n                    )}\n                </div>\n            </Fragment>\n        );\n    }\n}\n\nexport class FallbackAuthEntry<T extends object> extends React.Component<IAuthEntryProps & T> {\n    protected popupWindow: Window | null;\n    protected fallbackButton = createRef<HTMLDivElement>();\n\n    public constructor(props: IAuthEntryProps & T) {\n        super(props);\n\n        // we have to make the user click a button, as browsers will block\n        // the popup if we open it immediately.\n        this.popupWindow = null;\n    }\n\n    public componentDidMount(): void {\n        window.addEventListener(\"message\", this.onReceiveMessage);\n        this.props.onPhaseChange(DEFAULT_PHASE);\n    }\n\n    public componentWillUnmount(): void {\n        window.removeEventListener(\"message\", this.onReceiveMessage);\n        this.popupWindow?.close();\n    }\n\n    public focus = (): void => {\n        this.fallbackButton.current?.focus();\n    };\n\n    private onShowFallbackClick = (e: ButtonEvent): void => {\n        if (!this.props.authSessionId) return;\n\n        e.preventDefault();\n        e.stopPropagation();\n\n        const url = this.props.matrixClient.getFallbackAuthUrl(this.props.loginType, this.props.authSessionId);\n        this.popupWindow = window.open(url, \"_blank\");\n    };\n\n    private onReceiveMessage = (event: MessageEvent): void => {\n        if (event.data === \"authDone\" && event.source === this.popupWindow) {\n            this.props.submitAuthDict({});\n        }\n    };\n\n    public render(): React.ReactNode {\n        let errorSection;\n        if (this.props.errorText) {\n            errorSection = (\n                <div className=\"error\" role=\"alert\">\n                    {this.props.errorText}\n                </div>\n            );\n        }\n        return (\n            <div>\n                <AccessibleButton kind=\"link\" ref={this.fallbackButton} onClick={this.onShowFallbackClick}>\n                    {_t(\"auth|uia|fallback_button\")}\n                </AccessibleButton>\n                {errorSection}\n            </div>\n        );\n    }\n}\n\nexport enum CustomAuthType {\n    // This is the unstable value from MSC4312\n    MasCrossSigningReset = \"org.matrix.cross_signing_reset\",\n}\n\nexport class MasUnlockCrossSigningAuthEntry extends FallbackAuthEntry<{\n    stageParams?: {\n        url?: string;\n    };\n}> {\n    public static readonly LOGIN_TYPE = AuthType.OAuth;\n    public static readonly UNSTABLE_LOGIN_TYPE = CustomAuthType.MasCrossSigningReset;\n\n    private onGoToAccountClick = (): void => {\n        if (!this.props.stageParams?.url) return;\n        this.popupWindow = window.open(this.props.stageParams.url, \"_blank\");\n    };\n\n    private onRetryClick = (): void => {\n        this.props.submitAuthDict({});\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <EncryptionCard\n                Icon={UserProfileSolidIcon}\n                title={_t(\"auth|uia|mas_cross_signing_reset_title\")}\n                description={_t(\"auth|uia|mas_cross_signing_reset_description\", {\n                    serverName: this.props.matrixClient.getDomain(),\n                })}\n            >\n                <EncryptionCardButtons>\n                    <Button\n                        Icon={PopOutIcon}\n                        onClick={this.onGoToAccountClick}\n                        autoFocus\n                        kind=\"primary\"\n                        className=\"mx_Dialog_nonDialogButton\"\n                    >\n                        {_t(\"auth|uia|mas_cross_signing_reset_cta\")}\n                    </Button>\n                    <Button onClick={this.onRetryClick} kind=\"tertiary\" className=\"mx_Dialog_nonDialogButton\">\n                        {_t(\"action|retry\")}\n                    </Button>\n                </EncryptionCardButtons>\n            </EncryptionCard>\n        );\n    }\n}\n\nexport interface IStageComponentProps extends IAuthEntryProps {\n    stageParams?: Record<string, any>;\n    inputs?: IInputs;\n    stageState?: IStageStatus;\n    continueText?: string;\n    continueKind?: ContinueKind;\n    setEmailSid?(sid: string): void;\n    onCancel?(): void;\n    requestEmailToken?(): Promise<void>;\n}\n\nexport interface IStageComponent extends React.ComponentClass<React.PropsWithRef<IStageComponentProps>> {\n    attemptFailed?(): void;\n    focus?(): void;\n}\n\nexport default function getEntryComponentForLoginType(loginType: AuthType | CustomAuthType): IStageComponent {\n    switch (loginType) {\n        case AuthType.OAuth:\n        case CustomAuthType.MasCrossSigningReset:\n            return MasUnlockCrossSigningAuthEntry;\n        case AuthType.Password:\n            return PasswordAuthEntry;\n        case AuthType.Recaptcha:\n            return RecaptchaAuthEntry;\n        case AuthType.Email:\n            return EmailIdentityAuthEntry;\n        case AuthType.Msisdn:\n            return MsisdnAuthEntry;\n        case AuthType.Terms:\n            return TermsAuthEntry;\n        case AuthType.RegistrationToken:\n        case AuthType.UnstableRegistrationToken:\n            return RegistrationTokenAuthEntry;\n        case AuthType.Sso:\n        case AuthType.SsoUnstable:\n            return SSOAuthEntry;\n        default:\n            return FallbackAuthEntry;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type AriaRole, type JSX, type Ref, useCallback, useContext, useEffect, useState } from \"react\";\nimport classNames from \"classnames\";\nimport { ClientEvent, type SyncState } from \"matrix-js-sdk/src/matrix\";\nimport { Avatar } from \"@vector-im/compound-web\";\n\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { useTypedEventEmitter } from \"../../../hooks/useEventEmitter\";\nimport { _t } from \"../../../languageHandler\";\nimport { useScopedRoomContext } from \"../../../contexts/ScopedRoomContext.tsx\";\n\ninterface IProps {\n    name?: React.ComponentProps<typeof Avatar>[\"name\"]; // The name (first initial used as default)\n    idName?: React.ComponentProps<typeof Avatar>[\"id\"]; // ID for generating hash colours\n    title?: string; // onHover title text\n    url?: string | null; // highest priority of them all, shortcut to set in urls[0]\n    urls?: string[]; // [highest_priority, ... , lowest_priority]\n    type?: React.ComponentProps<typeof Avatar>[\"type\"];\n    size: string;\n    onClick?: (ev: ButtonEvent) => void;\n    className?: string;\n    tabIndex?: number;\n    altText?: string;\n    role?: AriaRole;\n    ref?: Ref<HTMLElement>;\n}\n\nconst calculateUrls = (url?: string | null, urls?: string[], lowBandwidth = false): string[] => {\n    // work out the full set of urls to try to load. This is formed like so:\n    // imageUrls: [ props.url, ...props.urls ]\n\n    let _urls: string[] = [];\n    if (!lowBandwidth) {\n        _urls = urls || [];\n\n        if (url) {\n            // copy urls and put url first\n            _urls = [url, ..._urls];\n        }\n    }\n\n    // deduplicate URLs\n    return Array.from(new Set(_urls));\n};\n\nconst useImageUrl = ({ url, urls }: { url?: string | null; urls?: string[] }): [string, () => void] => {\n    // Since this is a hot code path and the settings store can be slow, we\n    // use the cached lowBandwidth value from the room context if it exists\n    const roomContext = useScopedRoomContext(\"lowBandwidth\");\n    const lowBandwidth = roomContext?.lowBandwidth ?? SettingsStore.getValue(\"lowBandwidth\");\n\n    const [imageUrls, setUrls] = useState<string[]>(calculateUrls(url, urls, lowBandwidth));\n    const [urlsIndex, setIndex] = useState<number>(0);\n\n    const onError = useCallback(() => {\n        setIndex((i) => i + 1); // try the next one\n    }, []);\n\n    useEffect(() => {\n        setUrls(calculateUrls(url, urls, lowBandwidth));\n        setIndex(0);\n    }, [url, JSON.stringify(urls)]); // eslint-disable-line react-hooks/exhaustive-deps\n\n    const cli = useContext(MatrixClientContext);\n    const onClientSync = useCallback((syncState: SyncState, prevState: SyncState | null) => {\n        // Consider the client reconnected if there is no error with syncing.\n        // This means the state could be RECONNECTING, SYNCING, PREPARED or CATCHUP.\n        const reconnected = syncState !== \"ERROR\" && prevState !== syncState;\n        if (reconnected) {\n            setIndex(0);\n        }\n    }, []);\n    useTypedEventEmitter(cli, ClientEvent.Sync, onClientSync);\n\n    const imageUrl = imageUrls[urlsIndex];\n    return [imageUrl, onError];\n};\n\nconst BaseAvatar = (props: IProps): JSX.Element => {\n    const {\n        name,\n        idName,\n        title,\n        url,\n        urls,\n        size = \"40px\",\n        onClick,\n        className,\n        type = \"round\",\n        altText = _t(\"common|avatar\"),\n        ref,\n        ...otherProps\n    } = props;\n\n    const [imageUrl, onError] = useImageUrl({ url, urls });\n\n    const extraProps: Partial<React.ComponentProps<typeof Avatar>> = {};\n\n    if (onClick) {\n        extraProps[\"aria-live\"] = \"off\";\n        extraProps[\"role\"] = \"button\";\n    } else if (!imageUrl) {\n        extraProps[\"role\"] = \"presentation\";\n        extraProps[\"aria-label\"] = undefined;\n    } else {\n        extraProps[\"role\"] = undefined;\n    }\n\n    return (\n        <Avatar\n            ref={ref}\n            src={imageUrl}\n            id={idName ?? \"\"}\n            name={name ?? \"\"}\n            type={type}\n            size={size}\n            className={classNames(\"mx_BaseAvatar\", className)}\n            aria-label={altText}\n            onError={onError}\n            title={title}\n            onClick={onClick}\n            {...extraProps}\n            {...otherProps}\n            data-testid=\"avatar-img\"\n        />\n    );\n};\n\nexport default BaseAvatar;\nexport type BaseAvatarType = React.FC<IProps>;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport classNames from \"classnames\";\nimport {\n    EventType,\n    JoinRule,\n    type MatrixEvent,\n    type Room,\n    RoomEvent,\n    type User,\n    UserEvent,\n} from \"matrix-js-sdk/src/matrix\";\nimport { UnstableValue } from \"matrix-js-sdk/src/NamespacedValue\";\nimport { Tooltip } from \"@vector-im/compound-web\";\nimport { PublicIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport RoomAvatar from \"./RoomAvatar\";\nimport NotificationBadge from \"../rooms/NotificationBadge\";\nimport { RoomNotificationStateStore } from \"../../../stores/notifications/RoomNotificationStateStore\";\nimport { type NotificationState } from \"../../../stores/notifications/NotificationState\";\nimport { isPresenceEnabled } from \"../../../utils/presence\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { _t } from \"../../../languageHandler\";\nimport DMRoomMap from \"../../../utils/DMRoomMap\";\nimport { type IOOBData } from \"../../../stores/ThreepidInviteStore\";\nimport { getJoinedNonFunctionalMembers } from \"../../../utils/room/getJoinedNonFunctionalMembers\";\n\ninterface IProps {\n    room: Room;\n    size: string;\n    displayBadge?: boolean;\n    /**\n     * If true, show nothing if the notification would only cause a dot to be shown rather than\n     * a badge. That is: only display badges and not dots. Default: false.\n     */\n    hideIfDot?: boolean;\n    oobData?: IOOBData;\n    viewAvatarOnClick?: boolean;\n    tooltipProps?: {\n        tabIndex?: number;\n    };\n    className?: string;\n}\n\ninterface IState {\n    notificationState?: NotificationState;\n    icon: Icon;\n}\n\nconst BUSY_PRESENCE_NAME = new UnstableValue(\"busy\", \"org.matrix.msc3026.busy\");\n\nenum Icon {\n    // Note: the names here are used in CSS class names\n    None = \"NONE\", // ... except this one\n    Globe = \"GLOBE\",\n    PresenceOnline = \"ONLINE\",\n    PresenceAway = \"AWAY\",\n    PresenceOffline = \"OFFLINE\",\n    PresenceBusy = \"BUSY\",\n}\n\nfunction tooltipText(variant: Icon): string | undefined {\n    switch (variant) {\n        case Icon.Globe:\n            return _t(\"room|header|room_is_public\");\n        case Icon.PresenceOnline:\n            return _t(\"presence|online\");\n        case Icon.PresenceAway:\n            return _t(\"presence|away\");\n        case Icon.PresenceOffline:\n            return _t(\"presence|offline\");\n        case Icon.PresenceBusy:\n            return _t(\"presence|busy\");\n    }\n}\n\n/**\n * @deprecated Use {@link RoomAvatarView} instead.\n */\nexport default class DecoratedRoomAvatar extends React.PureComponent<IProps, IState> {\n    private _dmUser: User | null = null;\n    private isUnmounted = false;\n    private isWatchingTimeline = false;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            notificationState: RoomNotificationStateStore.instance.getRoomState(this.props.room),\n            icon: this.calculateIcon(),\n        };\n    }\n\n    public componentWillUnmount(): void {\n        this.isUnmounted = true;\n        if (this.isWatchingTimeline) this.props.room.off(RoomEvent.Timeline, this.onRoomTimeline);\n        this.dmUser = null; // clear listeners, if any\n    }\n\n    private get isPublicRoom(): boolean {\n        return this.props.room.getJoinRule() === JoinRule.Public;\n    }\n\n    private get dmUser(): User | null {\n        return this._dmUser;\n    }\n\n    private set dmUser(val: User | null) {\n        const oldUser = this._dmUser;\n        this._dmUser = val;\n        if (oldUser && oldUser !== this._dmUser) {\n            oldUser.off(UserEvent.CurrentlyActive, this.onPresenceUpdate);\n            oldUser.off(UserEvent.Presence, this.onPresenceUpdate);\n        }\n        if (this._dmUser && oldUser !== this._dmUser) {\n            this._dmUser.on(UserEvent.CurrentlyActive, this.onPresenceUpdate);\n            this._dmUser.on(UserEvent.Presence, this.onPresenceUpdate);\n        }\n    }\n\n    private onRoomTimeline = (ev: MatrixEvent, room?: Room): void => {\n        if (this.isUnmounted) return;\n        if (this.props.room.roomId !== room?.roomId) return;\n\n        if (ev.getType() === EventType.RoomJoinRules || ev.getType() === EventType.RoomMember) {\n            const newIcon = this.calculateIcon();\n            if (newIcon !== this.state.icon) {\n                this.setState({ icon: newIcon });\n            }\n        }\n    };\n\n    private onPresenceUpdate = (): void => {\n        if (this.isUnmounted) return;\n\n        const newIcon = this.getPresenceIcon();\n        if (newIcon !== this.state.icon) this.setState({ icon: newIcon });\n    };\n\n    private getPresenceIcon(): Icon {\n        if (!this.dmUser) return Icon.None;\n\n        let icon = Icon.None;\n\n        const isOnline = this.dmUser.currentlyActive || this.dmUser.presence === \"online\";\n        if (BUSY_PRESENCE_NAME.matches(this.dmUser.presence)) {\n            icon = Icon.PresenceBusy;\n        } else if (isOnline) {\n            icon = Icon.PresenceOnline;\n        } else if (this.dmUser.presence === \"offline\") {\n            icon = Icon.PresenceOffline;\n        } else if (this.dmUser.presence === \"unavailable\") {\n            icon = Icon.PresenceAway;\n        }\n\n        return icon;\n    }\n\n    private calculateIcon(): Icon {\n        let icon = Icon.None;\n\n        // We look at the DMRoomMap and not the tag here so that we don't exclude DMs in Favourites\n        const otherUserId = DMRoomMap.shared().getUserIdForRoomId(this.props.room.roomId);\n        if (otherUserId && getJoinedNonFunctionalMembers(this.props.room).length === 2) {\n            // Track presence, if available\n            if (isPresenceEnabled(this.props.room.client)) {\n                this.dmUser = MatrixClientPeg.safeGet().getUser(otherUserId);\n                icon = this.getPresenceIcon();\n            }\n        } else {\n            // Track publicity\n            icon = this.isPublicRoom ? Icon.Globe : Icon.None;\n            if (!this.isWatchingTimeline) {\n                this.props.room.on(RoomEvent.Timeline, this.onRoomTimeline);\n                this.isWatchingTimeline = true;\n            }\n        }\n        return icon;\n    }\n\n    public render(): React.ReactNode {\n        // Spread the remaining props to make it work with compound component\n        const { room, size, displayBadge, hideIfDot, oobData, viewAvatarOnClick, tooltipProps, className, ...props } =\n            this.props;\n\n        let badge: React.ReactNode;\n        if (this.props.displayBadge && this.state.notificationState) {\n            badge = (\n                <NotificationBadge\n                    notification={this.state.notificationState}\n                    hideIfDot={this.props.hideIfDot}\n                    roomId={this.props.room.roomId}\n                />\n            );\n        }\n\n        let icon: JSX.Element | undefined;\n        if (this.state.icon !== Icon.None) {\n            icon = (\n                <div\n                    tabIndex={this.props.tooltipProps?.tabIndex ?? 0}\n                    className={`mx_DecoratedRoomAvatar_icon mx_DecoratedRoomAvatar_icon_${this.state.icon.toLowerCase()}`}\n                >\n                    {this.state.icon === Icon.Globe ? <PublicIcon /> : null}\n                </div>\n            );\n        }\n\n        const classes = classNames(\n            \"mx_DecoratedRoomAvatar\",\n            {\n                mx_DecoratedRoomAvatar_cutout: icon,\n            },\n            className,\n        );\n\n        return (\n            <div className={classes} {...props}>\n                <RoomAvatar\n                    room={this.props.room}\n                    size={this.props.size}\n                    oobData={this.props.oobData}\n                    viewAvatarOnClick={this.props.viewAvatarOnClick}\n                />\n                {icon && (\n                    <Tooltip label={tooltipText(this.state.icon)!} placement=\"bottom\">\n                        {icon}\n                    </Tooltip>\n                )}\n                {badge}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2022 The Matrix.org Foundation C.I.C.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode, type Ref, useContext } from \"react\";\nimport { type RoomMember, type ResizeMethod } from \"matrix-js-sdk/src/matrix\";\n\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport BaseAvatar from \"./BaseAvatar\";\nimport { mediaFromMxc } from \"../../../customisations/Media\";\nimport { CardContext } from \"../right_panel/context\";\nimport UserIdentifierCustomisations from \"../../../customisations/UserIdentifier\";\nimport { useRoomMemberProfile } from \"../../../hooks/room/useRoomMemberProfile\";\nimport { _t } from \"../../../languageHandler\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext.tsx\";\n\ninterface IProps extends Omit<React.ComponentProps<typeof BaseAvatar>, \"name\" | \"idName\" | \"url\"> {\n    member: RoomMember | null;\n    fallbackUserId?: string;\n    size: string;\n    resizeMethod?: ResizeMethod;\n    // Whether the onClick of the avatar should be overridden to dispatch `Action.ViewUser`\n    viewUserOnClick?: boolean;\n    pushUserOnClick?: boolean;\n    title?: string;\n    style?: any;\n    forceHistorical?: boolean; // true to deny `useOnlyCurrentProfiles` usage. Default false.\n    hideTitle?: boolean;\n    children?: ReactNode;\n    ref?: Ref<HTMLElement>;\n}\n\nexport default function MemberAvatar({\n    size,\n    resizeMethod = \"crop\",\n    viewUserOnClick,\n    forceHistorical,\n    fallbackUserId,\n    hideTitle,\n    member: propsMember,\n    ref,\n    ...props\n}: IProps): JSX.Element {\n    const cli = useContext(MatrixClientContext);\n    const card = useContext(CardContext);\n\n    const member = useRoomMemberProfile({\n        userId: propsMember?.userId,\n        member: propsMember,\n        forceHistorical: forceHistorical,\n    });\n\n    const name = member?.name ?? fallbackUserId;\n    let title: string | undefined = props.title;\n    let imageUrl: string | null | undefined;\n    if (member?.name) {\n        if (member.getMxcAvatarUrl()) {\n            imageUrl = mediaFromMxc(member.getMxcAvatarUrl() ?? \"\", cli).getThumbnailOfSourceHttp(\n                parseInt(size, 10),\n                parseInt(size, 10),\n                resizeMethod,\n            );\n        }\n\n        if (!title) {\n            title =\n                UserIdentifierCustomisations.getDisplayUserIdentifier(member?.userId ?? \"\", {\n                    roomId: member?.roomId ?? \"\",\n                }) ?? fallbackUserId;\n        }\n    }\n\n    return (\n        <BaseAvatar\n            {...props}\n            size={size}\n            name={name ?? \"\"}\n            title={hideTitle ? undefined : title}\n            idName={member?.userId ?? fallbackUserId}\n            url={imageUrl}\n            onClick={\n                viewUserOnClick\n                    ? () => {\n                          dis.dispatch({\n                              action: Action.ViewUser,\n                              member: propsMember,\n                              push: card.isCard,\n                          });\n                      }\n                    : props.onClick\n            }\n            altText={_t(\"common|user_avatar\")}\n            ref={ref}\n        />\n    );\n}\n","/*\nCopyright 2024, 2025 New Vector Ltd.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useCallback, useMemo, type ComponentProps } from \"react\";\nimport { type Room, RoomType, KnownMembership, EventType } from \"matrix-js-sdk/src/matrix\";\nimport { type RoomAvatarEventContent } from \"matrix-js-sdk/src/types\";\n\nimport BaseAvatar from \"./BaseAvatar\";\nimport ImageView from \"../elements/ImageView\";\nimport Modal from \"../../../Modal\";\nimport * as Avatar from \"../../../Avatar\";\nimport { mediaFromMxc } from \"../../../customisations/Media\";\nimport { type IOOBData } from \"../../../stores/ThreepidInviteStore\";\nimport { filterBoolean } from \"../../../utils/arrays\";\nimport { useSettingValue } from \"../../../hooks/useSettings\";\nimport { useRoomState } from \"../../../hooks/useRoomState\";\nimport { useRoomIdName } from \"../../../hooks/room/useRoomIdName\";\nimport { MediaPreviewValue } from \"../../../@types/media_preview\";\n\ninterface IProps extends Omit<ComponentProps<typeof BaseAvatar>, \"name\" | \"idName\" | \"url\" | \"onClick\" | \"size\"> {\n    // Room may be left unset here, but if it is,\n    // oobData.avatarUrl should be set (else there\n    // would be nowhere to get the avatar from)\n    room?: Room;\n    // Optional here.\n    size?: ComponentProps<typeof BaseAvatar>[\"size\"];\n    oobData?: IOOBData & {\n        roomId?: string;\n    };\n    viewAvatarOnClick?: boolean;\n    onClick?(): void;\n}\n\nconst RoomAvatar: React.FC<IProps> = ({ room, viewAvatarOnClick, onClick, oobData, size = \"36px\", ...otherProps }) => {\n    const roomName = room?.name ?? oobData?.name ?? \"?\";\n    const avatarEvent = useRoomState(room, (state) => state.getStateEvents(EventType.RoomAvatar, \"\"));\n    const roomIdName = useRoomIdName(room, oobData);\n\n    const showAvatarsOnInvites =\n        useSettingValue(\"mediaPreviewConfig\", room?.roomId).invite_avatars === MediaPreviewValue.On;\n\n    const onRoomAvatarClick = useCallback(() => {\n        const avatarUrl = Avatar.avatarUrlForRoom(room ?? null);\n        if (!avatarUrl) return;\n        const params = {\n            src: avatarUrl,\n            name: room?.name,\n        };\n\n        Modal.createDialog(ImageView, params, \"mx_Dialog_lightbox\", undefined, true);\n    }, [room]);\n\n    const urls = useMemo(() => {\n        const myMembership = room?.getMyMembership();\n        if (!showAvatarsOnInvites && (myMembership === KnownMembership.Invite || !myMembership)) {\n            // The user has opted out of showing avatars, so return no urls here.\n            return [];\n        }\n\n        // parseInt ignores suffixes.\n        const sizeInt = parseInt(size, 10);\n        let oobAvatar: string | null = null;\n        if (oobData?.avatarUrl) {\n            oobAvatar = mediaFromMxc(oobData?.avatarUrl).getThumbnailOfSourceHttp(sizeInt, sizeInt, \"crop\");\n        }\n\n        return filterBoolean([\n            oobAvatar, // highest priority\n            Avatar.avatarUrlForRoom(\n                room ?? null,\n                sizeInt,\n                sizeInt,\n                \"crop\",\n                avatarEvent?.getContent<RoomAvatarEventContent>().url,\n            ),\n        ]);\n    }, [showAvatarsOnInvites, room, size, avatarEvent, oobData]);\n\n    return (\n        <BaseAvatar\n            {...otherProps}\n            size={size}\n            type={(room?.getType() ?? oobData?.roomType) === RoomType.Space ? \"square\" : \"round\"}\n            name={roomName}\n            idName={roomIdName}\n            urls={urls}\n            onClick={viewAvatarOnClick && urls[0] ? onRoomAvatarClick : onClick}\n        />\n    );\n};\n\nexport default RoomAvatar;\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { useDmMember } from \"../../components/views/avatars/WithPresenceIndicator.tsx\";\nimport { LocalRoom } from \"../../models/LocalRoom.ts\";\n\n/**\n * Determine a stable ID for generating hash colours. If the room\n * is a DM (or local room), then the other user's ID will be used.\n * @param oobData - out-of-band information about the room\n * @returns An ID string, or undefined if the room and oobData are undefined.\n */\nexport function useRoomIdName(room?: Room, oobData?: { roomId?: string }): string | undefined {\n    const dmMember = useDmMember(room);\n    if (dmMember) {\n        // If the room is a DM, we use the other user's ID for the color hash\n        // in order to match the room avatar with their avatar\n        return dmMember.userId;\n    } else if (room instanceof LocalRoom && room.targets.length === 1) {\n        return room.targets[0].userId;\n    } else if (room) {\n        return room.roomId;\n    } else {\n        return oobData?.roomId;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { type RoomMember } from \"matrix-js-sdk/src/matrix\";\n\nimport emailPillAvatar from \"../../../../res/img/icon-email-pill-avatar.svg\";\nimport { mediaFromMxc } from \"../../../customisations/Media\";\nimport { type Member, type ThreepidMember } from \"../../../utils/direct-messages\";\nimport BaseAvatar from \"./BaseAvatar\";\n\ninterface SearchResultAvatarProps {\n    user: Member | RoomMember;\n    size: string;\n}\n\nexport function SearchResultAvatar({ user, size }: SearchResultAvatarProps): JSX.Element {\n    if ((user as ThreepidMember).isEmail) {\n        // we can’t show a real avatar here, but we try to create the exact same markup that a real avatar would have\n        // BaseAvatar makes the avatar, if it's not clickable but just for decoration, invisible to screenreaders by\n        // specifically setting an empty alt text, so we do the same.\n        return (\n            <img\n                className=\"mx_SearchResultAvatar mx_SearchResultAvatar_threepidAvatar\"\n                alt=\"\"\n                src={emailPillAvatar}\n                width={size}\n                height={size}\n            />\n        );\n    } else {\n        const avatarUrl = user.getMxcAvatarUrl();\n        return (\n            <BaseAvatar\n                className=\"mx_SearchResultAvatar\"\n                url={avatarUrl ? mediaFromMxc(avatarUrl).getSquareThumbnailHttp(parseInt(size, 10)) : null}\n                name={user.name}\n                idName={user.userId}\n                size={size}\n            />\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode, useEffect, useState } from \"react\";\nimport { ClientEvent, type Room, type RoomMember, RoomStateEvent, UserEvent } from \"matrix-js-sdk/src/matrix\";\nimport { Tooltip } from \"@vector-im/compound-web\";\n\nimport { isPresenceEnabled } from \"../../../utils/presence\";\nimport { _t } from \"../../../languageHandler\";\nimport DMRoomMap from \"../../../utils/DMRoomMap\";\nimport { getJoinedNonFunctionalMembers } from \"../../../utils/room/getJoinedNonFunctionalMembers\";\nimport { useEventEmitter } from \"../../../hooks/useEventEmitter\";\nimport { BUSY_PRESENCE_NAME } from \"../rooms/PresenceLabel\";\n\ninterface Props {\n    room: Room;\n    size: string; // CSS size\n    tooltipProps?: {\n        tabIndex?: number;\n    };\n    children: ReactNode;\n}\n\nexport enum Presence {\n    // Note: the names here are used in CSS class names\n    Online = \"ONLINE\",\n    Away = \"AWAY\",\n    Offline = \"OFFLINE\",\n    Busy = \"BUSY\",\n}\n\nfunction tooltipText(variant: Presence): string {\n    switch (variant) {\n        case Presence.Online:\n            return _t(\"presence|online\");\n        case Presence.Away:\n            return _t(\"presence|away\");\n        case Presence.Offline:\n            return _t(\"presence|offline\");\n        case Presence.Busy:\n            return _t(\"presence|busy\");\n    }\n}\n\nfunction getDmMember(room: Room): RoomMember | null {\n    const otherUserId = DMRoomMap.shared().getUserIdForRoomId(room.roomId);\n    return otherUserId ? room.getMember(otherUserId) : null;\n}\n\nexport const useDmMember = (room?: Room): RoomMember | null => {\n    const [dmMember, setDmMember] = useState<RoomMember | null>(room ? getDmMember(room) : null);\n    const updateDmMember = (): void => {\n        setDmMember(room ? getDmMember(room) : null);\n    };\n\n    useEventEmitter(room?.currentState, RoomStateEvent.Members, updateDmMember);\n    useEventEmitter(room?.client, ClientEvent.AccountData, updateDmMember);\n    useEffect(updateDmMember, [room]);\n\n    return dmMember;\n};\n\nfunction getPresence(member: RoomMember | null): Presence | null {\n    if (!member?.user) return null;\n\n    const presence = member.user.presence;\n    const isOnline = member.user.currentlyActive || presence === \"online\";\n    if (BUSY_PRESENCE_NAME.matches(member.user.presence)) {\n        return Presence.Busy;\n    }\n    if (isOnline) {\n        return Presence.Online;\n    }\n    if (presence === \"offline\") {\n        return Presence.Offline;\n    }\n    if (presence === \"unavailable\") {\n        return Presence.Away;\n    }\n\n    return null;\n}\n\nexport const usePresence = (room: Room, member: RoomMember | null): Presence | null => {\n    const [presence, setPresence] = useState<Presence | null>(getPresence(member));\n    const updatePresence = (): void => {\n        setPresence(getPresence(member));\n    };\n\n    useEventEmitter(member?.user, UserEvent.Presence, updatePresence);\n    useEventEmitter(member?.user, UserEvent.CurrentlyActive, updatePresence);\n    useEffect(updatePresence, [member]);\n\n    if (getJoinedNonFunctionalMembers(room).length !== 2 || !isPresenceEnabled(room.client)) return null;\n    return presence;\n};\n\nconst WithPresenceIndicator: React.FC<Props> = ({ room, size, tooltipProps, children }) => {\n    const dmMember = useDmMember(room);\n    const presence = usePresence(room, dmMember);\n\n    let icon: JSX.Element | undefined;\n    if (presence) {\n        icon = (\n            <div\n                tabIndex={tooltipProps?.tabIndex ?? 0}\n                className={`mx_WithPresenceIndicator_icon mx_WithPresenceIndicator_icon_${presence.toLowerCase()}`}\n                style={{\n                    width: size,\n                    height: size,\n                }}\n            />\n        );\n    }\n\n    if (!presence) return <>{children}</>;\n\n    return (\n        <div className=\"mx_WithPresenceIndicator\">\n            {children}\n            <Tooltip label={tooltipText(presence)} placement=\"bottom\">\n                {icon}\n            </Tooltip>\n        </div>\n    );\n};\n\nexport default WithPresenceIndicator;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useCallback, useEffect, useState } from \"react\";\nimport { BeaconEvent, type Beacon } from \"matrix-js-sdk/src/matrix\";\n\nimport { formatDuration } from \"../../../DateUtils\";\nimport { useEventEmitterState } from \"../../../hooks/useEventEmitter\";\nimport { useInterval } from \"../../../hooks/useTimeout\";\nimport { _t } from \"../../../languageHandler\";\nimport { getBeaconMsUntilExpiry } from \"../../../utils/beacon\";\n\nconst MINUTE_MS = 60000;\nconst HOUR_MS = MINUTE_MS * 60;\nconst getUpdateInterval = (ms: number): number => {\n    // every 10 mins when more than an hour\n    if (ms > HOUR_MS) {\n        return MINUTE_MS * 10;\n    }\n    // every minute when more than a minute\n    if (ms > MINUTE_MS) {\n        return MINUTE_MS;\n    }\n    // otherwise every second\n    return 1000;\n};\nconst useMsRemaining = (beacon: Beacon): number => {\n    const beaconInfo = useEventEmitterState(beacon, BeaconEvent.Update, () => beacon.beaconInfo);\n\n    const [msRemaining, setMsRemaining] = useState(() => (beaconInfo ? getBeaconMsUntilExpiry(beaconInfo) : 0));\n\n    useEffect(() => {\n        if (!beaconInfo) {\n            return;\n        }\n        setMsRemaining(getBeaconMsUntilExpiry(beaconInfo));\n    }, [beaconInfo]);\n\n    const updateMsRemaining = useCallback(() => {\n        if (!beaconInfo) {\n            return;\n        }\n        const ms = getBeaconMsUntilExpiry(beaconInfo);\n        setMsRemaining(ms);\n    }, [beaconInfo]);\n\n    useInterval(updateMsRemaining, getUpdateInterval(msRemaining));\n\n    return msRemaining;\n};\n\nconst LiveTimeRemaining: React.FC<{ beacon: Beacon }> = ({ beacon }) => {\n    const msRemaining = useMsRemaining(beacon);\n\n    const timeRemaining = formatDuration(msRemaining);\n    const liveTimeRemaining = _t(\"time|left\", { timeRemaining });\n\n    return (\n        <span data-testid=\"room-live-share-expiry\" className=\"mx_LiveTimeRemaining\">\n            {liveTimeRemaining}\n        </span>\n    );\n};\n\nexport default LiveTimeRemaining;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type HTMLProps } from \"react\";\nimport classNames from \"classnames\";\nimport { type Beacon } from \"matrix-js-sdk/src/matrix\";\n\nimport StyledLiveBeaconIcon from \"./StyledLiveBeaconIcon\";\nimport { _t } from \"../../../languageHandler\";\nimport LiveTimeRemaining from \"./LiveTimeRemaining\";\nimport { BeaconDisplayStatus } from \"./displayStatus\";\nimport { getBeaconExpiryTimestamp } from \"../../../utils/beacon\";\nimport { formatTime } from \"../../../DateUtils\";\n\ninterface Props {\n    displayStatus: BeaconDisplayStatus;\n    displayLiveTimeRemaining?: boolean;\n    withIcon?: boolean;\n    beacon?: Beacon;\n    label?: string;\n}\n\nconst BeaconExpiryTime: React.FC<{ beacon: Beacon }> = ({ beacon }) => {\n    const expiryTime = formatTime(new Date(getBeaconExpiryTimestamp(beacon)));\n    return <span className=\"mx_BeaconStatus_expiryTime\">{_t(\"location_sharing|live_until\", { expiryTime })}</span>;\n};\n\nconst BeaconStatus: React.FC<Props & HTMLProps<HTMLDivElement>> = ({\n    beacon,\n    displayStatus,\n    displayLiveTimeRemaining,\n    label,\n    className,\n    children,\n    withIcon,\n    ...rest\n}) => {\n    const isIdle = displayStatus === BeaconDisplayStatus.Loading || displayStatus === BeaconDisplayStatus.Stopped;\n\n    return (\n        <div {...rest} className={classNames(\"mx_BeaconStatus\", `mx_BeaconStatus_${displayStatus}`, className)}>\n            {withIcon && (\n                <StyledLiveBeaconIcon\n                    className=\"mx_BeaconStatus_icon\"\n                    withError={displayStatus === BeaconDisplayStatus.Error}\n                    isIdle={isIdle}\n                />\n            )}\n            <div className=\"mx_BeaconStatus_description\">\n                {displayStatus === BeaconDisplayStatus.Loading && (\n                    <span className=\"mx_BeaconStatus_description_status\">\n                        {_t(\"location_sharing|loading_live_location\")}\n                    </span>\n                )}\n                {displayStatus === BeaconDisplayStatus.Stopped && (\n                    <span className=\"mx_BeaconStatus_description_status\">\n                        {_t(\"location_sharing|live_location_ended\")}\n                    </span>\n                )}\n                {displayStatus === BeaconDisplayStatus.Error && (\n                    <span className=\"mx_BeaconStatus_description_status\">\n                        {_t(\"location_sharing|live_location_error\")}\n                    </span>\n                )}\n                {displayStatus === BeaconDisplayStatus.Active && beacon && (\n                    <>\n                        <>\n                            <span className=\"mx_BeaconStatus_label\">{label}</span>\n                            {displayLiveTimeRemaining ? (\n                                <LiveTimeRemaining beacon={beacon} />\n                            ) : (\n                                <BeaconExpiryTime beacon={beacon} />\n                            )}\n                        </>\n                    </>\n                )}\n            </div>\n            {children}\n        </div>\n    );\n};\n\nexport default BeaconStatus;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Beacon } from \"matrix-js-sdk/src/matrix\";\nimport React, { type HTMLProps } from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { useOwnLiveBeacons } from \"../../../utils/beacon\";\nimport { preventDefaultWrapper } from \"../../../utils/NativeEventUtils\";\nimport BeaconStatus from \"./BeaconStatus\";\nimport { BeaconDisplayStatus } from \"./displayStatus\";\nimport AccessibleButton, { type ButtonEvent } from \"../elements/AccessibleButton\";\n\ninterface Props {\n    displayStatus: BeaconDisplayStatus;\n    className?: string;\n    beacon?: Beacon;\n    withIcon?: boolean;\n}\n\n/**\n * Wraps BeaconStatus with more capabilities\n * for errors and actions available for users own live beacons\n */\nconst OwnBeaconStatus: React.FC<Props & HTMLProps<HTMLDivElement>> = ({ beacon, displayStatus, ...rest }) => {\n    const {\n        hasLocationPublishError,\n        hasStopSharingError,\n        stoppingInProgress,\n        onStopSharing,\n        onResetLocationPublishError,\n    } = useOwnLiveBeacons(beacon?.identifier ? [beacon?.identifier] : []);\n\n    // combine display status with errors that only occur for user's own beacons\n    const ownDisplayStatus = hasLocationPublishError || hasStopSharingError ? BeaconDisplayStatus.Error : displayStatus;\n\n    return (\n        <BeaconStatus\n            beacon={beacon}\n            displayStatus={ownDisplayStatus}\n            label={_t(\"location_sharing|live_location_enabled\")}\n            displayLiveTimeRemaining\n            {...rest}\n        >\n            {ownDisplayStatus === BeaconDisplayStatus.Active && (\n                <AccessibleButton\n                    data-testid=\"beacon-status-stop-beacon\"\n                    kind=\"link\"\n                    // eat events here to avoid 1) the map and 2) reply or thread tiles\n                    // moving under the beacon status on stop/retry click\n                    onClick={preventDefaultWrapper<ButtonEvent>(onStopSharing)}\n                    className=\"mx_OwnBeaconStatus_button mx_OwnBeaconStatus_destructiveButton\"\n                    disabled={stoppingInProgress}\n                >\n                    {_t(\"action|stop\")}\n                </AccessibleButton>\n            )}\n            {hasLocationPublishError && (\n                <AccessibleButton\n                    data-testid=\"beacon-status-reset-wire-error\"\n                    kind=\"link\"\n                    // eat events here to avoid 1) the map and 2) reply or thread tiles\n                    // moving under the beacon status on stop/retry click\n                    onClick={preventDefaultWrapper(onResetLocationPublishError)}\n                    className=\"mx_OwnBeaconStatus_button mx_OwnBeaconStatus_destructiveButton\"\n                >\n                    {_t(\"action|retry\")}\n                </AccessibleButton>\n            )}\n            {hasStopSharingError && (\n                <AccessibleButton\n                    data-testid=\"beacon-status-stop-beacon-retry\"\n                    kind=\"link\"\n                    // eat events here to avoid 1) the map and 2) reply or thread tiles\n                    // moving under the beacon status on stop/retry click\n                    onClick={preventDefaultWrapper(onStopSharing)}\n                    className=\"mx_OwnBeaconStatus_button mx_OwnBeaconStatus_destructiveButton\"\n                >\n                    {_t(\"action|retry\")}\n                </AccessibleButton>\n            )}\n        </BeaconStatus>\n    );\n};\n\nexport default OwnBeaconStatus;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport classNames from \"classnames\";\n\nimport { Icon as LiveLocationIcon } from \"../../../../res/img/location/live-location.svg\";\n\ninterface Props extends React.SVGProps<SVGSVGElement> {\n    // use error styling when true\n    withError?: boolean;\n    isIdle?: boolean;\n}\nconst StyledLiveBeaconIcon: React.FC<Props> = ({ className, withError, isIdle, ...props }) => (\n    <LiveLocationIcon\n        {...props}\n        className={classNames(\"mx_StyledLiveBeaconIcon\", className, {\n            mx_StyledLiveBeaconIcon_error: withError,\n            mx_StyledLiveBeaconIcon_idle: isIdle,\n        })}\n    />\n);\n\nexport default StyledLiveBeaconIcon;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ContentHelpers } from \"matrix-js-sdk/src/matrix\";\n\nexport enum BeaconDisplayStatus {\n    Loading = \"Loading\",\n    Error = \"Error\",\n    Stopped = \"Stopped\",\n    Active = \"Active\",\n}\nexport const getBeaconDisplayStatus = (\n    isLive: boolean,\n    latestLocationState?: ContentHelpers.BeaconLocationState,\n    error?: Error,\n    waitingToStart?: boolean,\n): BeaconDisplayStatus => {\n    if (error) {\n        return BeaconDisplayStatus.Error;\n    }\n    if (waitingToStart) {\n        return BeaconDisplayStatus.Loading;\n    }\n    if (!isLive) {\n        return BeaconDisplayStatus.Stopped;\n    }\n    if (!latestLocationState) {\n        return BeaconDisplayStatus.Loading;\n    }\n    return BeaconDisplayStatus.Active;\n};\n","/*\nCopyright 2024,2025 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode, useState } from \"react\";\n\nimport QuestionDialog from \"./QuestionDialog\";\nimport { _t } from \"../../../languageHandler\";\nimport Field from \"../elements/Field\";\nimport { submitFeedback } from \"../../../rageshake/submit-rageshake\";\nimport StyledCheckbox from \"../elements/StyledCheckbox\";\nimport Modal from \"../../../Modal\";\nimport InfoDialog from \"./InfoDialog\";\n\ninterface IProps {\n    title: string;\n    subheading?: string;\n    rageshakeLabel?: string;\n    rageshakeData?: Record<string, any>;\n    children?: ReactNode;\n    onFinished(sendFeedback?: boolean): void;\n}\n\nconst GenericFeatureFeedbackDialog: React.FC<IProps> = ({\n    title,\n    subheading,\n    children,\n    rageshakeLabel,\n    rageshakeData = {},\n    onFinished,\n}) => {\n    const [comment, setComment] = useState(\"\");\n    const [canContact, setCanContact] = useState(false);\n\n    const sendFeedback = async (ok: boolean): Promise<void> => {\n        if (!ok) return onFinished(false);\n        // TODO: Handle rejection.\n        submitFeedback(rageshakeLabel, comment, canContact, rageshakeData);\n        onFinished(true);\n\n        Modal.createDialog(InfoDialog, {\n            title,\n            description: _t(\"feedback|sent\"),\n            button: _t(\"action|close\"),\n            hasCloseButton: false,\n            fixedWidth: false,\n        });\n    };\n\n    return (\n        <QuestionDialog\n            className=\"mx_GenericFeatureFeedbackDialog\"\n            hasCancelButton={true}\n            title={title}\n            description={\n                <React.Fragment>\n                    <div className=\"mx_GenericFeatureFeedbackDialog_subheading\">\n                        {subheading}\n                        &nbsp;\n                        {_t(\"feedback|platform_username\")}\n                        &nbsp;\n                        {children}\n                    </div>\n\n                    <Field\n                        id=\"feedbackComment\"\n                        label={_t(\"common|feedback\")}\n                        type=\"text\"\n                        autoComplete=\"off\"\n                        value={comment}\n                        element=\"textarea\"\n                        onChange={(ev) => {\n                            setComment(ev.target.value);\n                        }}\n                        autoFocus={true}\n                    />\n                    <StyledCheckbox\n                        checked={canContact}\n                        onChange={(e) => setCanContact((e.target as HTMLInputElement).checked)}\n                    >\n                        {_t(\"feedback|can_contact_label\")}\n                    </StyledCheckbox>\n                </React.Fragment>\n            }\n            button={_t(\"feedback|send_feedback_action\")}\n            buttonDisabled={!comment}\n            onFinished={sendFeedback}\n        />\n    );\n};\n\nexport default GenericFeatureFeedbackDialog;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport defaultDispatcher from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { UserTab } from \"./UserTab\";\nimport GenericFeatureFeedbackDialog from \"./GenericFeatureFeedbackDialog\";\nimport { type SettingKey } from \"../../../settings/Settings.tsx\";\n\n// XXX: Keep this around for re-use in future Betas\n\ninterface IProps {\n    featureId: SettingKey;\n    onFinished(sendFeedback?: boolean): void;\n}\n\nconst BetaFeedbackDialog: React.FC<IProps> = ({ featureId, onFinished }) => {\n    const info = SettingsStore.getBetaInfo(featureId);\n    if (!info) return null;\n\n    return (\n        <GenericFeatureFeedbackDialog\n            title={_t(\"labs|beta_feedback_title\", { featureName: info.title })}\n            subheading={info.feedbackSubheading ? _t(info.feedbackSubheading) : undefined}\n            onFinished={onFinished}\n            rageshakeLabel={info.feedbackLabel}\n            rageshakeData={Object.fromEntries(\n                (SettingsStore.getBetaInfo(featureId)?.extraSettings || []).map((k) => {\n                    return [k, SettingsStore.getValue(k)];\n                }),\n            )}\n        >\n            <AccessibleButton\n                kind=\"link_inline\"\n                onClick={() => {\n                    onFinished();\n                    defaultDispatcher.dispatch({\n                        action: Action.ViewUserSettings,\n                        initialTabId: UserTab.Labs,\n                    });\n                }}\n            >\n                {_t(\"labs|beta_feedback_leave_button\")}\n            </AccessibleButton>\n        </GenericFeatureFeedbackDialog>\n    );\n};\n\nexport default BetaFeedbackDialog;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode, useState } from \"react\";\nimport { sleep } from \"matrix-js-sdk/src/utils\";\n\nimport { _t } from \"../../../languageHandler\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { SettingLevel } from \"../../../settings/SettingLevel\";\nimport Modal from \"../../../Modal\";\nimport BetaFeedbackDialog from \"../dialogs/BetaFeedbackDialog\";\nimport SdkConfig from \"../../../SdkConfig\";\nimport SettingsFlag from \"../elements/SettingsFlag\";\nimport { useFeatureEnabled } from \"../../../hooks/useSettings\";\nimport InlineSpinner from \"../elements/InlineSpinner\";\nimport { shouldShowFeedback } from \"../../../utils/Feedback\";\nimport { type FeatureSettingKey } from \"../../../settings/Settings.tsx\";\n\n// XXX: Keep this around for re-use in future Betas\n\ninterface IProps {\n    title?: string;\n    featureId: FeatureSettingKey;\n}\n\ninterface IBetaPillProps {\n    onClick?: () => void;\n    tooltipTitle?: string;\n    tooltipCaption?: string;\n}\n\nexport const BetaPill: React.FC<IBetaPillProps> = ({\n    onClick,\n    tooltipTitle = _t(\"labs|beta_feature\"),\n    tooltipCaption = _t(\"labs|click_for_info\"),\n}) => {\n    if (onClick) {\n        return (\n            <AccessibleButton\n                className=\"mx_BetaCard_betaPill\"\n                aria-label={`${tooltipTitle} ${tooltipCaption}`}\n                title={tooltipTitle}\n                caption={tooltipCaption}\n                onClick={onClick}\n            >\n                {_t(\"common|beta\")}\n            </AccessibleButton>\n        );\n    }\n\n    return <span className=\"mx_BetaCard_betaPill\">{_t(\"common|beta\")}</span>;\n};\n\nconst BetaCard: React.FC<IProps> = ({ title: titleOverride, featureId }) => {\n    const info = SettingsStore.getBetaInfo(featureId);\n    const value = useFeatureEnabled(featureId);\n    const [busy, setBusy] = useState(false);\n    if (!info) return null; // Beta is invalid/disabled\n\n    const { title, caption, faq, image, feedbackLabel, feedbackSubheading, extraSettings, requiresRefresh } = info;\n\n    let feedbackButton;\n    if (value && feedbackLabel && feedbackSubheading && shouldShowFeedback()) {\n        feedbackButton = (\n            <AccessibleButton\n                onClick={() => {\n                    Modal.createDialog(BetaFeedbackDialog, { featureId });\n                }}\n                kind=\"primary\"\n            >\n                {_t(\"common|feedback\")}\n            </AccessibleButton>\n        );\n    }\n\n    let refreshWarning: string | undefined;\n    if (requiresRefresh) {\n        const brand = SdkConfig.get().brand;\n        refreshWarning = value ? _t(\"labs|leave_beta_reload\", { brand }) : _t(\"labs|join_beta_reload\", { brand });\n    }\n\n    let content: ReactNode;\n    if (busy) {\n        content = <InlineSpinner />;\n    } else if (value) {\n        content = _t(\"labs|leave_beta\");\n    } else {\n        content = _t(\"labs|join_beta\");\n    }\n\n    return (\n        <div className=\"mx_BetaCard\">\n            <div className=\"mx_BetaCard_columns\">\n                <div className=\"mx_BetaCard_columns_description\">\n                    <h3 className=\"mx_BetaCard_title\">\n                        <span>{titleOverride || _t(title)}</span>\n                        <BetaPill />\n                    </h3>\n                    <div className=\"mx_BetaCard_caption\">{caption()}</div>\n                    <div className=\"mx_BetaCard_buttons\">\n                        {feedbackButton}\n                        <AccessibleButton\n                            onClick={async (): Promise<void> => {\n                                setBusy(true);\n                                // make it look like we're doing something for two seconds,\n                                // otherwise users think clicking did nothing\n                                if (!requiresRefresh) {\n                                    await sleep(2000);\n                                }\n                                await SettingsStore.setValue(featureId, null, SettingLevel.DEVICE, !value);\n                                if (!requiresRefresh) {\n                                    setBusy(false);\n                                }\n                            }}\n                            kind={feedbackButton ? \"primary_outline\" : \"primary\"}\n                            disabled={busy}\n                        >\n                            {content}\n                        </AccessibleButton>\n                    </div>\n                    {refreshWarning && <div className=\"mx_BetaCard_refreshWarning\">{refreshWarning}</div>}\n                    {faq && <div className=\"mx_BetaCard_faq\">{faq(value)}</div>}\n                </div>\n                <div className=\"mx_BetaCard_columns_image_wrapper\">\n                    <img className=\"mx_BetaCard_columns_image\" src={image} alt=\"\" />\n                </div>\n            </div>\n            {extraSettings && value && (\n                <div className=\"mx_BetaCard_relatedSettings\">\n                    {extraSettings.map((key) => (\n                        <SettingsFlag key={key} name={key} level={SettingLevel.DEVICE} />\n                    ))}\n                </div>\n            )}\n        </div>\n    );\n};\n\nexport default BetaCard;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode } from \"react\";\nimport classNames from \"classnames\";\nimport { CheckIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport ContextMenu, {\n    ChevronFace,\n    type IProps as IContextMenuProps,\n    MenuItem,\n    MenuItemCheckbox,\n    MenuItemRadio,\n} from \"../../structures/ContextMenu\";\nimport { _t } from \"../../../languageHandler\";\n\ninterface IProps extends IContextMenuProps {\n    className?: string;\n    compact?: boolean;\n}\n\ninterface IOptionListProps {\n    first?: boolean;\n    red?: boolean;\n    label?: string;\n    className?: string;\n    children: ReactNode;\n}\n\ninterface IOptionProps extends React.ComponentProps<typeof MenuItem> {\n    icon?: ReactNode;\n    isDestructive?: boolean;\n}\n\ninterface ICheckboxProps extends React.ComponentProps<typeof MenuItemCheckbox> {\n    icon?: ReactNode;\n    words?: boolean;\n}\n\ninterface IRadioProps extends React.ComponentProps<typeof MenuItemRadio> {\n    icon?: ReactNode;\n}\n\nexport const IconizedContextMenuRadio: React.FC<IRadioProps> = ({ label, icon, active, className, ...props }) => {\n    return (\n        <MenuItemRadio\n            {...props}\n            className={classNames(className, {\n                mx_IconizedContextMenu_item: true,\n                mx_IconizedContextMenu_active: active,\n            })}\n            active={active}\n            label={label}\n        >\n            {icon}\n            <span className=\"mx_IconizedContextMenu_label\">{label}</span>\n            {active && <CheckIcon className=\"mx_IconizedContextMenu_checked\" />}\n        </MenuItemRadio>\n    );\n};\n\nexport const IconizedContextMenuCheckbox: React.FC<ICheckboxProps> = ({\n    label,\n    icon,\n    active,\n    className,\n    words,\n    ...props\n}) => {\n    let marker: JSX.Element | undefined;\n    if (words) {\n        marker = (\n            <span className=\"mx_IconizedContextMenu_activeText\">{active ? _t(\"common|on\") : _t(\"common|off\")}</span>\n        );\n    } else if (active) {\n        marker = <CheckIcon className=\"mx_IconizedContextMenu_checked\" />;\n    }\n\n    return (\n        <MenuItemCheckbox\n            {...props}\n            className={classNames(className, {\n                mx_IconizedContextMenu_item: true,\n                mx_IconizedContextMenu_active: active,\n            })}\n            active={active}\n            label={label}\n        >\n            {icon}\n            <span className=\"mx_IconizedContextMenu_label\">{label}</span>\n            {marker}\n        </MenuItemCheckbox>\n    );\n};\n\nexport const IconizedContextMenuOption: React.FC<IOptionProps> = ({\n    label,\n    className,\n    icon,\n    children,\n    isDestructive,\n    ...props\n}) => {\n    return (\n        <MenuItem\n            element=\"li\"\n            {...props}\n            className={classNames(className, {\n                mx_IconizedContextMenu_item: true,\n                mx_IconizedContextMenu_itemDestructive: isDestructive,\n            })}\n            label={label}\n        >\n            {icon}\n            <span className=\"mx_IconizedContextMenu_label\">{label}</span>\n            {children}\n        </MenuItem>\n    );\n};\n\nexport const IconizedContextMenuOptionList: React.FC<IOptionListProps> = ({\n    first,\n    red,\n    className,\n    label,\n    children,\n}) => {\n    const classes = classNames(\"mx_IconizedContextMenu_optionList\", className, {\n        mx_IconizedContextMenu_optionList_notFirst: !first,\n        mx_IconizedContextMenu_optionList_red: red,\n    });\n\n    return (\n        <div className={classes}>\n            {label && (\n                <div>\n                    <span className=\"mx_IconizedContextMenu_optionList_label\">{label}</span>\n                </div>\n            )}\n            {children}\n        </div>\n    );\n};\n\nconst IconizedContextMenu: React.FC<React.PropsWithChildren<IProps>> = ({ className, children, compact, ...props }) => {\n    const classes = classNames(\"mx_IconizedContextMenu\", className, {\n        mx_IconizedContextMenu_compact: compact,\n    });\n\n    return (\n        <ContextMenu chevronFace={ChevronFace.None} {...props}>\n            <ul role=\"none\" className={classes}>\n                {children}\n            </ul>\n        </ContextMenu>\n    );\n};\n\nexport default IconizedContextMenu;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type MatrixEvent, type MatrixClient, type TimelineEvents } from \"matrix-js-sdk/src/matrix\";\nimport { PollEndEvent } from \"matrix-js-sdk/src/extensible_events_v1/PollEndEvent\";\n\nimport { _t } from \"../../../languageHandler\";\nimport QuestionDialog from \"./QuestionDialog\";\nimport { findTopAnswer } from \"../messages/MPollBody\";\nimport Modal from \"../../../Modal\";\nimport ErrorDialog from \"./ErrorDialog\";\nimport { type GetRelationsForEvent } from \"../rooms/EventTile\";\n\ninterface IProps {\n    matrixClient: MatrixClient;\n    event: MatrixEvent;\n    onFinished: (success?: boolean) => void;\n    getRelationsForEvent?: GetRelationsForEvent;\n}\n\nexport default class EndPollDialog extends React.Component<IProps> {\n    private onFinished = async (endPoll: boolean): Promise<void> => {\n        if (endPoll) {\n            const room = this.props.matrixClient.getRoom(this.props.event.getRoomId());\n            const poll = room?.polls.get(this.props.event.getId()!);\n\n            if (!poll) {\n                throw new Error(\"No poll instance found in room.\");\n            }\n\n            try {\n                const responses = await poll.getResponses();\n                const topAnswer = findTopAnswer(this.props.event, responses);\n\n                const message =\n                    topAnswer === \"\" ? _t(\"poll|end_message_no_votes\") : _t(\"poll|end_message\", { topAnswer });\n\n                const endEvent = PollEndEvent.from(this.props.event.getId()!, message).serialize();\n\n                await this.props.matrixClient.sendEvent(\n                    this.props.event.getRoomId()!,\n                    endEvent.type as keyof TimelineEvents,\n                    endEvent.content as TimelineEvents[keyof TimelineEvents],\n                );\n            } catch (e) {\n                console.error(\"Failed to submit poll response event:\", e);\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"poll|error_ending_title\"),\n                    description: _t(\"poll|error_ending_description\"),\n                });\n            }\n        }\n        this.props.onFinished(endPoll);\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <QuestionDialog\n                title={_t(\"poll|end_title\")}\n                description={_t(\"poll|end_description\")}\n                button={_t(\"poll|end_title\")}\n                onFinished={(endPoll: boolean) => this.onFinished(endPoll)}\n            />\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2023 The Matrix.org Foundation C.I.C.\nCopyright 2021, 2022 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, createRef, useContext } from \"react\";\nimport {\n    EventStatus,\n    type MatrixEvent,\n    MatrixEventEvent,\n    RoomMemberEvent,\n    EventType,\n    RelationType,\n    type Relations,\n    Thread,\n    M_POLL_START,\n} from \"matrix-js-sdk/src/matrix\";\nimport {\n    CheckIcon,\n    ChevronUpIcon,\n    EditIcon,\n    ErrorSolidIcon,\n    InlineCodeIcon,\n    LinkIcon,\n    PinIcon,\n    QuoteIcon,\n    ReactionAddIcon,\n    ReplyIcon,\n    RestartIcon,\n    ThreadsIcon,\n    UnpinIcon,\n    DeleteIcon,\n    ForwardIcon,\n    PopOutIcon,\n    VisibilityOnIcon,\n    ShareIcon,\n    CopyIcon,\n    TreeIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { _t } from \"../../../languageHandler\";\nimport Modal from \"../../../Modal\";\nimport Resend from \"../../../Resend\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { isUrlPermitted } from \"../../../HtmlUtils\";\nimport { canEditContent, editEvent, isContentActionable } from \"../../../utils/EventUtils\";\nimport IconizedContextMenu, { IconizedContextMenuOption, IconizedContextMenuOptionList } from \"./IconizedContextMenu\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { type RoomPermalinkCreator } from \"../../../utils/permalinks/Permalinks\";\nimport { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport { copyPlaintext, getSelectedText } from \"../../../utils/strings\";\nimport ContextMenu, { toRightOf, type MenuProps } from \"../../structures/ContextMenu\";\nimport ReactionPicker from \"../emojipicker/ReactionPicker\";\nimport ViewSource from \"../../structures/ViewSource\";\nimport { createRedactEventDialog } from \"../dialogs/ConfirmRedactDialog\";\nimport { ShareDialog } from \"../dialogs/ShareDialog\";\nimport RoomContext, { TimelineRenderingType } from \"../../../contexts/RoomContext\";\nimport EndPollDialog from \"../dialogs/EndPollDialog\";\nimport { isPollEnded } from \"../messages/MPollBody\";\nimport { type ViewRoomPayload } from \"../../../dispatcher/payloads/ViewRoomPayload\";\nimport { type GetRelationsForEvent, type IEventTileOps } from \"../rooms/EventTile\";\nimport { type OpenForwardDialogPayload } from \"../../../dispatcher/payloads/OpenForwardDialogPayload\";\nimport { type OpenReportEventDialogPayload } from \"../../../dispatcher/payloads/OpenReportEventDialogPayload\";\nimport { createMapSiteLinkFromEvent } from \"../../../utils/location\";\nimport { getForwardableEvent } from \"../../../events/forward/getForwardableEvent\";\nimport { getShareableLocationEvent } from \"../../../events/location/getShareableLocationEvent\";\nimport { type ShowThreadPayload } from \"../../../dispatcher/payloads/ShowThreadPayload\";\nimport { CardContext } from \"../right_panel/context\";\nimport PinningUtils from \"../../../utils/PinningUtils\";\nimport PosthogTrackers from \"../../../PosthogTrackers.ts\";\n\ninterface IReplyInThreadButton {\n    mxEvent: MatrixEvent;\n    closeMenu: () => void;\n}\n\nconst ReplyInThreadButton: React.FC<IReplyInThreadButton> = ({ mxEvent, closeMenu }) => {\n    const context = useContext(CardContext);\n    const relationType = mxEvent?.getRelation()?.rel_type;\n\n    // Can't create a thread from an event with an existing relation\n    if (Boolean(relationType) && relationType !== RelationType.Thread) return null;\n\n    const onClick = (): void => {\n        if (mxEvent.getThread() && !mxEvent.isThreadRoot) {\n            dis.dispatch<ShowThreadPayload>({\n                action: Action.ShowThread,\n                rootEvent: mxEvent.getThread()!.rootEvent!,\n                initialEvent: mxEvent,\n                scroll_into_view: true,\n                highlighted: true,\n                push: context.isCard,\n            });\n        } else {\n            dis.dispatch<ShowThreadPayload>({\n                action: Action.ShowThread,\n                rootEvent: mxEvent,\n                push: context.isCard,\n            });\n        }\n        closeMenu();\n    };\n\n    return <IconizedContextMenuOption icon={<ThreadsIcon />} label={_t(\"action|reply_in_thread\")} onClick={onClick} />;\n};\n\ninterface IProps extends MenuProps {\n    /* the MatrixEvent associated with the context menu */\n    mxEvent: MatrixEvent;\n    // An optional EventTileOps implementation that can be used to unhide preview widgets\n    eventTileOps?: IEventTileOps;\n    // Callback called when the menu is dismissed\n    permalinkCreator?: RoomPermalinkCreator;\n    /* an optional function to be called when the user clicks collapse thread, if not provided hide button */\n    collapseReplyChain?(): void;\n    /* callback called when the menu is dismissed */\n    onFinished(): void;\n    // If the menu is inside a dialog, we sometimes need to close that dialog after click (forwarding)\n    onCloseDialog?(): void;\n    // True if the menu is being used as a right click menu\n    rightClick?: boolean;\n    // The Relations model from the JS SDK for reactions to `mxEvent`\n    reactions?: Relations | null;\n    // A permalink to this event or an href of an anchor element the user has clicked\n    link?: string;\n\n    getRelationsForEvent?: GetRelationsForEvent;\n}\n\ninterface IState {\n    canRedact: boolean;\n    canPin: boolean;\n    reactionPickerDisplayed: boolean;\n}\n\nexport default class MessageContextMenu extends React.Component<IProps, IState> {\n    public static contextType = RoomContext;\n    declare public context: React.ContextType<typeof RoomContext>;\n\n    private reactButtonRef = createRef<any>(); // XXX Ref to a functional component\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            canRedact: false,\n            canPin: false,\n            reactionPickerDisplayed: false,\n        };\n    }\n\n    public componentDidMount(): void {\n        MatrixClientPeg.safeGet().on(RoomMemberEvent.PowerLevel, this.checkPermissions);\n\n        // re-check the permissions on send progress (`maySendRedactionForEvent` only returns true for events that have\n        // been fully sent and echoed back, and we want to ensure the \"Remove\" option is added once that happens.)\n        this.props.mxEvent.on(MatrixEventEvent.Status, this.checkPermissions);\n\n        this.checkPermissions();\n    }\n\n    public componentWillUnmount(): void {\n        const cli = MatrixClientPeg.get();\n        if (cli) {\n            cli.removeListener(RoomMemberEvent.PowerLevel, this.checkPermissions);\n        }\n        this.props.mxEvent.removeListener(MatrixEventEvent.Status, this.checkPermissions);\n    }\n\n    private checkPermissions = (): void => {\n        const cli = MatrixClientPeg.safeGet();\n        const room = cli.getRoom(this.props.mxEvent.getRoomId());\n\n        // We explicitly decline to show the redact option on ACL events as it has a potential\n        // to obliterate the room - https://github.com/matrix-org/synapse/issues/4042\n        // Similarly for encryption events, since redacting them \"breaks everything\"\n        const canRedact =\n            !!room?.currentState.maySendRedactionForEvent(this.props.mxEvent, cli.getSafeUserId()) &&\n            this.props.mxEvent.getType() !== EventType.RoomServerAcl &&\n            this.props.mxEvent.getType() !== EventType.RoomEncryption;\n\n        const canPin = PinningUtils.canPin(cli, this.props.mxEvent) || PinningUtils.canUnpin(cli, this.props.mxEvent);\n\n        this.setState({ canRedact, canPin });\n    };\n\n    private canEndPoll(mxEvent: MatrixEvent): boolean {\n        return (\n            M_POLL_START.matches(mxEvent.getType()) &&\n            this.state.canRedact &&\n            !isPollEnded(mxEvent, MatrixClientPeg.safeGet())\n        );\n    }\n\n    /**\n     * Returns true if the current selection is entirely within a single \"mx_MTextBody\" element.\n     */\n    private isSelectionWithinSingleTextBody(): boolean {\n        const selection = window.getSelection();\n        if (!selection || selection.rangeCount === 0) return false;\n        const range = selection.getRangeAt(0);\n\n        function getParentByClass(node: Node | null, className: string): HTMLElement | null {\n            while (node) {\n                if (node instanceof HTMLElement && node.classList.contains(className)) {\n                    return node;\n                }\n                node = node.parentNode;\n            }\n            return null;\n        }\n\n        const startTextBody = getParentByClass(range.startContainer, \"mx_MTextBody\");\n        const endTextBody = getParentByClass(range.endContainer, \"mx_MTextBody\");\n\n        return !!startTextBody && startTextBody === endTextBody;\n    }\n\n    private onResendReactionsClick = (): void => {\n        for (const reaction of this.getUnsentReactions()) {\n            Resend.resend(MatrixClientPeg.safeGet(), reaction);\n        }\n        this.closeMenu();\n    };\n\n    private onJumpToRelatedEventClick = (relatedEventId: string): void => {\n        dis.dispatch({\n            action: \"view_room\",\n            room_id: this.props.mxEvent.getRoomId(),\n            event_id: relatedEventId,\n            highlighted: true,\n        });\n    };\n\n    private onReportEventClick = (): void => {\n        dis.dispatch<OpenReportEventDialogPayload>({\n            action: Action.OpenReportEventDialog,\n            event: this.props.mxEvent,\n        });\n        this.closeMenu();\n    };\n\n    private onViewSourceClick = (): void => {\n        Modal.createDialog(\n            ViewSource,\n            {\n                mxEvent: this.props.mxEvent,\n            },\n            \"mx_Dialog_viewsource\",\n        );\n        this.closeMenu();\n    };\n\n    private onRedactClick = (): void => {\n        const { mxEvent, onCloseDialog } = this.props;\n        createRedactEventDialog({\n            mxEvent,\n            onCloseDialog,\n        });\n        this.closeMenu();\n    };\n\n    private onForwardClick = (forwardableEvent: MatrixEvent) => (): void => {\n        dis.dispatch<OpenForwardDialogPayload>({\n            action: Action.OpenForwardDialog,\n            event: forwardableEvent,\n            permalinkCreator: this.props.permalinkCreator ?? null,\n        });\n        this.closeMenu();\n    };\n\n    private onPinClick = (isPinned: boolean): void => {\n        // Pin or unpin in background\n        PinningUtils.pinOrUnpinEvent(MatrixClientPeg.safeGet(), this.props.mxEvent);\n        PosthogTrackers.trackPinUnpinMessage(isPinned ? \"Pin\" : \"Unpin\", \"Timeline\");\n\n        this.closeMenu();\n    };\n\n    private closeMenu = (): void => {\n        this.props.onFinished();\n    };\n\n    private onUnhidePreviewClick = (): void => {\n        this.props.eventTileOps?.unhideWidget();\n        this.closeMenu();\n    };\n\n    private onShareClick = (e: ButtonEvent): void => {\n        e.preventDefault();\n        Modal.createDialog(ShareDialog, {\n            target: this.props.mxEvent,\n            permalinkCreator: this.props.permalinkCreator,\n        });\n        this.closeMenu();\n    };\n\n    private onCopyLinkClick = (e: ButtonEvent): void => {\n        e.preventDefault(); // So that we don't open the permalink\n        if (!this.props.link) return;\n        copyPlaintext(this.props.link);\n        this.closeMenu();\n    };\n\n    private onCollapseReplyChainClick = (): void => {\n        this.props.collapseReplyChain?.();\n        this.closeMenu();\n    };\n\n    private onCopyClick = (): void => {\n        copyPlaintext(getSelectedText());\n        this.closeMenu();\n    };\n\n    private onQuoteClick = (): void => {\n        const selectedText = getSelectedText();\n        if (selectedText) {\n            // Format as markdown quote\n            const quotedText = selectedText\n                .trim()\n                .split(/\\r?\\n/)\n                .map((line) => `> ${line}`)\n                .join(\"\\n\");\n            dis.dispatch({\n                action: Action.ComposerInsert,\n                text: \"\\n\" + quotedText + \"\\n\\n \",\n                timelineRenderingType: this.context.timelineRenderingType,\n            });\n        }\n        this.closeMenu();\n    };\n\n    private onEditClick = (): void => {\n        editEvent(\n            MatrixClientPeg.safeGet(),\n            this.props.mxEvent,\n            this.context.timelineRenderingType,\n            this.props.getRelationsForEvent,\n        );\n        this.closeMenu();\n    };\n\n    private onReplyClick = (): void => {\n        dis.dispatch({\n            action: \"reply_to_event\",\n            event: this.props.mxEvent,\n            context: this.context.timelineRenderingType,\n        });\n        this.closeMenu();\n    };\n\n    private onReactClick = (): void => {\n        this.setState({ reactionPickerDisplayed: true });\n    };\n\n    private onCloseReactionPicker = (): void => {\n        this.setState({ reactionPickerDisplayed: false });\n        this.closeMenu();\n    };\n\n    private onEndPollClick = (): void => {\n        const matrixClient = MatrixClientPeg.safeGet();\n        Modal.createDialog(\n            EndPollDialog,\n            {\n                matrixClient,\n                event: this.props.mxEvent,\n                getRelationsForEvent: this.props.getRelationsForEvent,\n            },\n            \"mx_Dialog_endPoll\",\n        );\n        this.closeMenu();\n    };\n\n    private getReactions(filter: (e: MatrixEvent) => boolean): MatrixEvent[] {\n        const cli = MatrixClientPeg.safeGet();\n        const room = cli.getRoom(this.props.mxEvent.getRoomId());\n        const eventId = this.props.mxEvent.getId();\n        return (\n            room?.getPendingEvents().filter((e) => {\n                const relation = e.getRelation();\n                return relation?.rel_type === RelationType.Annotation && relation.event_id === eventId && filter(e);\n            }) ?? []\n        );\n    }\n\n    private getUnsentReactions(): MatrixEvent[] {\n        return this.getReactions((e) => e.status === EventStatus.NOT_SENT);\n    }\n\n    private viewInRoom = (): void => {\n        dis.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            event_id: this.props.mxEvent.getId(),\n            highlighted: true,\n            room_id: this.props.mxEvent.getRoomId(),\n            metricsTrigger: undefined, // room doesn't change\n        });\n        this.closeMenu();\n    };\n\n    public render(): React.ReactNode {\n        const cli = MatrixClientPeg.safeGet();\n        const me = cli.getUserId();\n        const { mxEvent, rightClick, link, eventTileOps, reactions, collapseReplyChain, ...other } = this.props;\n        delete other.getRelationsForEvent;\n        delete other.permalinkCreator;\n\n        const eventStatus = mxEvent.status;\n        const unsentReactionsCount = this.getUnsentReactions().length;\n        const contentActionable = isContentActionable(mxEvent);\n        const permalink = this.props.permalinkCreator?.forEvent(this.props.mxEvent.getId()!);\n        // status is SENT before remote-echo, null after\n        const isSent = !eventStatus || eventStatus === EventStatus.SENT;\n        const { timelineRenderingType, canReact, canSendMessages } = this.context;\n        const isThread =\n            timelineRenderingType === TimelineRenderingType.Thread ||\n            timelineRenderingType === TimelineRenderingType.ThreadsList;\n        const isThreadRootEvent = isThread && mxEvent?.getThread()?.rootEvent === mxEvent;\n\n        let resendReactionsButton: JSX.Element | undefined;\n        if (!mxEvent.isRedacted() && unsentReactionsCount !== 0) {\n            resendReactionsButton = (\n                <IconizedContextMenuOption\n                    icon={<RestartIcon />}\n                    label={_t(\"timeline|context_menu|resent_unsent_reactions\", { unsentCount: unsentReactionsCount })}\n                    onClick={this.onResendReactionsClick}\n                />\n            );\n        }\n\n        let redactButton: JSX.Element | undefined;\n        if (isSent && this.state.canRedact) {\n            redactButton = (\n                <IconizedContextMenuOption\n                    icon={<DeleteIcon />}\n                    label={_t(\"action|remove\")}\n                    onClick={this.onRedactClick}\n                />\n            );\n        }\n\n        let openInMapSiteButton: JSX.Element | undefined;\n        const shareableLocationEvent = getShareableLocationEvent(mxEvent, cli);\n        if (shareableLocationEvent) {\n            const mapSiteLink = createMapSiteLinkFromEvent(shareableLocationEvent);\n            openInMapSiteButton = (\n                <IconizedContextMenuOption\n                    icon={<PopOutIcon />}\n                    onClick={null}\n                    label={_t(\"timeline|context_menu|open_in_osm\")}\n                    element=\"a\"\n                    {...{\n                        href: mapSiteLink,\n                        target: \"_blank\",\n                        rel: \"noreferrer noopener\",\n                    }}\n                />\n            );\n        }\n\n        let forwardButton: JSX.Element | undefined;\n        const forwardableEvent = getForwardableEvent(mxEvent, cli);\n        if (contentActionable && forwardableEvent) {\n            forwardButton = (\n                <IconizedContextMenuOption\n                    icon={<ForwardIcon />}\n                    label={_t(\"action|forward\")}\n                    onClick={this.onForwardClick(forwardableEvent)}\n                />\n            );\n        }\n\n        // This is specifically not behind the developerMode flag to give people insight into the Matrix\n        const viewSourceButton = (\n            <IconizedContextMenuOption\n                icon={<InlineCodeIcon />}\n                label={_t(\"timeline|context_menu|view_source\")}\n                onClick={this.onViewSourceClick}\n            />\n        );\n\n        let unhidePreviewButton: JSX.Element | undefined;\n        if (eventTileOps?.isWidgetHidden()) {\n            unhidePreviewButton = (\n                <IconizedContextMenuOption\n                    icon={<VisibilityOnIcon />}\n                    label={_t(\"timeline|context_menu|show_url_preview\")}\n                    onClick={this.onUnhidePreviewClick}\n                />\n            );\n        }\n\n        let permalinkButton: JSX.Element | undefined;\n        if (permalink) {\n            permalinkButton = (\n                <IconizedContextMenuOption\n                    icon={<ShareIcon />}\n                    onClick={this.onShareClick}\n                    label={_t(\"action|share\")}\n                    element=\"a\"\n                    {\n                        // XXX: Typescript signature for AccessibleButton doesn't work properly for non-inputs like `a`\n                        ...{\n                            href: permalink,\n                            target: \"_blank\",\n                            rel: \"noreferrer noopener\",\n                        }\n                    }\n                />\n            );\n        }\n\n        let endPollButton: JSX.Element | undefined;\n        if (this.canEndPoll(mxEvent)) {\n            endPollButton = (\n                <IconizedContextMenuOption\n                    icon={<CheckIcon />}\n                    label={_t(\"poll|end_title\")}\n                    onClick={this.onEndPollClick}\n                />\n            );\n        }\n\n        // Bridges can provide a 'external_url' to link back to the source.\n        let externalURLButton: JSX.Element | undefined;\n        if (\n            typeof mxEvent.getContent().external_url === \"string\" &&\n            isUrlPermitted(mxEvent.getContent().external_url)\n        ) {\n            externalURLButton = (\n                <IconizedContextMenuOption\n                    icon={<LinkIcon />}\n                    onClick={this.closeMenu}\n                    label={_t(\"timeline|context_menu|external_url\")}\n                    element=\"a\"\n                    {\n                        // XXX: Typescript signature for AccessibleButton doesn't work properly for non-inputs like `a`\n                        ...{\n                            target: \"_blank\",\n                            rel: \"noreferrer noopener\",\n                            href: mxEvent.getContent().external_url,\n                        }\n                    }\n                />\n            );\n        }\n\n        let collapseReplyChainButton: JSX.Element | undefined;\n        if (collapseReplyChain) {\n            collapseReplyChainButton = (\n                <IconizedContextMenuOption\n                    icon={<ChevronUpIcon />}\n                    label={_t(\"timeline|context_menu|collapse_reply_thread\")}\n                    onClick={this.onCollapseReplyChainClick}\n                />\n            );\n        }\n\n        let jumpToRelatedEventButton: JSX.Element | undefined;\n        const relatedEventId = mxEvent.getAssociatedId();\n        if (relatedEventId && SettingsStore.getValue(\"developerMode\")) {\n            jumpToRelatedEventButton = (\n                <IconizedContextMenuOption\n                    icon={<TreeIcon />}\n                    label={_t(\"timeline|context_menu|view_related_event\")}\n                    onClick={() => this.onJumpToRelatedEventClick(relatedEventId)}\n                />\n            );\n        }\n\n        let reportEventButton: JSX.Element | undefined;\n        if (mxEvent.getSender() !== me) {\n            reportEventButton = (\n                <IconizedContextMenuOption\n                    icon={<ErrorSolidIcon />}\n                    label={_t(\"timeline|context_menu|report\")}\n                    onClick={this.onReportEventClick}\n                />\n            );\n        }\n\n        let copyLinkButton: JSX.Element | undefined;\n        if (link) {\n            copyLinkButton = (\n                <IconizedContextMenuOption\n                    icon={<CopyIcon />}\n                    onClick={this.onCopyLinkClick}\n                    label={_t(\"action|copy_link\")}\n                    element=\"a\"\n                    {\n                        // XXX: Typescript signature for AccessibleButton doesn't work properly for non-inputs like `a`\n                        ...{\n                            href: link,\n                            target: \"_blank\",\n                            rel: \"noreferrer noopener\",\n                        }\n                    }\n                />\n            );\n        }\n\n        const selectedText = getSelectedText();\n\n        let copyButton: JSX.Element | undefined;\n        if (rightClick && selectedText) {\n            copyButton = (\n                <IconizedContextMenuOption\n                    icon={<CopyIcon />}\n                    label={_t(\"action|copy\")}\n                    triggerOnMouseDown={true} // We use onMouseDown so that the selection isn't cleared when we click\n                    onClick={this.onCopyClick}\n                />\n            );\n        }\n\n        let quoteButton: JSX.Element | undefined;\n        if (rightClick && selectedText && selectedText.trim().length > 0 && this.isSelectionWithinSingleTextBody()) {\n            quoteButton = (\n                <IconizedContextMenuOption\n                    icon={<QuoteIcon />}\n                    label={_t(\"action|quote\")}\n                    triggerOnMouseDown={true}\n                    onClick={this.onQuoteClick}\n                />\n            );\n        }\n\n        let editButton: JSX.Element | undefined;\n        if (rightClick && canEditContent(cli, mxEvent)) {\n            editButton = (\n                <IconizedContextMenuOption icon={<EditIcon />} label={_t(\"action|edit\")} onClick={this.onEditClick} />\n            );\n        }\n\n        let replyButton: JSX.Element | undefined;\n        if (rightClick && contentActionable && canSendMessages) {\n            replyButton = (\n                <IconizedContextMenuOption\n                    icon={<ReplyIcon />}\n                    label={_t(\"action|reply\")}\n                    onClick={this.onReplyClick}\n                />\n            );\n        }\n\n        let replyInThreadButton: JSX.Element | undefined;\n        if (\n            rightClick &&\n            contentActionable &&\n            canSendMessages &&\n            Thread.hasServerSideSupport &&\n            timelineRenderingType !== TimelineRenderingType.Thread\n        ) {\n            replyInThreadButton = <ReplyInThreadButton mxEvent={mxEvent} closeMenu={this.closeMenu} />;\n        }\n\n        let reactButton: JSX.Element | undefined;\n        if (rightClick && contentActionable && canReact) {\n            reactButton = (\n                <IconizedContextMenuOption\n                    icon={<ReactionAddIcon />}\n                    label={_t(\"action|react\")}\n                    onClick={this.onReactClick}\n                    inputRef={this.reactButtonRef}\n                />\n            );\n        }\n\n        let pinButton: JSX.Element | undefined;\n        if (rightClick && this.state.canPin) {\n            const isPinned = PinningUtils.isPinned(MatrixClientPeg.safeGet(), this.props.mxEvent);\n            pinButton = (\n                <IconizedContextMenuOption\n                    icon={isPinned ? <UnpinIcon /> : <PinIcon />}\n                    label={isPinned ? _t(\"action|unpin\") : _t(\"action|pin\")}\n                    onClick={() => this.onPinClick(isPinned)}\n                />\n            );\n        }\n\n        let viewInRoomButton: JSX.Element | undefined;\n        if (isThreadRootEvent) {\n            viewInRoomButton = (\n                <IconizedContextMenuOption\n                    icon={<VisibilityOnIcon />}\n                    label={_t(\"timeline|mab|view_in_room\")}\n                    onClick={this.viewInRoom}\n                />\n            );\n        }\n\n        let nativeItemsList: JSX.Element | undefined;\n        if (copyButton || quoteButton || copyLinkButton) {\n            nativeItemsList = (\n                <IconizedContextMenuOptionList>\n                    {copyButton}\n                    {quoteButton}\n                    {copyLinkButton}\n                </IconizedContextMenuOptionList>\n            );\n        }\n\n        let quickItemsList: JSX.Element | undefined;\n        if (editButton || replyButton || reactButton || pinButton) {\n            quickItemsList = (\n                <IconizedContextMenuOptionList>\n                    {reactButton}\n                    {replyButton}\n                    {replyInThreadButton}\n                    {editButton}\n                    {pinButton}\n                </IconizedContextMenuOptionList>\n            );\n        }\n\n        const commonItemsList = (\n            <IconizedContextMenuOptionList>\n                {viewInRoomButton}\n                {openInMapSiteButton}\n                {endPollButton}\n                {forwardButton}\n                {permalinkButton}\n                {reportEventButton}\n                {externalURLButton}\n                {jumpToRelatedEventButton}\n                {unhidePreviewButton}\n                {viewSourceButton}\n                {resendReactionsButton}\n                {collapseReplyChainButton}\n            </IconizedContextMenuOptionList>\n        );\n\n        let redactItemList: JSX.Element | undefined;\n        if (redactButton) {\n            redactItemList = <IconizedContextMenuOptionList red>{redactButton}</IconizedContextMenuOptionList>;\n        }\n\n        let reactionPicker: JSX.Element | undefined;\n        if (this.state.reactionPickerDisplayed) {\n            const buttonRect = (this.reactButtonRef.current as HTMLElement)?.getBoundingClientRect();\n            reactionPicker = (\n                <ContextMenu {...toRightOf(buttonRect)} onFinished={this.closeMenu} managed={false} focusLock>\n                    <ReactionPicker mxEvent={mxEvent} onFinished={this.onCloseReactionPicker} reactions={reactions} />\n                </ContextMenu>\n            );\n        }\n\n        return (\n            <React.Fragment>\n                <IconizedContextMenu\n                    {...other}\n                    className=\"mx_MessageContextMenu\"\n                    compact={true}\n                    data-testid=\"mx_MessageContextMenu\"\n                >\n                    {nativeItemsList}\n                    {quickItemsList}\n                    {commonItemsList}\n                    {redactItemList}\n                </IconizedContextMenu>\n                {reactionPicker}\n            </React.Fragment>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { LabsIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport Modal from \"../../../Modal\";\nimport DevtoolsDialog from \"../dialogs/DevtoolsDialog\";\nimport { IconizedContextMenuOption } from \"./IconizedContextMenu\";\nimport { _t } from \"../../../languageHandler\";\n\ninterface Props {\n    onFinished: () => void;\n    roomId: string;\n}\n\nexport const DeveloperToolsOption: React.FC<Props> = ({ onFinished, roomId }) => {\n    return (\n        <IconizedContextMenuOption\n            onClick={() => {\n                Modal.createDialog(\n                    DevtoolsDialog,\n                    {\n                        roomId: roomId,\n                    },\n                    \"mx_DevtoolsDialog_wrapper\",\n                );\n                onFinished();\n            }}\n            label={_t(\"devtools|title\")}\n            icon={<LabsIcon />}\n        />\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport React, { type JSX, useContext } from \"react\";\nimport {\n    FavouriteSolidIcon,\n    LinkIcon,\n    SettingsSolidIcon,\n    ArrowDownIcon,\n    MarkAsReadIcon,\n    MarkAsUnreadIcon,\n    LeaveIcon,\n    UserAddIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport RoomListActions from \"../../../actions/RoomListActions\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { useEventEmitterState } from \"../../../hooks/useEventEmitter\";\nimport { useUnreadNotifications } from \"../../../hooks/useUnreadNotifications\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { _t } from \"../../../languageHandler\";\nimport { NotificationLevel } from \"../../../stores/notifications/NotificationLevel\";\nimport { DefaultTagID, type TagID } from \"../../../stores/room-list/models\";\nimport RoomListStore, { LISTS_UPDATE_EVENT } from \"../../../stores/room-list/RoomListStore\";\nimport DMRoomMap from \"../../../utils/DMRoomMap\";\nimport { clearRoomNotification, setMarkedUnreadState } from \"../../../utils/notifications\";\nimport { type IProps as IContextMenuProps } from \"../../structures/ContextMenu\";\nimport IconizedContextMenu, {\n    IconizedContextMenuCheckbox,\n    IconizedContextMenuOption,\n    IconizedContextMenuOptionList,\n} from \"../context_menus/IconizedContextMenu\";\nimport { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport { shouldShowComponent } from \"../../../customisations/helpers/UIComponents\";\nimport { UIComponent } from \"../../../settings/UIFeature\";\nimport { DeveloperToolsOption } from \"./DeveloperToolsOption\";\nimport { useSettingValue } from \"../../../hooks/useSettings\";\n\nexport interface RoomGeneralContextMenuProps extends IContextMenuProps {\n    room: Room;\n    /**\n     * Called when the 'favourite' option is selected, after the menu has processed\n     * the mouse or keyboard event.\n     * @param event The event that caused the option to be selected.\n     */\n    onPostFavoriteClick?: (event: ButtonEvent) => void;\n    /**\n     * Called when the 'low priority' option is selected, after the menu has processed\n     * the mouse or keyboard event.\n     * @param event The event that caused the option to be selected.\n     */\n    onPostLowPriorityClick?: (event: ButtonEvent) => void;\n    /**\n     * Called when the 'invite' option is selected, after the menu has processed\n     * the mouse or keyboard event.\n     * @param event The event that caused the option to be selected.\n     */\n    onPostInviteClick?: (event: ButtonEvent) => void;\n    /**\n     * Called when the 'copy link' option is selected, after the menu has processed\n     * the mouse or keyboard event.\n     * @param event The event that caused the option to be selected.\n     */\n    onPostCopyLinkClick?: (event: ButtonEvent) => void;\n    /**\n     * Called when the 'settings' option is selected, after the menu has processed\n     * the mouse or keyboard event.\n     * @param event The event that caused the option to be selected.\n     */\n    onPostSettingsClick?: (event: ButtonEvent) => void;\n    /**\n     * Called when the 'forget room' option is selected, after the menu has processed\n     * the mouse or keyboard event.\n     * @param event The event that caused the option to be selected.\n     */\n    onPostForgetClick?: (event: ButtonEvent) => void;\n    /**\n     * Called when the 'leave' option is selected, after the menu has processed\n     * the mouse or keyboard event.\n     * @param event The event that caused the option to be selected.\n     */\n    onPostLeaveClick?: (event: ButtonEvent) => void;\n    /**\n     * Called when the 'mark as read' option is selected, after the menu has processed\n     * the mouse or keyboard event.\n     * @param event The event that caused the option to be selected.\n     */\n    onPostMarkAsReadClick?: (event: ButtonEvent) => void;\n    /**\n     * Called when the 'mark as unread' option is selected, after the menu has processed\n     * the mouse or keyboard event.\n     * @param event The event that caused the option to be selected.\n     */\n    onPostMarkAsUnreadClick?: (event: ButtonEvent) => void;\n}\n\n/**\n * Room context menu accessible via the room list.\n */\nexport const RoomGeneralContextMenu: React.FC<RoomGeneralContextMenuProps> = ({\n    room,\n    onFinished,\n    onPostFavoriteClick,\n    onPostLowPriorityClick,\n    onPostInviteClick,\n    onPostCopyLinkClick,\n    onPostSettingsClick,\n    onPostLeaveClick,\n    onPostForgetClick,\n    onPostMarkAsReadClick,\n    onPostMarkAsUnreadClick,\n    ...props\n}) => {\n    const cli = useContext(MatrixClientContext);\n    const roomTags = useEventEmitterState(RoomListStore.instance, LISTS_UPDATE_EVENT, () =>\n        RoomListStore.instance.getTagsForRoom(room),\n    );\n    const isDm = DMRoomMap.shared().getUserIdForRoomId(room.roomId);\n    const wrapHandler = (\n        handler: (ev: ButtonEvent) => void,\n        postHandler?: (ev: ButtonEvent) => void,\n        persistent = false,\n    ): ((ev: ButtonEvent) => void) => {\n        return (ev: ButtonEvent) => {\n            ev.preventDefault();\n            ev.stopPropagation();\n\n            handler(ev);\n\n            const action = getKeyBindingsManager().getAccessibilityAction(ev as React.KeyboardEvent);\n            if (!persistent || action === KeyBindingAction.Enter) {\n                onFinished();\n            }\n            postHandler?.(ev);\n        };\n    };\n\n    const onTagRoom = (ev: ButtonEvent, tagId: TagID): void => {\n        if (!cli) return;\n        if (tagId === DefaultTagID.Favourite || tagId === DefaultTagID.LowPriority) {\n            const inverseTag = tagId === DefaultTagID.Favourite ? DefaultTagID.LowPriority : DefaultTagID.Favourite;\n            const isApplied = RoomListStore.instance.getTagsForRoom(room).includes(tagId);\n            const removeTag = isApplied ? tagId : inverseTag;\n            const addTag = isApplied ? null : tagId;\n            dis.dispatch(RoomListActions.tagRoom(cli, room, removeTag, addTag, 0));\n        } else {\n            logger.warn(`Unexpected tag ${tagId} applied to ${room.roomId}`);\n        }\n    };\n\n    const isFavorite = roomTags.includes(DefaultTagID.Favourite);\n    const favoriteOption: JSX.Element = (\n        <IconizedContextMenuCheckbox\n            onClick={wrapHandler((ev) => onTagRoom(ev, DefaultTagID.Favourite), onPostFavoriteClick, true)}\n            active={isFavorite}\n            label={isFavorite ? _t(\"room|context_menu|unfavourite\") : _t(\"room|context_menu|favourite\")}\n            icon={<FavouriteSolidIcon />}\n        />\n    );\n\n    const isLowPriority = roomTags.includes(DefaultTagID.LowPriority);\n    const lowPriorityOption: JSX.Element = (\n        <IconizedContextMenuCheckbox\n            onClick={wrapHandler((ev) => onTagRoom(ev, DefaultTagID.LowPriority), onPostLowPriorityClick, true)}\n            active={isLowPriority}\n            label={_t(\"room|context_menu|low_priority\")}\n            icon={<ArrowDownIcon />}\n        />\n    );\n\n    let inviteOption: JSX.Element | null = null;\n    if (room.canInvite(cli.getUserId()!) && !isDm && shouldShowComponent(UIComponent.InviteUsers)) {\n        inviteOption = (\n            <IconizedContextMenuOption\n                onClick={wrapHandler(\n                    () =>\n                        dis.dispatch({\n                            action: \"view_invite\",\n                            roomId: room.roomId,\n                        }),\n                    onPostInviteClick,\n                )}\n                label={_t(\"action|invite\")}\n                icon={<UserAddIcon />}\n            />\n        );\n    }\n\n    let copyLinkOption: JSX.Element | null = null;\n    if (!isDm) {\n        copyLinkOption = (\n            <IconizedContextMenuOption\n                onClick={wrapHandler(\n                    () =>\n                        dis.dispatch({\n                            action: \"copy_room\",\n                            room_id: room.roomId,\n                        }),\n                    onPostCopyLinkClick,\n                )}\n                label={_t(\"room|context_menu|copy_link\")}\n                icon={<LinkIcon />}\n            />\n        );\n    }\n\n    const settingsOption: JSX.Element = (\n        <IconizedContextMenuOption\n            onClick={wrapHandler(\n                () =>\n                    dis.dispatch({\n                        action: \"open_room_settings\",\n                        room_id: room.roomId,\n                    }),\n                onPostSettingsClick,\n            )}\n            label={_t(\"common|settings\")}\n            icon={<SettingsSolidIcon />}\n        />\n    );\n\n    let leaveOption: JSX.Element;\n    if (roomTags.includes(DefaultTagID.Archived)) {\n        leaveOption = (\n            <IconizedContextMenuOption\n                icon={<LeaveIcon />}\n                label={_t(\"room|context_menu|forget\")}\n                className=\"mx_IconizedContextMenu_option_red\"\n                onClick={wrapHandler(\n                    () =>\n                        dis.dispatch({\n                            action: \"forget_room\",\n                            room_id: room.roomId,\n                        }),\n                    onPostForgetClick,\n                )}\n            />\n        );\n    } else {\n        leaveOption = (\n            <IconizedContextMenuOption\n                onClick={wrapHandler(\n                    () =>\n                        dis.dispatch({\n                            action: \"leave_room\",\n                            room_id: room.roomId,\n                        }),\n                    onPostLeaveClick,\n                )}\n                label={_t(\"action|leave\")}\n                className=\"mx_IconizedContextMenu_option_red\"\n                icon={<LeaveIcon />}\n            />\n        );\n    }\n\n    const { level } = useUnreadNotifications(room);\n    const markAsReadOption: JSX.Element | null = (() => {\n        if (level > NotificationLevel.None) {\n            return (\n                <IconizedContextMenuOption\n                    onClick={wrapHandler(() => {\n                        clearRoomNotification(room, cli);\n                        onFinished?.();\n                    }, onPostMarkAsReadClick)}\n                    label={_t(\"room|context_menu|mark_read\")}\n                    icon={<MarkAsReadIcon />}\n                />\n            );\n        } else if (!roomTags.includes(DefaultTagID.Archived)) {\n            return (\n                <IconizedContextMenuOption\n                    onClick={wrapHandler(() => {\n                        setMarkedUnreadState(room, cli, true);\n                        onFinished?.();\n                    }, onPostMarkAsUnreadClick)}\n                    label={_t(\"room|context_menu|mark_unread\")}\n                    icon={<MarkAsUnreadIcon />}\n                />\n            );\n        } else {\n            return null;\n        }\n    })();\n\n    const developerModeEnabled = useSettingValue(\"developerMode\");\n    const developerToolsOption = developerModeEnabled ? (\n        <DeveloperToolsOption onFinished={onFinished} roomId={room.roomId} />\n    ) : null;\n\n    return (\n        <IconizedContextMenu {...props} onFinished={onFinished} className=\"mx_RoomGeneralContextMenu\" compact>\n            <IconizedContextMenuOptionList>\n                {markAsReadOption}\n                {!roomTags.includes(DefaultTagID.Archived) && (\n                    <>\n                        {favoriteOption}\n                        {lowPriorityOption}\n                        {inviteOption}\n                        {copyLinkOption}\n                        {settingsOption}\n                    </>\n                )}\n                {developerToolsOption}\n            </IconizedContextMenuOptionList>\n            <IconizedContextMenuOptionList red>{leaveOption}</IconizedContextMenuOptionList>\n        </IconizedContextMenu>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport React, { type JSX } from \"react\";\n\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { useNotificationState } from \"../../../hooks/useRoomNotificationState\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { _t } from \"../../../languageHandler\";\nimport { RoomNotifState } from \"../../../RoomNotifs\";\nimport { type IProps as IContextMenuProps } from \"../../structures/ContextMenu\";\nimport IconizedContextMenu, {\n    IconizedContextMenuOptionList,\n    IconizedContextMenuRadio,\n} from \"../context_menus/IconizedContextMenu\";\nimport { type ButtonEvent } from \"../elements/AccessibleButton\";\n\ninterface IProps extends IContextMenuProps {\n    room: Room;\n}\n\nexport const RoomNotificationContextMenu: React.FC<IProps> = ({ room, onFinished, ...props }) => {\n    const [notificationState, setNotificationState] = useNotificationState(room);\n\n    const wrapHandler = (handler: (ev: ButtonEvent) => void, persistent = false): ((ev: ButtonEvent) => void) => {\n        return (ev: ButtonEvent) => {\n            ev.preventDefault();\n            ev.stopPropagation();\n\n            handler(ev);\n\n            const action = getKeyBindingsManager().getAccessibilityAction(ev as React.KeyboardEvent);\n            if (!persistent || action === KeyBindingAction.Enter) {\n                onFinished();\n            }\n        };\n    };\n\n    const defaultOption: JSX.Element = (\n        <IconizedContextMenuRadio\n            label={_t(\"room|context_menu|notifications_default\")}\n            active={notificationState === RoomNotifState.AllMessages}\n            onClick={wrapHandler(() => setNotificationState(RoomNotifState.AllMessages))}\n        />\n    );\n\n    const allMessagesOption: JSX.Element = (\n        <IconizedContextMenuRadio\n            label={_t(\"notifications|all_messages\")}\n            active={notificationState === RoomNotifState.AllMessagesLoud}\n            onClick={wrapHandler(() => setNotificationState(RoomNotifState.AllMessagesLoud))}\n        />\n    );\n\n    const mentionsOption: JSX.Element = (\n        <IconizedContextMenuRadio\n            label={_t(\"notifications|mentions_keywords\")}\n            active={notificationState === RoomNotifState.MentionsOnly}\n            onClick={wrapHandler(() => setNotificationState(RoomNotifState.MentionsOnly))}\n        />\n    );\n\n    const muteOption: JSX.Element = (\n        <IconizedContextMenuRadio\n            label={_t(\"room|context_menu|notifications_mute\")}\n            active={notificationState === RoomNotifState.Mute}\n            onClick={wrapHandler(() => setNotificationState(RoomNotifState.Mute))}\n        />\n    );\n\n    return (\n        <IconizedContextMenu {...props} onFinished={onFinished} className=\"mx_RoomNotificationContextMenu\" compact>\n            <IconizedContextMenuOptionList first>\n                {defaultOption}\n                {allMessagesOption}\n                {mentionsOption}\n                {muteOption}\n            </IconizedContextMenuOptionList>\n        </IconizedContextMenu>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useContext } from \"react\";\nimport { type Room, EventType, RoomType } from \"matrix-js-sdk/src/matrix\";\nimport {\n    HomeSolidIcon,\n    PlusIcon,\n    SettingsSolidIcon,\n    LeaveIcon,\n    SearchIcon,\n    PreferencesIcon,\n    UserAddIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { type IProps as IContextMenuProps } from \"../../structures/ContextMenu\";\nimport IconizedContextMenu, { IconizedContextMenuOption, IconizedContextMenuOptionList } from \"./IconizedContextMenu\";\nimport { _t } from \"../../../languageHandler\";\nimport {\n    shouldShowSpaceSettings,\n    showCreateNewRoom,\n    showCreateNewSubspace,\n    showSpaceInvite,\n    showSpacePreferences,\n    showSpaceSettings,\n} from \"../../../utils/space\";\nimport { leaveSpace } from \"../../../utils/leave-behaviour\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport defaultDispatcher from \"../../../dispatcher/dispatcher\";\nimport { BetaPill } from \"../beta/BetaCard\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { useFeatureEnabled } from \"../../../hooks/useSettings\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { shouldShowComponent } from \"../../../customisations/helpers/UIComponents\";\nimport { UIComponent } from \"../../../settings/UIFeature\";\nimport PosthogTrackers from \"../../../PosthogTrackers\";\nimport { type ViewRoomPayload } from \"../../../dispatcher/payloads/ViewRoomPayload\";\n\ninterface IProps extends IContextMenuProps {\n    space?: Room;\n    hideHeader?: boolean;\n}\n\nconst SpaceContextMenu: React.FC<IProps> = ({ space, hideHeader, onFinished, ...props }) => {\n    const cli = useContext(MatrixClientContext);\n    const userId = cli.getSafeUserId();\n    const videoRoomsEnabled = useFeatureEnabled(\"feature_video_rooms\");\n    const elementCallVideoRoomsEnabled = useFeatureEnabled(\"feature_element_call_video_rooms\");\n\n    if (!space) return null;\n\n    let inviteOption: JSX.Element | null = null;\n    if (space.getJoinRule() === \"public\" || space.canInvite(userId)) {\n        const onInviteClick = (ev: ButtonEvent): void => {\n            ev.preventDefault();\n            ev.stopPropagation();\n\n            showSpaceInvite(space);\n            onFinished();\n        };\n\n        inviteOption = (\n            <IconizedContextMenuOption\n                data-testid=\"invite-option\"\n                className=\"mx_SpacePanel_contextMenu_inviteButton\"\n                icon={<UserAddIcon />}\n                label={_t(\"action|invite\")}\n                onClick={onInviteClick}\n            />\n        );\n    }\n\n    let settingsOption: JSX.Element | null = null;\n    let leaveOption: JSX.Element | null = null;\n    if (shouldShowSpaceSettings(space)) {\n        const onSettingsClick = (ev: ButtonEvent): void => {\n            ev.preventDefault();\n            ev.stopPropagation();\n\n            showSpaceSettings(space);\n            onFinished();\n        };\n\n        settingsOption = (\n            <IconizedContextMenuOption\n                data-testid=\"settings-option\"\n                icon={<SettingsSolidIcon />}\n                label={_t(\"common|settings\")}\n                onClick={onSettingsClick}\n            />\n        );\n    } else {\n        const onLeaveClick = (ev: ButtonEvent): void => {\n            ev.preventDefault();\n            ev.stopPropagation();\n\n            leaveSpace(space);\n            onFinished();\n        };\n\n        leaveOption = (\n            <IconizedContextMenuOption\n                data-testid=\"leave-option\"\n                icon={<LeaveIcon />}\n                className=\"mx_IconizedContextMenu_option_red\"\n                label={_t(\"space|leave_dialog_action\")}\n                onClick={onLeaveClick}\n            />\n        );\n    }\n\n    let devtoolsOption: JSX.Element | null = null;\n    if (SettingsStore.getValue(\"developerMode\")) {\n        const onViewTimelineClick = (ev: ButtonEvent): void => {\n            ev.preventDefault();\n            ev.stopPropagation();\n\n            defaultDispatcher.dispatch<ViewRoomPayload>({\n                action: Action.ViewRoom,\n                room_id: space.roomId,\n                forceTimeline: true,\n                metricsTrigger: undefined, // room doesn't change\n            });\n            onFinished();\n        };\n\n        devtoolsOption = (\n            <IconizedContextMenuOption\n                icon={<SettingsSolidIcon />}\n                label={_t(\"space|context_menu|devtools_open_timeline\")}\n                onClick={onViewTimelineClick}\n            />\n        );\n    }\n\n    const hasPermissionToAddSpaceChild = space.currentState.maySendStateEvent(EventType.SpaceChild, userId);\n    const canAddRooms = hasPermissionToAddSpaceChild && shouldShowComponent(UIComponent.CreateRooms);\n    const canAddVideoRooms = canAddRooms && videoRoomsEnabled;\n    const canAddSubSpaces = hasPermissionToAddSpaceChild && shouldShowComponent(UIComponent.CreateSpaces);\n\n    let newRoomSection: JSX.Element | null = null;\n    if (canAddRooms || canAddSubSpaces) {\n        const onNewRoomClick = (ev: ButtonEvent): void => {\n            ev.preventDefault();\n            ev.stopPropagation();\n\n            PosthogTrackers.trackInteraction(\"WebSpaceContextMenuNewRoomItem\", ev);\n            showCreateNewRoom(space);\n            onFinished();\n        };\n\n        const onNewVideoRoomClick = (ev: ButtonEvent): void => {\n            ev.preventDefault();\n            ev.stopPropagation();\n\n            showCreateNewRoom(space, elementCallVideoRoomsEnabled ? RoomType.UnstableCall : RoomType.ElementVideo);\n            onFinished();\n        };\n\n        const onNewSubspaceClick = (ev: ButtonEvent): void => {\n            ev.preventDefault();\n            ev.stopPropagation();\n\n            showCreateNewSubspace(space);\n            onFinished();\n        };\n\n        newRoomSection = (\n            <>\n                <div data-testid=\"add-to-space-header\" className=\"mx_SpacePanel_contextMenu_separatorLabel\">\n                    {_t(\"action|add\")}\n                </div>\n                {canAddRooms && (\n                    <IconizedContextMenuOption\n                        data-testid=\"new-room-option\"\n                        icon={<PlusIcon />}\n                        label={_t(\"common|room\")}\n                        onClick={onNewRoomClick}\n                    />\n                )}\n                {canAddVideoRooms && (\n                    <IconizedContextMenuOption\n                        data-testid=\"new-video-room-option\"\n                        icon={<PlusIcon />}\n                        label={_t(\"common|video_room\")}\n                        onClick={onNewVideoRoomClick}\n                    >\n                        <BetaPill />\n                    </IconizedContextMenuOption>\n                )}\n                {canAddSubSpaces && (\n                    <IconizedContextMenuOption\n                        data-testid=\"new-subspace-option\"\n                        icon={<PlusIcon />}\n                        label={_t(\"common|space\")}\n                        onClick={onNewSubspaceClick}\n                    >\n                        <BetaPill />\n                    </IconizedContextMenuOption>\n                )}\n            </>\n        );\n    }\n\n    const onPreferencesClick = (ev: ButtonEvent): void => {\n        ev.preventDefault();\n        ev.stopPropagation();\n\n        showSpacePreferences(space);\n        onFinished();\n    };\n\n    const openSpace = (ev: ButtonEvent): void => {\n        ev.preventDefault();\n        ev.stopPropagation();\n\n        defaultDispatcher.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            room_id: space.roomId,\n            metricsTrigger: undefined, // other\n        });\n        onFinished();\n    };\n\n    const onExploreRoomsClick = (ev: ButtonEvent): void => {\n        PosthogTrackers.trackInteraction(\"WebSpaceContextMenuExploreRoomsItem\", ev);\n        openSpace(ev);\n    };\n\n    const onHomeClick = (ev: ButtonEvent): void => {\n        PosthogTrackers.trackInteraction(\"WebSpaceContextMenuHomeItem\", ev);\n        openSpace(ev);\n    };\n\n    return (\n        <IconizedContextMenu {...props} onFinished={onFinished} className=\"mx_SpacePanel_contextMenu\" compact>\n            {!hideHeader && <div className=\"mx_SpacePanel_contextMenu_header\">{space.name}</div>}\n            <IconizedContextMenuOptionList first>\n                <IconizedContextMenuOption\n                    icon={<HomeSolidIcon />}\n                    label={_t(\"space|context_menu|home\")}\n                    onClick={onHomeClick}\n                />\n                {inviteOption}\n                <IconizedContextMenuOption\n                    icon={<SearchIcon />}\n                    label={canAddRooms ? _t(\"space|context_menu|manage_and_explore\") : _t(\"space|context_menu|explore\")}\n                    onClick={onExploreRoomsClick}\n                />\n                <IconizedContextMenuOption\n                    icon={<PreferencesIcon />}\n                    label={_t(\"common|preferences\")}\n                    onClick={onPreferencesClick}\n                />\n                {devtoolsOption}\n                {settingsOption}\n                {leaveOption}\n                {newRoomSection}\n            </IconizedContextMenuOptionList>\n        </IconizedContextMenu>\n    );\n};\n\nexport default SpaceContextMenu;\n","/*\nCopyright 2024,2025 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactElement, type ReactNode, useContext, useId, useMemo, useRef, useState } from \"react\";\nimport classNames from \"classnames\";\nimport { type Room, EventType } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { sleep } from \"matrix-js-sdk/src/utils\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { CheckIcon, ErrorIcon, RestartIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t, _td } from \"../../../languageHandler\";\nimport BaseDialog from \"./BaseDialog\";\nimport Dropdown from \"../elements/Dropdown\";\nimport SearchBox from \"../../structures/SearchBox\";\nimport SpaceStore from \"../../../stores/spaces/SpaceStore\";\nimport RoomAvatar from \"../avatars/RoomAvatar\";\nimport { getDisplayAliasForRoom } from \"../../../Rooms\";\nimport AccessibleButton, { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport AutoHideScrollbar from \"../../structures/AutoHideScrollbar\";\nimport DMRoomMap from \"../../../utils/DMRoomMap\";\nimport { calculateRoomVia } from \"../../../utils/permalinks/Permalinks\";\nimport StyledCheckbox from \"../elements/StyledCheckbox\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { sortRooms } from \"../../../stores/room-list/algorithms/tag-sorting/RecentAlgorithm\";\nimport ProgressBar from \"../elements/ProgressBar\";\nimport DecoratedRoomAvatar from \"../avatars/DecoratedRoomAvatar\";\nimport QueryMatcher from \"../../../autocomplete/QueryMatcher\";\nimport LazyRenderList from \"../elements/LazyRenderList\";\nimport { useSettingValue } from \"../../../hooks/useSettings\";\nimport { filterBoolean } from \"../../../utils/arrays\";\nimport { type NonEmptyArray } from \"../../../@types/common\";\n\n// These values match CSS\nconst ROW_HEIGHT = 32 + 12;\nconst HEADER_HEIGHT = 15;\nconst GROUP_MARGIN = 24;\n\ninterface IProps {\n    space: Room;\n    onCreateRoomClick(ev: ButtonEvent): void;\n    onAddSubspaceClick(): void;\n    onFinished(added?: boolean): void;\n}\n\nexport const Entry: React.FC<{\n    room: Room;\n    checked: boolean;\n    onChange?(value: boolean): void;\n}> = ({ room, checked, onChange }) => {\n    const id = useId();\n    return (\n        <li id={id} className=\"mx_AddExistingToSpace_entry\" aria-label={room.name}>\n            {room?.isSpaceRoom() ? (\n                <RoomAvatar room={room} size=\"32px\" />\n            ) : (\n                <DecoratedRoomAvatar room={room} size=\"32px\" />\n            )}\n            <span className=\"mx_AddExistingToSpace_entry_name\">{room.name}</span>\n            <StyledCheckbox\n                aria-labelledby={id}\n                onChange={onChange ? (e) => onChange(e.currentTarget.checked) : undefined}\n                checked={checked}\n                disabled={!onChange}\n            />\n        </li>\n    );\n};\n\ntype OnChangeFn = (checked: boolean, room: Room) => void;\n\ntype Renderer = (\n    rooms: Room[],\n    selectedToAdd: Set<Room>,\n    scrollState: IScrollState,\n    onChange: undefined | OnChangeFn,\n) => ReactNode;\n\ninterface IAddExistingToSpaceProps {\n    space: Room;\n    footerPrompt?: ReactNode;\n    filterPlaceholder: string;\n    emptySelectionButton?: ReactNode;\n    onFinished(added: boolean): void;\n    roomsRenderer?: Renderer;\n    spacesRenderer?: Renderer;\n    dmsRenderer?: Renderer;\n}\n\ninterface IScrollState {\n    scrollTop: number;\n    height: number;\n}\n\nconst getScrollState = (\n    { scrollTop, height }: IScrollState,\n    numItems: number,\n    ...prevGroupSizes: number[]\n): IScrollState => {\n    let heightBefore = 0;\n    prevGroupSizes.forEach((size) => {\n        heightBefore += GROUP_MARGIN + HEADER_HEIGHT + size * ROW_HEIGHT;\n    });\n\n    const viewportTop = scrollTop;\n    const viewportBottom = viewportTop + height;\n    const listTop = heightBefore + HEADER_HEIGHT;\n    const listBottom = listTop + numItems * ROW_HEIGHT;\n    const top = Math.max(viewportTop, listTop);\n    const bottom = Math.min(viewportBottom, listBottom);\n    // the viewport height and scrollTop passed to the LazyRenderList\n    // is capped at the intersection with the real viewport, so lists\n    // out of view are passed height 0, so they won't render any items.\n    return {\n        scrollTop: Math.max(0, scrollTop - listTop),\n        height: Math.max(0, bottom - top),\n    };\n};\n\nexport const AddExistingToSpace: React.FC<IAddExistingToSpaceProps> = ({\n    space,\n    footerPrompt,\n    emptySelectionButton,\n    filterPlaceholder,\n    roomsRenderer,\n    dmsRenderer,\n    spacesRenderer,\n    onFinished,\n}) => {\n    const cli = useContext(MatrixClientContext);\n    const msc3946ProcessDynamicPredecessor = useSettingValue(\"feature_dynamic_room_predecessors\");\n    const visibleRooms = useMemo(\n        () =>\n            cli\n                ?.getVisibleRooms(msc3946ProcessDynamicPredecessor)\n                .filter((r) => r.getMyMembership() === KnownMembership.Join) ?? [],\n        [cli, msc3946ProcessDynamicPredecessor],\n    );\n\n    const scrollRef = useRef<AutoHideScrollbar<\"div\">>(null);\n    const [scrollState, setScrollState] = useState<IScrollState>({\n        // these are estimates which update as soon as it mounts\n        scrollTop: 0,\n        height: 600,\n    });\n\n    const [selectedToAdd, setSelectedToAdd] = useState(new Set<Room>());\n    const [progress, setProgress] = useState<number | null>(null);\n    const [error, setError] = useState(false);\n    const [query, setQuery] = useState(\"\");\n    const lcQuery = query.toLowerCase().trim();\n\n    const existingSubspacesSet = useMemo(() => new Set(SpaceStore.instance.getChildSpaces(space.roomId)), [space]);\n    const existingRoomsSet = useMemo(() => new Set(SpaceStore.instance.getChildRooms(space.roomId)), [space]);\n\n    const [spaces, rooms, dms] = useMemo(() => {\n        let rooms = visibleRooms;\n\n        if (lcQuery) {\n            const matcher = new QueryMatcher<Room>(visibleRooms, {\n                keys: [\"name\"],\n                funcs: [(r) => filterBoolean([r.getCanonicalAlias(), ...r.getAltAliases()])],\n                shouldMatchWordsOnly: false,\n            });\n\n            rooms = matcher.match(lcQuery);\n        }\n\n        const joinRule = space.getJoinRule();\n        return sortRooms(rooms).reduce<[spaces: Room[], rooms: Room[], dms: Room[]]>(\n            (arr, room) => {\n                if (room.isSpaceRoom()) {\n                    if (room !== space && !existingSubspacesSet.has(room)) {\n                        arr[0].push(room);\n                    }\n                } else if (!existingRoomsSet.has(room)) {\n                    if (!DMRoomMap.shared().getUserIdForRoomId(room.roomId)) {\n                        arr[1].push(room);\n                    } else if (joinRule !== \"public\") {\n                        // Only show DMs for non-public spaces as they make very little sense in spaces other than \"Just Me\" ones.\n                        arr[2].push(room);\n                    }\n                }\n                return arr;\n            },\n            [[], [], []],\n        );\n    }, [visibleRooms, space, lcQuery, existingRoomsSet, existingSubspacesSet]);\n\n    const addRooms = async (): Promise<void> => {\n        setError(false);\n        setProgress(0);\n\n        let error = false;\n\n        for (const room of selectedToAdd) {\n            const via = calculateRoomVia(room);\n            try {\n                await SpaceStore.instance.addRoomToSpace(space, room.roomId, via).catch(async (e): Promise<void> => {\n                    if (e.errcode === \"M_LIMIT_EXCEEDED\") {\n                        await sleep(e.data.retry_after_ms);\n                        await SpaceStore.instance.addRoomToSpace(space, room.roomId, via); // retry\n                        return;\n                    }\n\n                    throw e;\n                });\n                setProgress((i) => (i ?? 0) + 1);\n            } catch (e) {\n                logger.error(\"Failed to add rooms to space\", e);\n                error = true;\n                break;\n            }\n        }\n\n        if (!error) {\n            onFinished(true);\n        } else {\n            setError(error);\n        }\n    };\n\n    const busy = progress !== null;\n\n    let footer;\n    if (error) {\n        footer = (\n            <>\n                <ErrorIcon height=\"24px\" width=\"24px\" />\n\n                <span className=\"mx_AddExistingToSpaceDialog_error\">\n                    <div className=\"mx_AddExistingToSpaceDialog_errorHeading\">\n                        {_t(\"space|add_existing_room_space|error_heading\")}\n                    </div>\n                    <div className=\"mx_AddExistingToSpaceDialog_errorCaption\">{_t(\"action|try_again\")}</div>\n                </span>\n\n                <AccessibleButton className=\"mx_AddExistingToSpaceDialog_retryButton\" onClick={addRooms}>\n                    <RestartIcon />\n                    {_t(\"action|retry\")}\n                </AccessibleButton>\n            </>\n        );\n    } else if (busy) {\n        footer = (\n            <span>\n                <ProgressBar value={progress} max={selectedToAdd.size} />\n                <div className=\"mx_AddExistingToSpaceDialog_progressText\">\n                    {_t(\"space|add_existing_room_space|progress_text\", {\n                        count: selectedToAdd.size,\n                        progress,\n                    })}\n                </div>\n            </span>\n        );\n    } else {\n        let button = emptySelectionButton;\n        if (!button || selectedToAdd.size > 0) {\n            button = (\n                <AccessibleButton kind=\"primary\" disabled={selectedToAdd.size < 1} onClick={addRooms}>\n                    {_t(\"action|add\")}\n                </AccessibleButton>\n            );\n        }\n\n        footer = (\n            <>\n                <span>{footerPrompt}</span>\n\n                {button}\n            </>\n        );\n    }\n\n    const onChange =\n        !busy && !error\n            ? (checked: boolean, room: Room) => {\n                  if (checked) {\n                      selectedToAdd.add(room);\n                  } else {\n                      selectedToAdd.delete(room);\n                  }\n                  setSelectedToAdd(new Set(selectedToAdd));\n              }\n            : undefined;\n\n    // only count spaces when alone as they're shown on a separate modal all on their own\n    const numSpaces = spacesRenderer && !dmsRenderer && !roomsRenderer ? spaces.length : 0;\n    const numRooms = roomsRenderer ? rooms.length : 0;\n    const numDms = dmsRenderer ? dms.length : 0;\n\n    let noResults = true;\n    if (numSpaces > 0 || numRooms > 0 || numDms > 0) {\n        noResults = false;\n    }\n\n    const onScroll = (): void => {\n        const body = scrollRef.current?.containerRef.current;\n        if (!body) return;\n        setScrollState({\n            scrollTop: body.scrollTop,\n            height: body.clientHeight,\n        });\n    };\n\n    const wrappedRef = (body: HTMLDivElement | null): void => {\n        if (!body) return;\n        setScrollState({\n            scrollTop: body.scrollTop,\n            height: body.clientHeight,\n        });\n    };\n\n    const roomsScrollState = getScrollState(scrollState, numRooms);\n    const spacesScrollState = getScrollState(scrollState, numSpaces, numRooms);\n    const dmsScrollState = getScrollState(scrollState, numDms, numSpaces, numRooms);\n\n    return (\n        <div className=\"mx_AddExistingToSpace\">\n            <SearchBox\n                className=\"mx_textinput_icon mx_textinput_search\"\n                placeholder={filterPlaceholder}\n                onSearch={setQuery}\n                autoFocus={true}\n            />\n            <AutoHideScrollbar\n                className=\"mx_AddExistingToSpace_content\"\n                onScroll={onScroll}\n                wrappedRef={wrappedRef}\n                ref={scrollRef}\n            >\n                {rooms.length > 0 && roomsRenderer\n                    ? roomsRenderer(rooms, selectedToAdd, roomsScrollState, onChange)\n                    : undefined}\n\n                {spaces.length > 0 && spacesRenderer\n                    ? spacesRenderer(spaces, selectedToAdd, spacesScrollState, onChange)\n                    : null}\n\n                {dms.length > 0 && dmsRenderer ? dmsRenderer(dms, selectedToAdd, dmsScrollState, onChange) : null}\n\n                {noResults ? (\n                    <span className=\"mx_AddExistingToSpace_noResults\">{_t(\"common|no_results\")}</span>\n                ) : undefined}\n            </AutoHideScrollbar>\n\n            <div className=\"mx_AddExistingToSpace_footer\">{footer}</div>\n        </div>\n    );\n};\n\nconst defaultRendererFactory =\n    (title: TranslationKey): Renderer =>\n    (rooms, selectedToAdd, { scrollTop, height }, onChange) => (\n        <div className=\"mx_AddExistingToSpace_section\">\n            <h3>{_t(title)}</h3>\n            <LazyRenderList\n                element=\"ul\"\n                itemHeight={ROW_HEIGHT}\n                items={rooms}\n                scrollTop={scrollTop}\n                height={height}\n                renderItem={(room) => (\n                    <Entry\n                        key={room.roomId}\n                        room={room}\n                        checked={selectedToAdd.has(room)}\n                        onChange={\n                            onChange\n                                ? (checked: boolean) => {\n                                      onChange(checked, room);\n                                  }\n                                : undefined\n                        }\n                    />\n                )}\n            />\n        </div>\n    );\n\nexport const defaultRoomsRenderer = defaultRendererFactory(_td(\"common|rooms\"));\nexport const defaultSpacesRenderer = defaultRendererFactory(_td(\"common|spaces\"));\nexport const defaultDmsRenderer = defaultRendererFactory(_td(\"space|add_existing_room_space|dm_heading\"));\n\ninterface ISubspaceSelectorProps {\n    title: string;\n    space: Room;\n    value: Room;\n    onChange(space: Room): void;\n}\n\nexport const SubspaceSelector: React.FC<ISubspaceSelectorProps> = ({ title, space, value, onChange }) => {\n    const options = useMemo(() => {\n        return [\n            space,\n            ...SpaceStore.instance.getChildSpaces(space.roomId).filter((space) => {\n                return space.currentState.maySendStateEvent(EventType.SpaceChild, space.client.getSafeUserId());\n            }),\n        ];\n    }, [space]);\n\n    let body;\n    if (options.length > 1) {\n        body = (\n            <Dropdown\n                id=\"mx_SpaceSelectDropdown\"\n                className=\"mx_SpaceSelectDropdown\"\n                onOptionChange={(key: string) => {\n                    onChange(options.find((space) => space.roomId === key) || space);\n                }}\n                value={value.roomId}\n                label={_t(\"space|add_existing_room_space|space_dropdown_label\")}\n            >\n                {\n                    options.map((space) => {\n                        const classes = classNames({\n                            mx_SubspaceSelector_dropdownOptionActive: space === value,\n                        });\n                        return (\n                            <div key={space.roomId} className={classes}>\n                                <RoomAvatar room={space} size=\"24px\" />\n                                {space.name || getDisplayAliasForRoom(space) || space.roomId}\n                                {space === value ? <CheckIcon /> : null}\n                            </div>\n                        );\n                    }) as NonEmptyArray<ReactElement & { key: string }>\n                }\n            </Dropdown>\n        );\n    } else {\n        body = (\n            <div className=\"mx_SubspaceSelector_onlySpace\">\n                {space.name || getDisplayAliasForRoom(space) || space.roomId}\n            </div>\n        );\n    }\n\n    return (\n        <div className=\"mx_SubspaceSelector\">\n            <RoomAvatar room={value} size=\"40px\" />\n            <div>\n                <h1>{title}</h1>\n                {body}\n            </div>\n        </div>\n    );\n};\n\nconst AddExistingToSpaceDialog: React.FC<IProps> = ({ space, onCreateRoomClick, onAddSubspaceClick, onFinished }) => {\n    const [selectedSpace, setSelectedSpace] = useState(space);\n\n    return (\n        <BaseDialog\n            title={\n                <SubspaceSelector\n                    title={_t(\"space|add_existing_room_space|space_dropdown_title\")}\n                    space={space}\n                    value={selectedSpace}\n                    onChange={setSelectedSpace}\n                />\n            }\n            className=\"mx_AddExistingToSpaceDialog\"\n            contentId=\"mx_AddExistingToSpace\"\n            onFinished={onFinished}\n            fixedWidth={false}\n        >\n            <MatrixClientContext.Provider value={space.client}>\n                <AddExistingToSpace\n                    space={space}\n                    onFinished={onFinished}\n                    footerPrompt={\n                        <>\n                            <div>{_t(\"space|add_existing_room_space|create\")}</div>\n                            <AccessibleButton\n                                kind=\"link\"\n                                onClick={(ev: ButtonEvent) => {\n                                    onCreateRoomClick(ev);\n                                    onFinished();\n                                }}\n                            >\n                                {_t(\"space|add_existing_room_space|create_prompt\")}\n                            </AccessibleButton>\n                        </>\n                    }\n                    filterPlaceholder={_t(\"space|room_filter_placeholder\")}\n                    roomsRenderer={defaultRoomsRenderer}\n                    spacesRenderer={() => (\n                        <div className=\"mx_AddExistingToSpace_section\">\n                            <h3>{_t(\"common|spaces\")}</h3>\n                            <AccessibleButton\n                                kind=\"link\"\n                                onClick={() => {\n                                    onAddSubspaceClick();\n                                    onFinished();\n                                }}\n                            >\n                                {_t(\"space|add_existing_room_space|subspace_moved_note\")}\n                            </AccessibleButton>\n                        </div>\n                    )}\n                    dmsRenderer={defaultDmsRenderer}\n                />\n            </MatrixClientContext.Provider>\n        </BaseDialog>\n    );\n};\n\nexport default AddExistingToSpaceDialog;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\nCopyright 2019 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useCallback } from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { SettingLevel } from \"../../../settings/SettingLevel\";\nimport BaseDialog from \"./BaseDialog\";\n\nexport interface UnknownProfile {\n    userId: string;\n    errorText: string;\n}\n\nexport type UnknownProfiles = UnknownProfile[];\n\nexport interface AskInviteAnywayDialogProps {\n    unknownProfileUsers: UnknownProfiles;\n    onInviteAnyways: () => void;\n    onGiveUp: () => void;\n    onFinished: (success: boolean) => void;\n    description?: string;\n    inviteNeverWarnLabel?: string;\n    inviteLabel?: string;\n}\n\nexport default function AskInviteAnywayDialog({\n    onFinished,\n    onGiveUp,\n    onInviteAnyways,\n    unknownProfileUsers,\n    description: descriptionProp,\n    inviteNeverWarnLabel,\n    inviteLabel,\n}: AskInviteAnywayDialogProps): JSX.Element {\n    const onInviteClicked = useCallback((): void => {\n        onInviteAnyways();\n        onFinished(true);\n    }, [onInviteAnyways, onFinished]);\n\n    const onInviteNeverWarnClicked = useCallback((): void => {\n        SettingsStore.setValue(\"promptBeforeInviteUnknownUsers\", null, SettingLevel.ACCOUNT, false);\n        onInviteAnyways();\n        onFinished(true);\n    }, [onInviteAnyways, onFinished]);\n\n    const onGiveUpClicked = useCallback((): void => {\n        onGiveUp();\n        onFinished(false);\n    }, [onGiveUp, onFinished]);\n\n    const errorList = unknownProfileUsers.map((address) => (\n        <li key={address.userId}>\n            {address.userId}: {address.errorText}\n        </li>\n    ));\n\n    const description = descriptionProp ?? _t(\"invite|unable_find_profiles_description_default\");\n\n    return (\n        <BaseDialog\n            className=\"mx_RetryInvitesDialog\"\n            onFinished={onGiveUpClicked}\n            title={_t(\"invite|unable_find_profiles_title\")}\n            contentId=\"mx_Dialog_content\"\n        >\n            <div id=\"mx_Dialog_content\">\n                <p>{description}</p>\n                <ul>{errorList}</ul>\n            </div>\n\n            <div className=\"mx_Dialog_buttons\">\n                <button onClick={onGiveUpClicked}>{_t(\"action|close\")}</button>\n                <button onClick={onInviteNeverWarnClicked}>\n                    {inviteNeverWarnLabel ?? _t(\"invite|unable_find_profiles_invite_never_warn_label_default\")}\n                </button>\n                <button onClick={onInviteClicked} autoFocus={true}>\n                    {inviteLabel ?? _t(\"invite|unable_find_profiles_invite_label_default\")}\n                </button>\n            </div>\n        </BaseDialog>\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018, 2019 New Vector Ltd\nCopyright 2017 Vector Creations Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport FocusLock from \"react-focus-lock\";\nimport classNames from \"classnames\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { I18nContext } from \"@element-hq/web-shared-components\";\nimport { CloseIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { _t } from \"../../../languageHandler\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport Heading from \"../typography/Heading\";\nimport { PosthogScreenTracker, type ScreenName } from \"../../../PosthogTrackers\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\n\ninterface IProps {\n    /**\n     * Whether the dialog should have a 'close' button and a keyDown handler which\n     * will intercept 'Escape'.\n     *\n     * This should only be set to `false` if there is nothing the app can sensibly do if the\n     * dialog is cancelled, eg. \"We can't restore your session and\n     * the app cannot work\".\n     *\n     * Default: `true`.\n     */\n    \"hasCancel\"?: boolean;\n\n    /**\n     * Callback that will be called when the 'close' button is clicked or 'Escape' is pressed.\n     *\n     * Not used if `hasCancel` is false.\n     */\n    \"onFinished\"?: () => void;\n\n    // called when a key is pressed\n    \"onKeyDown\"?: (e: KeyboardEvent | React.KeyboardEvent) => void;\n\n    // CSS class to apply to dialog div\n    \"className\"?: string;\n\n    // if true, dialog container is 60% of the viewport width. Otherwise,\n    // the container will have no fixed size, allowing its contents to\n    // determine its size. Default: true.\n    \"fixedWidth\"?: boolean;\n\n    // To be displayed at the top of the dialog. Even above the title.\n    \"top\"?: React.ReactNode;\n\n    // Title for the dialog.\n    \"title\"?: React.ReactNode;\n    // Specific aria label to use, if not provided will set aria-labelledBy to mx_Dialog_title\n    \"aria-label\"?: string;\n\n    // Path to an icon to put in the header\n    \"headerImage\"?: string;\n\n    // children should be the content of the dialog\n    \"children\"?: React.ReactNode;\n\n    // Id of content element\n    // If provided, this is used to add a aria-describedby attribute\n    \"contentId\"?: string;\n\n    // optional additional class for the title element (basically anything that can be passed to classnames)\n    \"titleClass\"?: string | string[];\n\n    \"headerButton\"?: JSX.Element;\n\n    // optional Posthog ScreenName to supply during the lifetime of this dialog\n    \"screenName\"?: ScreenName;\n}\n\n/*\n * Basic container for modal dialogs.\n *\n * Includes a div for the title, and a keypress handler which cancels the\n * dialog on escape.\n */\nexport default class BaseDialog extends React.Component<IProps> {\n    private matrixClient: MatrixClient;\n\n    public static defaultProps: Partial<IProps> = {\n        hasCancel: true,\n        fixedWidth: true,\n    };\n\n    public constructor(props: IProps) {\n        super(props);\n\n        // XXX: The contract on MatrixClientContext says it is only available within a LoggedInView subtree,\n        // given that modals function outside the MatrixChat React tree this simulates that. We don't want to\n        // use safeGet as it throwing would mean we cannot use modals whilst the user isn't logged in.\n        // The longer term solution is to move our ModalManager into the React tree to inherit contexts properly.\n        this.matrixClient = MatrixClientPeg.get()!;\n    }\n\n    private onKeyDown = (e: KeyboardEvent | React.KeyboardEvent): void => {\n        this.props.onKeyDown?.(e);\n\n        const action = getKeyBindingsManager().getAccessibilityAction(e);\n        switch (action) {\n            case KeyBindingAction.Escape:\n                if (!this.props.hasCancel) break;\n\n                e.stopPropagation();\n                e.preventDefault();\n                this.props.onFinished?.();\n                break;\n        }\n    };\n\n    private onCancelClick = (): void => {\n        this.props.onFinished?.();\n    };\n\n    public render(): React.ReactNode {\n        let cancelButton;\n        if (this.props.hasCancel) {\n            cancelButton = (\n                <AccessibleButton\n                    onClick={this.onCancelClick}\n                    className=\"mx_Dialog_cancelButton\"\n                    title={_t(\"action|close\")}\n                    aria-label={_t(\"dialog_close_label\")}\n                    placement=\"bottom\"\n                >\n                    <CloseIcon />\n                </AccessibleButton>\n            );\n        }\n\n        let headerImage;\n        if (this.props.headerImage) {\n            headerImage = <img className=\"mx_Dialog_titleImage\" src={this.props.headerImage} alt=\"\" />;\n        }\n\n        const lockProps: Record<string, any> = {\n            \"onKeyDown\": this.onKeyDown,\n            \"role\": \"dialog\",\n            // Allow the dialog to be keyboard focusable\n            // So the escape key handling works in more cases (say you select the header)\n            \"tabIndex\": -1,\n            // This should point to a node describing the dialog.\n            // If we were about to completely follow this recommendation we'd need to\n            // make all the components relying on BaseDialog to be aware of it.\n            // So instead we will use the whole content as the description.\n            // Description comes first and if the content contains more text,\n            // AT users can skip its presentation.\n            \"aria-describedby\": this.props.contentId,\n        };\n\n        if (this.props[\"aria-label\"]) {\n            lockProps[\"aria-label\"] = this.props[\"aria-label\"];\n        } else {\n            lockProps[\"aria-labelledby\"] = \"mx_BaseDialog_title\";\n        }\n\n        return (\n            // XXX: We can't import ModuleAPI here because it causes a dependency cycle - hack and\n            // use the copy on the window object :(\n            <I18nContext.Provider value={window.mxModuleApi.i18n}>\n                <MatrixClientContext.Provider value={this.matrixClient}>\n                    {this.props.screenName && <PosthogScreenTracker screenName={this.props.screenName} />}\n                    <FocusLock\n                        returnFocus={true}\n                        lockProps={lockProps}\n                        className={classNames(this.props.className, {\n                            mx_Dialog_fixedWidth: this.props.fixedWidth,\n                        })}\n                    >\n                        {this.props.top}\n                        <div\n                            className={classNames(\"mx_Dialog_header\", {\n                                mx_Dialog_headerWithButton: !!this.props.headerButton,\n                            })}\n                        >\n                            {!!(this.props.title || headerImage) && (\n                                <Heading\n                                    size=\"3\"\n                                    as=\"h1\"\n                                    className={classNames(\"mx_Dialog_title\", this.props.titleClass)}\n                                    id=\"mx_BaseDialog_title\"\n                                >\n                                    {headerImage}\n                                    {this.props.title}\n                                </Heading>\n                            )}\n                            {this.props.headerButton}\n                        </div>\n                        {this.props.children}\n                        {cancelButton}\n                    </FocusLock>\n                </MatrixClientContext.Provider>\n            </I18nContext.Provider>\n        );\n    }\n}\n","/*\nCopyright 2026 Element Creations Ltd.\nCopyright 2024 New Vector Ltd.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2017 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode } from \"react\";\nimport { Link, Text } from \"@vector-im/compound-web\";\n\nimport SdkConfig from \"../../../SdkConfig\";\nimport Modal from \"../../../Modal\";\nimport { _t } from \"../../../languageHandler\";\nimport sendBugReport, { downloadBugReport, RageshakeError } from \"../../../rageshake/submit-rageshake\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport QuestionDialog from \"./QuestionDialog\";\nimport BaseDialog from \"./BaseDialog\";\nimport Field from \"../elements/Field\";\nimport Spinner from \"../elements/Spinner\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport { sendSentryReport } from \"../../../sentry\";\nimport defaultDispatcher from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { getBrowserSupport } from \"../../../SupportedBrowser\";\nimport { BugReportEndpointURLLocal } from \"../../../IConfigOptions\";\n\nexport interface BugReportDialogProps {\n    onFinished: (success: boolean) => void;\n    initialText?: string;\n    label?: string;\n    error?: unknown;\n}\n\ninterface IState {\n    sendLogs: boolean;\n    busy: boolean;\n    err: ReactNode | null;\n    issueUrl: string;\n    text: string;\n    progress: string | null;\n    downloadBusy: boolean;\n    downloadProgress: string | null;\n}\n\nexport default class BugReportDialog extends React.Component<BugReportDialogProps, IState> {\n    private unmounted: boolean;\n    private issueRef: React.RefObject<Field | null>;\n    private readonly isLocalOnly: boolean;\n\n    public constructor(props: BugReportDialogProps) {\n        super(props);\n\n        this.state = {\n            sendLogs: true,\n            busy: false,\n            err: null,\n            issueUrl: \"\",\n            text: props.initialText || \"\",\n            progress: null,\n            downloadBusy: false,\n            downloadProgress: null,\n        };\n\n        this.unmounted = false;\n        this.issueRef = React.createRef();\n        // This config is static at runtime, but may change during tests.\n        this.isLocalOnly = SdkConfig.get().bug_report_endpoint_url === BugReportEndpointURLLocal;\n    }\n\n    public componentDidMount(): void {\n        this.unmounted = false;\n        this.issueRef.current?.focus();\n\n        // Get all of the extra info dumped to the console when someone is about\n        // to send debug logs. Since this is a fire and forget action, we do\n        // this when the bug report dialog is opened instead of when we submit\n        // logs because we have no signal to know when all of the various\n        // components have finished logging. Someone could potentially send logs\n        // before we fully dump everything but it's probably unlikely.\n        defaultDispatcher.dispatch({\n            action: Action.DumpDebugLogs,\n        });\n    }\n\n    public componentWillUnmount(): void {\n        this.unmounted = true;\n    }\n\n    private onCancel = (): void => {\n        this.props.onFinished(false);\n    };\n\n    private getErrorText(error: Error | RageshakeError): ReactNode {\n        if (error instanceof RageshakeError) {\n            let errorText;\n            switch (error.errorcode) {\n                case \"DISALLOWED_APP\":\n                    errorText = _t(\"bug_reporting|failed_send_logs_causes|disallowed_app\");\n                    break;\n                case \"REJECTED_BAD_VERSION\":\n                    errorText = _t(\"bug_reporting|failed_send_logs_causes|rejected_version\");\n                    break;\n                case \"REJECTED_UNEXPECTED_RECOVERY_KEY\":\n                    errorText = _t(\"bug_reporting|failed_send_logs_causes|rejected_recovery_key\");\n                    break;\n                default:\n                    if (error.errorcode?.startsWith(\"REJECTED\")) {\n                        errorText = _t(\"bug_reporting|failed_send_logs_causes|rejected_generic\");\n                    } else {\n                        errorText = _t(\"bug_reporting|failed_send_logs_causes|server_unknown_error\");\n                    }\n                    break;\n            }\n            return (\n                <>\n                    <p>{errorText}</p>\n                    {error.policyURL && (\n                        <Link size=\"medium\" target=\"_blank\" href={error.policyURL}>\n                            {_t(\"action|learn_more\")}\n                        </Link>\n                    )}\n                </>\n            );\n        } else {\n            return <p>{_t(\"bug_reporting|failed_send_logs_causes|unknown_error\")}</p>;\n        }\n    }\n\n    private onSubmit = (): void => {\n        if ((!this.state.text || !this.state.text.trim()) && (!this.state.issueUrl || !this.state.issueUrl.trim())) {\n            this.setState({\n                err: _t(\"bug_reporting|error_empty\"),\n            });\n            return;\n        }\n\n        const userText =\n            (this.state.text.length > 0 ? this.state.text + \"\\n\\n\" : \"\") +\n            \"Issue: \" +\n            (this.state.issueUrl.length > 0 ? this.state.issueUrl : \"No issue link given\");\n\n        this.setState({ busy: true, progress: null, err: null });\n        this.sendProgressCallback(_t(\"bug_reporting|preparing_logs\"));\n\n        if (this.isLocalOnly) {\n            // Shouldn't reach here, but throw in case we do.\n            this.setState({\n                err: _t(\"bug_reporting|failed_send_logs_causes|unknown_error\"),\n            });\n            return;\n        }\n\n        sendBugReport(SdkConfig.get().bug_report_endpoint_url, {\n            userText,\n            sendLogs: true,\n            progressCallback: this.sendProgressCallback,\n            labels: this.props.label ? [this.props.label] : [],\n        }).then(\n            () => {\n                if (!this.unmounted) {\n                    this.props.onFinished(false);\n                    Modal.createDialog(QuestionDialog, {\n                        title: _t(\"bug_reporting|logs_sent\"),\n                        description: _t(\"bug_reporting|thank_you\"),\n                        hasCancelButton: false,\n                    });\n                }\n            },\n            (err) => {\n                if (!this.unmounted) {\n                    this.setState({\n                        busy: false,\n                        progress: null,\n                        err: this.getErrorText(err),\n                    });\n                }\n            },\n        );\n\n        sendSentryReport(this.state.text, this.state.issueUrl, this.props.error);\n    };\n\n    private onDownload = async (): Promise<void> => {\n        this.setState({ downloadBusy: true });\n        this.downloadProgressCallback(_t(\"bug_reporting|preparing_download\"));\n\n        try {\n            await downloadBugReport({\n                sendLogs: true,\n                progressCallback: this.downloadProgressCallback,\n                labels: this.props.label ? [this.props.label] : [],\n            });\n\n            this.setState({\n                downloadBusy: false,\n                downloadProgress: null,\n            });\n        } catch (err) {\n            if (!this.unmounted) {\n                this.setState({\n                    downloadBusy: false,\n                    downloadProgress:\n                        _t(\"bug_reporting|failed_download_logs\") + `${err instanceof Error ? err.message : \"\"}`,\n                });\n            }\n        }\n    };\n\n    private onTextChange = (ev: React.FormEvent<HTMLTextAreaElement>): void => {\n        this.setState({ text: ev.currentTarget.value });\n    };\n\n    private onIssueUrlChange = (ev: React.FormEvent<HTMLInputElement>): void => {\n        this.setState({ issueUrl: ev.currentTarget.value });\n    };\n\n    private sendProgressCallback = (progress: string): void => {\n        if (this.unmounted) {\n            return;\n        }\n        this.setState({ progress });\n    };\n\n    private downloadProgressCallback = (downloadProgress: string): void => {\n        if (this.unmounted) {\n            return;\n        }\n        this.setState({ downloadProgress });\n    };\n\n    public render(): React.ReactNode {\n        let error: JSX.Element | undefined;\n        if (this.state.err) {\n            error = <div className=\"error\">{this.state.err}</div>;\n        }\n\n        let progress: JSX.Element | undefined;\n        if (this.state.busy) {\n            progress = (\n                <div className=\"progress\">\n                    <Spinner />\n                    {this.state.progress} ...\n                </div>\n            );\n        }\n\n        let warning: JSX.Element | undefined;\n        if (\n            (window.Modernizr && Object.values(window.Modernizr).some((support) => support === false)) ||\n            !getBrowserSupport()\n        ) {\n            warning = <Text weight=\"semibold\">{_t(\"bug_reporting|unsupported_browser\")}</Text>;\n        }\n\n        return (\n            <BaseDialog\n                className=\"mx_BugReportDialog\"\n                onFinished={this.onCancel}\n                title={this.isLocalOnly ? _t(\"bug_reporting|download_logs\") : _t(\"bug_reporting|submit_debug_logs\")}\n                contentId=\"mx_Dialog_content\"\n            >\n                <div className=\"mx_Dialog_content\" id=\"mx_Dialog_content\">\n                    {warning}\n                    <Text>{_t(\"bug_reporting|description\")}</Text>\n                    {this.isLocalOnly ? (\n                        <>{this.state.downloadProgress && <span>{this.state.downloadProgress} ...</span>}</>\n                    ) : (\n                        <>\n                            <Text weight=\"semibold\">\n                                {_t(\n                                    \"bug_reporting|before_submitting\",\n                                    {},\n                                    {\n                                        a: (sub) => (\n                                            <Link target=\"_blank\" href={SdkConfig.get().feedback.new_issue_url}>\n                                                {sub}\n                                            </Link>\n                                        ),\n                                    },\n                                )}\n                            </Text>\n\n                            <div className=\"mx_BugReportDialog_download\">\n                                <AccessibleButton\n                                    onClick={this.onDownload}\n                                    kind=\"link\"\n                                    disabled={this.state.downloadBusy}\n                                >\n                                    {_t(\"bug_reporting|download_logs\")}\n                                </AccessibleButton>\n                                {this.state.downloadProgress && <span>{this.state.downloadProgress} ...</span>}\n                            </div>\n\n                            <Field\n                                type=\"text\"\n                                className=\"mx_BugReportDialog_field_input\"\n                                label={_t(\"bug_reporting|github_issue\")}\n                                onChange={this.onIssueUrlChange}\n                                value={this.state.issueUrl}\n                                placeholder=\"https://github.com/vector-im/element-web/issues/...\"\n                                ref={this.issueRef}\n                            />\n                            <Field\n                                className=\"mx_BugReportDialog_field_input\"\n                                element=\"textarea\"\n                                label={_t(\"bug_reporting|textarea_label\")}\n                                rows={5}\n                                onChange={this.onTextChange}\n                                value={this.state.text}\n                                placeholder={_t(\"bug_reporting|additional_context\")}\n                            />\n                            {progress}\n                            {error}\n                        </>\n                    )}\n                </div>\n                <DialogButtons\n                    primaryButton={this.isLocalOnly ? _t(\"bug_reporting|download_logs\") : _t(\"bug_reporting|send_logs\")}\n                    onPrimaryButtonClick={this.isLocalOnly ? this.onDownload : this.onSubmit}\n                    focus={true}\n                    onCancel={this.onCancel}\n                    disabled={this.isLocalOnly ? this.state.downloadBusy : this.state.busy}\n                />\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017 Vector Creations Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type IRedactOpts, type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport React from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport Modal from \"../../../Modal\";\nimport ErrorDialog from \"./ErrorDialog\";\nimport TextInputDialog from \"./TextInputDialog\";\n\ninterface IProps {\n    event: MatrixEvent;\n    onFinished(success?: false, reason?: void): void;\n    onFinished(success: true, reason?: string): void;\n}\n\n/*\n * A dialog for confirming a redaction.\n */\nexport default class ConfirmRedactDialog extends React.Component<IProps> {\n    public render(): React.ReactNode {\n        let description = _t(\"redact|confirm_description\");\n        if (this.props.event.isState()) {\n            description += \" \" + _t(\"redact|confirm_description_state\");\n        }\n\n        return (\n            <TextInputDialog\n                onFinished={this.props.onFinished}\n                title={_t(\"redact|confirm_button\")}\n                description={description}\n                placeholder={_t(\"redact|reason_label\")}\n                focus\n                button={_t(\"action|remove\")}\n            />\n        );\n    }\n}\n\nexport function createRedactEventDialog({\n    mxEvent,\n    onCloseDialog = () => {},\n}: {\n    mxEvent: MatrixEvent;\n    onCloseDialog?: () => void;\n}): void {\n    const eventId = mxEvent.getId();\n\n    if (!eventId) throw new Error(\"cannot redact event without ID\");\n\n    const roomId = mxEvent.getRoomId();\n\n    if (!roomId) throw new Error(`cannot redact event ${mxEvent.getId()} without room ID`);\n    const { finished } = Modal.createDialog(ConfirmRedactDialog, { event: mxEvent }, \"mx_Dialog_confirmredact\");\n\n    finished.then(async ([proceed, reason]) => {\n        if (!proceed) return;\n\n        const cli = MatrixClientPeg.safeGet();\n        const withRelTypes: Pick<IRedactOpts, \"with_rel_types\"> = {};\n\n        try {\n            onCloseDialog?.();\n            await cli.redactEvent(roomId, eventId, undefined, {\n                ...(reason ? { reason } : {}),\n                ...withRelTypes,\n            });\n        } catch (e: any) {\n            const code = e.errcode || e.statusCode;\n            // only show the dialog if failing for something other than a network error\n            // (e.g. no errcode or statusCode) as in that case the redactions end up in the\n            // detached queue and we show the room status bar to allow retry\n            if (typeof code !== \"undefined\") {\n                // display error message stating you couldn't delete this.\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"common|error\"),\n                    description: _t(\"redact|error\", { code }),\n                });\n            }\n        }\n    });\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017 Vector Creations Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEvent, type FormEvent, type ReactNode } from \"react\";\nimport { type RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport classNames from \"classnames\";\n\nimport { _t } from \"../../../languageHandler\";\nimport MemberAvatar from \"../avatars/MemberAvatar\";\nimport BaseDialog from \"./BaseDialog\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport Field from \"../elements/Field\";\nimport UserIdentifierCustomisations from \"../../../customisations/UserIdentifier\";\n\ninterface IProps {\n    // matrix-js-sdk (room) member object.\n    member: RoomMember;\n    action: string; // eg. 'Ban'\n    title: string; // eg. 'Ban this user?'\n\n    // Whether to display a text field for a reason\n    // If true, the second argument to onFinished will\n    // be the string entered.\n    askReason?: boolean;\n    danger?: boolean;\n    children?: ReactNode;\n    className?: string;\n    roomId?: string;\n    onFinished: (success?: boolean, reason?: string) => void;\n}\n\ninterface IState {\n    reason: string;\n}\n\n/*\n * A dialog for confirming an operation on another user.\n * Takes a user ID and a verb, displays the target user prominently\n * such that it should be easy to confirm that the operation is being\n * performed on the right person, and displays the operation prominently\n * to make it obvious what is going to happen.\n * Also tweaks the style for 'dangerous' actions (albeit only with colour)\n */\nexport default class ConfirmUserActionDialog extends React.Component<IProps, IState> {\n    public static defaultProps: Partial<IProps> = {\n        danger: false,\n        askReason: false,\n    };\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            reason: \"\",\n        };\n    }\n\n    private onOk = (ev: FormEvent): void => {\n        ev.preventDefault();\n        this.props.onFinished(true, this.state.reason);\n    };\n\n    private onCancel = (): void => {\n        this.props.onFinished(false);\n    };\n\n    private onReasonChange = (ev: ChangeEvent<HTMLInputElement>): void => {\n        this.setState({\n            reason: ev.target.value,\n        });\n    };\n\n    public render(): React.ReactNode {\n        const confirmButtonClass = this.props.danger ? \"danger\" : \"\";\n\n        let reasonBox;\n        if (this.props.askReason) {\n            reasonBox = (\n                <form onSubmit={this.onOk}>\n                    <Field\n                        type=\"text\"\n                        onChange={this.onReasonChange}\n                        value={this.state.reason}\n                        className=\"mx_ConfirmUserActionDialog_reasonField\"\n                        label={_t(\"room_settings|permissions|ban_reason\")}\n                        autoFocus={true}\n                    />\n                </form>\n            );\n        }\n\n        const avatar = <MemberAvatar member={this.props.member} size=\"48px\" />;\n        const name = this.props.member.name;\n        const userId = this.props.member.userId;\n\n        const displayUserIdentifier = UserIdentifierCustomisations.getDisplayUserIdentifier(userId, {\n            roomId: this.props.roomId,\n            withDisplayName: true,\n        });\n\n        return (\n            <BaseDialog\n                className={classNames(\"mx_ConfirmUserActionDialog\", this.props.className)}\n                onFinished={this.props.onFinished}\n                title={this.props.title}\n                contentId=\"mx_Dialog_content\"\n            >\n                <div id=\"mx_Dialog_content\" className=\"mx_Dialog_content\">\n                    <div className=\"mx_ConfirmUserActionDialog_user\">\n                        <div className=\"mx_ConfirmUserActionDialog_avatar\">{avatar}</div>\n                        <div className=\"mx_ConfirmUserActionDialog_name\">{name}</div>\n                        <div className=\"mx_ConfirmUserActionDialog_userId\">{displayUserIdentifier}</div>\n                    </div>\n\n                    {reasonBox}\n                    {this.props.children}\n                </div>\n                <DialogButtons\n                    primaryButton={this.props.action}\n                    onPrimaryButtonClick={this.onOk}\n                    primaryButtonClass={confirmButtonClass}\n                    focus={!this.props.askReason}\n                    onCancel={this.onCancel}\n                />\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\nCopyright 2017 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, {\n    type JSX,\n    type ChangeEvent,\n    createRef,\n    type KeyboardEvent,\n    type SyntheticEvent,\n    type ChangeEventHandler,\n} from \"react\";\nimport { type Room, RoomType, JoinRule, Preset, Visibility } from \"matrix-js-sdk/src/matrix\";\nimport { Form, SettingsToggleInput } from \"@vector-im/compound-web\";\n\nimport SdkConfig from \"../../../SdkConfig\";\nimport withValidation, { type IFieldState, type IValidationResult } from \"../elements/Validation\";\nimport { _t } from \"../../../languageHandler\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { checkUserIsAllowedToChangeEncryption, type IOpts } from \"../../../createRoom\";\nimport Field from \"../elements/Field\";\nimport RoomAliasField from \"../elements/RoomAliasField\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport BaseDialog from \"../dialogs/BaseDialog\";\nimport JoinRuleDropdown from \"../elements/JoinRuleDropdown\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { privateShouldBeEncrypted } from \"../../../utils/rooms\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { UIFeature } from \"../../../settings/UIFeature\";\n\ninterface IProps {\n    type?: RoomType;\n    defaultPublic?: boolean;\n    defaultName?: string;\n    parentSpace?: Room;\n    defaultEncrypted?: boolean;\n    defaultStateEncrypted?: boolean;\n    onFinished(proceed?: false): void;\n    onFinished(proceed: true, opts: IOpts): void;\n}\n\ninterface IState {\n    /**\n     * The selected room join rule.\n     */\n    joinRule: JoinRule;\n    /**\n     * Indicates whether the created room should have public visibility (ie, it should be\n     * shown in the public room list). Only applicable if `joinRule` == `JoinRule.Knock`.\n     */\n    isPublicKnockRoom: boolean;\n    /**\n     * Indicates whether end-to-end encryption is enabled for the room.\n     */\n    isEncrypted: boolean;\n    /**\n     * Indicates whether end-to-end state encryption is enabled for this room.\n     * See MSC4362. Available if feature_msc4362_encrypted_state_events is enabled.\n     */\n    isStateEncrypted: boolean;\n    /**\n     * The room name.\n     */\n    name: string;\n    /**\n     * The room topic.\n     */\n    topic: string;\n    /**\n     * The room alias.\n     */\n    alias: string;\n    /**\n     * Indicates whether the details section is open.\n     */\n    detailsOpen: boolean;\n    /**\n     * Indicates whether federation is disabled for the room.\n     */\n    noFederate: boolean;\n    /**\n     * Indicates whether the room name is valid.\n     */\n    nameIsValid: boolean;\n    /**\n     * Indicates whether the user can change encryption settings for the room.\n     */\n    canChangeEncryption: boolean;\n}\n\nexport default class CreateRoomDialog extends React.Component<IProps, IState> {\n    private readonly askToJoinEnabled: boolean;\n    private readonly advancedSettingsEnabled: boolean;\n    private readonly allowCreatingPublicRooms: boolean;\n    private readonly supportsRestricted: boolean;\n    private nameField = createRef<Field>();\n    private aliasField = createRef<RoomAliasField>();\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.askToJoinEnabled = SettingsStore.getValue(\"feature_ask_to_join\");\n        this.advancedSettingsEnabled = SettingsStore.getValue(UIFeature.AdvancedSettings);\n        this.allowCreatingPublicRooms = SettingsStore.getValue(UIFeature.AllowCreatingPublicRooms);\n\n        this.supportsRestricted = !!this.props.parentSpace;\n        const defaultPublic = this.allowCreatingPublicRooms && this.props.defaultPublic;\n\n        let joinRule = JoinRule.Invite;\n        if (defaultPublic) {\n            joinRule = JoinRule.Public;\n        } else if (this.supportsRestricted) {\n            joinRule = JoinRule.Restricted;\n        }\n\n        const cli = MatrixClientPeg.safeGet();\n        this.state = {\n            isPublicKnockRoom: defaultPublic || false,\n            isEncrypted: this.props.defaultEncrypted ?? privateShouldBeEncrypted(cli),\n            isStateEncrypted: this.props.defaultStateEncrypted ?? false,\n            joinRule,\n            name: this.props.defaultName || \"\",\n            topic: \"\",\n            alias: \"\",\n            detailsOpen: false,\n            noFederate: SdkConfig.get().default_federate === false,\n            nameIsValid: false,\n            canChangeEncryption: false,\n        };\n    }\n\n    private roomCreateOptions(): IOpts {\n        const opts: IOpts = {};\n        const createOpts: IOpts[\"createOpts\"] = (opts.createOpts = {});\n        opts.roomType = this.props.type;\n        opts.name = this.state.name;\n\n        if (this.state.joinRule === JoinRule.Public) {\n            createOpts.visibility = Visibility.Public;\n            createOpts.preset = Preset.PublicChat;\n            opts.guestAccess = false;\n            const { alias } = this.state;\n            createOpts.room_alias_name = alias.substring(1, alias.indexOf(\":\"));\n        } else {\n            const encryptedStateFeature = SettingsStore.getValue(\"feature_msc4362_encrypted_state_events\", null, false);\n\n            opts.encryption = this.state.isEncrypted;\n            opts.stateEncryption = encryptedStateFeature && this.state.isStateEncrypted;\n        }\n\n        if (this.state.topic) {\n            opts.topic = this.state.topic;\n        }\n        if (this.state.noFederate) {\n            createOpts.creation_content = { \"m.federate\": false };\n        }\n\n        opts.parentSpace = this.props.parentSpace;\n        if (this.props.parentSpace && this.state.joinRule === JoinRule.Restricted) {\n            opts.joinRule = JoinRule.Restricted;\n        }\n\n        if (this.state.joinRule === JoinRule.Knock) {\n            opts.joinRule = JoinRule.Knock;\n            createOpts.visibility = this.state.isPublicKnockRoom ? Visibility.Public : Visibility.Private;\n        }\n\n        return opts;\n    }\n\n    public componentDidMount(): void {\n        const cli = MatrixClientPeg.safeGet();\n        checkUserIsAllowedToChangeEncryption(cli, Preset.PrivateChat).then(({ allowChange, forcedValue }) =>\n            this.setState((state) => ({\n                canChangeEncryption: allowChange,\n                // override with forcedValue if it is set\n                isEncrypted: forcedValue ?? state.isEncrypted,\n            })),\n        );\n\n        // move focus to first field when showing dialog\n        this.nameField.current?.focus();\n    }\n\n    private onKeyDown = (event: KeyboardEvent): void => {\n        const action = getKeyBindingsManager().getAccessibilityAction(event);\n        switch (action) {\n            case KeyBindingAction.Enter:\n                this.onOk();\n                event.preventDefault();\n                event.stopPropagation();\n                break;\n        }\n    };\n\n    private onOk = async (): Promise<void> => {\n        if (!this.nameField.current) return;\n        const activeElement = document.activeElement as HTMLElement;\n        activeElement?.blur();\n        await this.nameField.current.validate({ allowEmpty: false });\n        if (this.aliasField.current) {\n            await this.aliasField.current.validate({ allowEmpty: false });\n        }\n        // Validation and state updates are async, so we need to wait for them to complete\n        // first. Queue a `setState` callback and wait for it to resolve.\n        await new Promise<void>((resolve) => this.setState({}, resolve));\n        if (this.state.nameIsValid && (!this.aliasField.current || this.aliasField.current.isValid)) {\n            this.props.onFinished(true, this.roomCreateOptions());\n        } else {\n            let field: RoomAliasField | Field | null = null;\n            if (!this.state.nameIsValid) {\n                field = this.nameField.current;\n            } else if (this.aliasField.current && !this.aliasField.current.isValid) {\n                field = this.aliasField.current;\n            }\n            if (field) {\n                field.focus();\n                await field.validate({ allowEmpty: false, focused: true });\n            }\n        }\n    };\n\n    private onCancel = (): void => {\n        this.props.onFinished(false);\n    };\n\n    private onNameChange = (ev: ChangeEvent<HTMLInputElement>): void => {\n        this.setState({ name: ev.target.value });\n    };\n\n    private onTopicChange = (ev: ChangeEvent<HTMLInputElement>): void => {\n        this.setState({ topic: ev.target.value });\n    };\n\n    private onJoinRuleChange = (joinRule: JoinRule): void => {\n        this.setState({ joinRule });\n    };\n\n    private onEncryptedChange: ChangeEventHandler<HTMLInputElement> = (evt): void => {\n        this.setState({ isEncrypted: evt.target.checked });\n    };\n\n    private onStateEncryptedChange: ChangeEventHandler<HTMLInputElement> = (evt): void => {\n        this.setState({ isStateEncrypted: evt.target.checked });\n    };\n\n    private onAliasChange = (alias: string): void => {\n        this.setState({ alias });\n    };\n\n    private onDetailsToggled = (ev: SyntheticEvent<HTMLDetailsElement>): void => {\n        this.setState({ detailsOpen: (ev.target as HTMLDetailsElement).open });\n    };\n\n    private onNoFederateChange: ChangeEventHandler<HTMLInputElement> = (evt): void => {\n        this.setState({ noFederate: evt.target.checked });\n    };\n\n    private onNameValidate = async (fieldState: IFieldState): Promise<IValidationResult> => {\n        const result = await CreateRoomDialog.validateRoomName(fieldState);\n        this.setState({ nameIsValid: !!result.valid });\n        return result;\n    };\n\n    private onIsPublicKnockRoomChange: ChangeEventHandler<HTMLInputElement> = (evt): void => {\n        this.setState({ isPublicKnockRoom: evt.target.checked });\n    };\n\n    private static validateRoomName = withValidation({\n        rules: [\n            {\n                key: \"required\",\n                test: async ({ value }) => !!value,\n                invalid: () => _t(\"create_room|name_validation_required\"),\n            },\n        ],\n    });\n\n    public render(): React.ReactNode {\n        const isVideoRoom = this.props.type === RoomType.ElementVideo || this.props.type === RoomType.UnstableCall;\n\n        let aliasField: JSX.Element | undefined;\n        if (this.state.joinRule === JoinRule.Public) {\n            const domain = MatrixClientPeg.safeGet().getDomain()!;\n            aliasField = (\n                <div className=\"mx_CreateRoomDialog_aliasContainer\">\n                    <RoomAliasField\n                        ref={this.aliasField}\n                        onChange={this.onAliasChange}\n                        domain={domain}\n                        value={this.state.alias}\n                    />\n                </div>\n            );\n        }\n\n        let publicPrivateLabel: JSX.Element | undefined;\n        if (this.state.joinRule === JoinRule.Restricted) {\n            publicPrivateLabel = (\n                <p>\n                    {_t(\n                        \"create_room|join_rule_restricted_label\",\n                        {},\n                        {\n                            SpaceName: () => (\n                                <strong>{this.props.parentSpace?.name ?? _t(\"common|unnamed_space\")}</strong>\n                            ),\n                        },\n                    )}\n                    &nbsp;\n                    {_t(\"create_room|join_rule_change_notice\")}\n                </p>\n            );\n        } else if (this.state.joinRule === JoinRule.Public && this.props.parentSpace) {\n            publicPrivateLabel = (\n                <p>\n                    {_t(\n                        \"create_room|join_rule_public_parent_space_label\",\n                        {},\n                        {\n                            SpaceName: () => (\n                                <strong>{this.props.parentSpace?.name ?? _t(\"common|unnamed_space\")}</strong>\n                            ),\n                        },\n                    )}\n                    &nbsp;\n                    {_t(\"create_room|join_rule_change_notice\")}\n                </p>\n            );\n        } else if (this.state.joinRule === JoinRule.Public) {\n            publicPrivateLabel = (\n                <p>\n                    {_t(\"create_room|join_rule_public_label\")}\n                    &nbsp;\n                    {_t(\"create_room|join_rule_change_notice\")}\n                </p>\n            );\n        } else if (this.state.joinRule === JoinRule.Invite) {\n            publicPrivateLabel = (\n                <p>\n                    {_t(\"create_room|join_rule_invite_label\")}\n                    &nbsp;\n                    {_t(\"create_room|join_rule_change_notice\")}\n                </p>\n            );\n        } else if (this.state.joinRule === JoinRule.Knock) {\n            publicPrivateLabel = <p>{_t(\"create_room|join_rule_knock_label\")}</p>;\n        }\n\n        let visibilitySection: JSX.Element | undefined;\n        if (this.state.joinRule === JoinRule.Knock) {\n            visibilitySection = (\n                <SettingsToggleInput\n                    name=\"publish-room\"\n                    className=\"mx_CreateRoomDialog_labelledCheckbox\"\n                    label={_t(\"room_settings|security|publish_room\")}\n                    onChange={this.onIsPublicKnockRoomChange}\n                    checked={this.state.isPublicKnockRoom}\n                />\n            );\n        }\n\n        let e2eeSection: JSX.Element | undefined;\n        if (this.state.joinRule !== JoinRule.Public) {\n            let microcopy: string;\n            if (privateShouldBeEncrypted(MatrixClientPeg.safeGet())) {\n                if (this.state.canChangeEncryption) {\n                    microcopy = isVideoRoom\n                        ? _t(\"create_room|encrypted_video_room_warning\")\n                        : _t(\"create_room|encrypted_warning\");\n                } else {\n                    microcopy = _t(\"create_room|encryption_forced\");\n                }\n            } else {\n                microcopy = _t(\"settings|security|e2ee_default_disabled_warning\");\n            }\n            e2eeSection = (\n                <SettingsToggleInput\n                    name=\"encryption-toggle\"\n                    label={_t(\"create_room|encryption_label\")}\n                    onChange={this.onEncryptedChange}\n                    checked={this.state.isEncrypted}\n                    disabled={!this.state.canChangeEncryption}\n                    helpMessage={microcopy}\n                />\n            );\n        }\n\n        let e2eeStateSection: JSX.Element | undefined;\n        if (\n            SettingsStore.getValue(\"feature_msc4362_encrypted_state_events\", null, false) &&\n            this.state.joinRule !== JoinRule.Public\n        ) {\n            let microcopy: string;\n            if (!this.state.canChangeEncryption) {\n                microcopy = _t(\"create_room|encryption_forced\");\n            } else {\n                microcopy = _t(\"create_room|state_encrypted_warning\");\n            }\n            e2eeStateSection = (\n                <SettingsToggleInput\n                    name=\"state-encryption-toggle\"\n                    label={_t(\"create_room|state_encryption_label\")}\n                    onChange={this.onStateEncryptedChange}\n                    checked={this.state.isStateEncrypted}\n                    disabled={!this.state.canChangeEncryption}\n                    helpMessage={microcopy}\n                />\n            );\n        }\n\n        let federateLabel = _t(\"create_room|unfederated_label_default_off\");\n        if (SdkConfig.get().default_federate === false) {\n            // We only change the label if the default setting is different to avoid jarring text changes to the\n            // user. They will have read the implications of turning this off/on, so no need to rephrase for them.\n            federateLabel = _t(\"create_room|unfederated_label_default_on\");\n        }\n\n        let title: string;\n        if (isVideoRoom) {\n            title = _t(\"create_room|title_video_room\");\n        } else if (this.props.parentSpace || this.state.joinRule === JoinRule.Knock) {\n            title = _t(\"action|create_a_room\");\n        } else {\n            title =\n                this.state.joinRule === JoinRule.Public\n                    ? _t(\"create_room|title_public_room\")\n                    : _t(\"create_room|title_private_room\");\n        }\n\n        return (\n            <BaseDialog\n                className=\"mx_CreateRoomDialog\"\n                onFinished={this.props.onFinished}\n                title={title}\n                screenName=\"CreateRoom\"\n            >\n                <div className=\"mx_Dialog_content\">\n                    <Form.Root onSubmit={this.onOk} onKeyDown={this.onKeyDown}>\n                        <Field\n                            ref={this.nameField}\n                            label={_t(\"common|name\")}\n                            onChange={this.onNameChange}\n                            onValidate={this.onNameValidate}\n                            value={this.state.name}\n                            className=\"mx_CreateRoomDialog_name\"\n                        />\n                        <Field\n                            label={_t(\"create_room|topic_label\")}\n                            onChange={this.onTopicChange}\n                            value={this.state.topic}\n                            className=\"mx_CreateRoomDialog_topic\"\n                        />\n\n                        <div>\n                            <JoinRuleDropdown\n                                label={_t(\"create_room|room_visibility_label\")}\n                                labelInvite={_t(\"create_room|join_rule_invite\")}\n                                labelKnock={\n                                    this.askToJoinEnabled ? _t(\"room_settings|security|join_rule_knock\") : undefined\n                                }\n                                labelPublic={this.allowCreatingPublicRooms ? _t(\"common|public_room\") : undefined}\n                                labelRestricted={\n                                    this.supportsRestricted ? _t(\"create_room|join_rule_restricted\") : undefined\n                                }\n                                value={this.state.joinRule}\n                                onChange={this.onJoinRuleChange}\n                            />\n\n                            {publicPrivateLabel}\n                        </div>\n\n                        {visibilitySection}\n                        {e2eeSection}\n                        {e2eeStateSection}\n                        {aliasField}\n                        {this.advancedSettingsEnabled && (\n                            <details onToggle={this.onDetailsToggled} className=\"mx_CreateRoomDialog_details\">\n                                <summary className=\"mx_CreateRoomDialog_details_summary\">\n                                    {this.state.detailsOpen ? _t(\"action|hide_advanced\") : _t(\"action|show_advanced\")}\n                                </summary>\n                                <SettingsToggleInput\n                                    name=\"unfederated\"\n                                    label={_t(\"create_room|unfederated\", {\n                                        serverName: MatrixClientPeg.safeGet().getDomain(),\n                                    })}\n                                    onChange={this.onNoFederateChange}\n                                    checked={this.state.noFederate}\n                                    helpMessage={federateLabel}\n                                />\n                            </details>\n                        )}\n                    </Form.Root>\n                </div>\n                <DialogButtons\n                    primaryButton={\n                        isVideoRoom ? _t(\"create_room|action_create_video_room\") : _t(\"create_room|action_create_room\")\n                    }\n                    onPrimaryButtonClick={this.onOk}\n                    onCancel={this.onCancel}\n                />\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\nCopyright 2022 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useContext, useMemo } from \"react\";\nimport { EventType } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport BaseTool, { DevtoolsContext, type IDevtoolsProps } from \"./BaseTool\";\nimport { _t } from \"../../../../languageHandler\";\n\nconst ServersInRoom: React.FC<IDevtoolsProps> = ({ onBack }) => {\n    const context = useContext(DevtoolsContext);\n\n    const servers = useMemo<Record<string, number>>(() => {\n        const servers: Record<string, number> = {};\n        context.room.currentState.getStateEvents(EventType.RoomMember).forEach((ev) => {\n            if (ev.getContent().membership !== KnownMembership.Join) return; // only count joined users\n            const server = ev.getSender()!.split(\":\")[1];\n            servers[server] = (servers[server] ?? 0) + 1;\n        });\n        return servers;\n    }, [context.room]);\n\n    return (\n        <BaseTool onBack={onBack}>\n            <table>\n                <thead>\n                    <tr>\n                        <th>{_t(\"common|server\")}</th>\n                        <th>{_t(\"devtools|number_of_users\")}</th>\n                    </tr>\n                </thead>\n                <tbody>\n                    {Object.entries(servers).map(([server, numUsers]) => (\n                        <tr key={server}>\n                            <td>{server}</td>\n                            <td>{numUsers}</td>\n                        </tr>\n                    ))}\n                </tbody>\n            </table>\n        </BaseTool>\n    );\n};\n\nexport default ServersInRoom;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018-2023 The Matrix.org Foundation C.I.C.\nCopyright 2022 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEvent, useContext, useMemo, useState } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { _t, _td } from \"../../../../languageHandler\";\nimport BaseTool, { DevtoolsContext, type IDevtoolsProps } from \"./BaseTool\";\nimport AccessibleButton from \"../../elements/AccessibleButton\";\nimport SettingsStore, { LEVEL_ORDER } from \"../../../../settings/SettingsStore\";\nimport { type SettingLevel } from \"../../../../settings/SettingLevel\";\nimport { type SettingKey, SETTINGS, type SettingValueType } from \"../../../../settings/Settings\";\nimport Field from \"../../elements/Field\";\n\nconst SettingExplorer: React.FC<IDevtoolsProps> = ({ onBack }) => {\n    const [setting, setSetting] = useState<SettingKey | null>(null);\n    const [editing, setEditing] = useState(false);\n\n    if (setting && editing) {\n        const onBack = (): void => {\n            setEditing(false);\n        };\n        return <EditSetting setting={setting} onBack={onBack} />;\n    } else if (setting) {\n        const onBack = (): void => {\n            setSetting(null);\n        };\n        const onEdit = async (): Promise<void> => {\n            setEditing(true);\n        };\n        return <ViewSetting setting={setting} onBack={onBack} onEdit={onEdit} />;\n    } else {\n        const onView = (setting: SettingKey): void => {\n            setSetting(setting);\n        };\n        const onEdit = (setting: SettingKey): void => {\n            setSetting(setting);\n            setEditing(true);\n        };\n        return <SettingsList onBack={onBack} onView={onView} onEdit={onEdit} />;\n    }\n};\n\nexport default SettingExplorer;\n\ninterface ICanEditLevelFieldProps {\n    setting: SettingKey;\n    level: SettingLevel;\n    roomId?: string;\n}\n\nconst CanEditLevelField: React.FC<ICanEditLevelFieldProps> = ({ setting, roomId, level }) => {\n    const canEdit = SettingsStore.canSetValue(setting, roomId ?? null, level);\n    const className = canEdit ? \"mx_DevTools_SettingsExplorer_mutable\" : \"mx_DevTools_SettingsExplorer_immutable\";\n    return (\n        <td className={className}>\n            <code>{canEdit.toString()}</code>\n        </td>\n    );\n};\n\nfunction renderExplicitSettingValues(setting: SettingKey, roomId?: string): string {\n    const vals: Record<string, SettingValueType> = {};\n    for (const level of LEVEL_ORDER) {\n        try {\n            vals[level] = SettingsStore.getValueAt(level, setting, roomId, true, true);\n            if (vals[level] === undefined) {\n                vals[level] = null;\n            }\n        } catch (e) {\n            logger.warn(e);\n        }\n    }\n    return JSON.stringify(vals, null, 4);\n}\n\ninterface IEditSettingProps extends Pick<IDevtoolsProps, \"onBack\"> {\n    setting: SettingKey;\n}\n\nconst EditSetting: React.FC<IEditSettingProps> = ({ setting, onBack }) => {\n    const context = useContext(DevtoolsContext);\n    const [explicitValue, setExplicitValue] = useState(renderExplicitSettingValues(setting));\n    const [explicitRoomValue, setExplicitRoomValue] = useState(\n        renderExplicitSettingValues(setting, context.room.roomId),\n    );\n\n    const onSave = async (): Promise<string | undefined> => {\n        try {\n            const parsedExplicit = JSON.parse(explicitValue);\n            const parsedExplicitRoom = JSON.parse(explicitRoomValue);\n            for (const level of Object.keys(parsedExplicit)) {\n                logger.log(`[Devtools] Setting value of ${setting} at ${level} from user input`);\n                try {\n                    const val = parsedExplicit[level];\n                    await SettingsStore.setValue(setting, null, level as SettingLevel, val);\n                } catch (e) {\n                    logger.warn(e);\n                }\n            }\n\n            const roomId = context.room.roomId;\n            for (const level of Object.keys(parsedExplicit)) {\n                logger.log(`[Devtools] Setting value of ${setting} at ${level} in ${roomId} from user input`);\n                try {\n                    const val = parsedExplicitRoom[level];\n                    await SettingsStore.setValue(setting, roomId, level as SettingLevel, val);\n                } catch (e) {\n                    logger.warn(e);\n                }\n            }\n            onBack();\n        } catch (e) {\n            return _t(\"devtools|failed_to_save\") + (e instanceof Error ? ` (${e.message})` : \"\");\n        }\n    };\n\n    return (\n        <BaseTool onBack={onBack} actionLabel={_td(\"devtools|save_setting_values\")} onAction={onSave}>\n            <h3>\n                {_t(\"devtools|setting_colon\")} <code>{setting}</code>\n            </h3>\n\n            <div className=\"mx_DevTools_SettingsExplorer_warning\">\n                <strong>{_t(\"devtools|caution_colon\")}</strong> {_t(\"devtools|use_at_own_risk\")}\n            </div>\n\n            <div>\n                {_t(\"devtools|setting_definition\")}\n                <pre>\n                    <code>{JSON.stringify(SETTINGS[setting], null, 4)}</code>\n                </pre>\n            </div>\n\n            <div>\n                <table>\n                    <thead>\n                        <tr>\n                            <th>{_t(\"devtools|level\")}</th>\n                            <th>{_t(\"devtools|settable_global\")}</th>\n                            <th>{_t(\"devtools|settable_room\")}</th>\n                        </tr>\n                    </thead>\n                    <tbody>\n                        {LEVEL_ORDER.map((lvl) => (\n                            <tr key={lvl}>\n                                <td>\n                                    <code>{lvl}</code>\n                                </td>\n                                <CanEditLevelField setting={setting} level={lvl} />\n                                <CanEditLevelField setting={setting} roomId={context.room.roomId} level={lvl} />\n                            </tr>\n                        ))}\n                    </tbody>\n                </table>\n            </div>\n\n            <div>\n                <Field\n                    id=\"valExpl\"\n                    label={_t(\"devtools|values_explicit\")}\n                    type=\"text\"\n                    className=\"mx_DevTools_textarea\"\n                    element=\"textarea\"\n                    autoComplete=\"off\"\n                    value={explicitValue}\n                    onChange={(e) => setExplicitValue(e.target.value)}\n                />\n            </div>\n\n            <div>\n                <Field\n                    id=\"valExpl\"\n                    label={_t(\"devtools|values_explicit_room\")}\n                    type=\"text\"\n                    className=\"mx_DevTools_textarea\"\n                    element=\"textarea\"\n                    autoComplete=\"off\"\n                    value={explicitRoomValue}\n                    onChange={(e) => setExplicitRoomValue(e.target.value)}\n                />\n            </div>\n        </BaseTool>\n    );\n};\n\ninterface IViewSettingProps extends Pick<IDevtoolsProps, \"onBack\"> {\n    setting: SettingKey;\n    onEdit(): Promise<void>;\n}\n\nconst ViewSetting: React.FC<IViewSettingProps> = ({ setting, onEdit, onBack }) => {\n    const context = useContext(DevtoolsContext);\n\n    return (\n        <BaseTool onBack={onBack} actionLabel={_td(\"devtools|edit_values\")} onAction={onEdit}>\n            <h3>\n                {_t(\"devtools|setting_colon\")} <code>{setting}</code>\n            </h3>\n\n            <div>\n                {_t(\"devtools|setting_definition\")}\n                <pre>\n                    <code>{JSON.stringify(SETTINGS[setting], null, 4)}</code>\n                </pre>\n            </div>\n\n            <div>\n                {_t(\"devtools|value_colon\")}&nbsp;\n                <code>{renderSettingValue(SettingsStore.getValue(setting))}</code>\n            </div>\n\n            <div>\n                {_t(\"devtools|value_this_room_colon\")}&nbsp;\n                <code>{renderSettingValue(SettingsStore.getValue(setting, context.room.roomId))}</code>\n            </div>\n\n            <div>\n                {_t(\"devtools|values_explicit_colon\")}\n                <pre>\n                    <code>{renderExplicitSettingValues(setting)}</code>\n                </pre>\n            </div>\n\n            <div>\n                {_t(\"devtools|values_explicit_this_room_colon\")}\n                <pre>\n                    <code>{renderExplicitSettingValues(setting, context.room.roomId)}</code>\n                </pre>\n            </div>\n        </BaseTool>\n    );\n};\n\nfunction renderSettingValue(val: any): string {\n    // Note: we don't .toString() a string because we want JSON.stringify to inject quotes for us\n    const toStringTypes = [\"boolean\", \"number\"];\n    if (toStringTypes.includes(typeof val)) {\n        return val.toString();\n    } else {\n        return JSON.stringify(val);\n    }\n}\n\ninterface ISettingsListProps extends Pick<IDevtoolsProps, \"onBack\"> {\n    onView(setting: string): void;\n    onEdit(setting: string): void;\n}\n\nconst SettingsList: React.FC<ISettingsListProps> = ({ onBack, onView, onEdit }) => {\n    const context = useContext(DevtoolsContext);\n    const [query, setQuery] = useState(\"\");\n\n    const allSettings = useMemo(() => {\n        let allSettings = Object.keys(SETTINGS) as SettingKey[];\n        if (query) {\n            const lcQuery = query.toLowerCase();\n            allSettings = allSettings.filter((setting) => setting.toLowerCase().includes(lcQuery));\n        }\n        return allSettings;\n    }, [query]);\n\n    return (\n        <BaseTool onBack={onBack} className=\"mx_DevTools_SettingsExplorer\">\n            <Field\n                label={_t(\"common|filter_results\")}\n                autoFocus={true}\n                size={64}\n                type=\"text\"\n                autoComplete=\"off\"\n                value={query}\n                onChange={(ev: ChangeEvent<HTMLInputElement>) => setQuery(ev.target.value)}\n                className=\"mx_TextInputDialog_input mx_DevTools_RoomStateExplorer_query\"\n            />\n            <table>\n                <thead>\n                    <tr>\n                        <th>{_t(\"devtools|setting_id\")}</th>\n                        <th>{_t(\"devtools|value\")}</th>\n                        <th>{_t(\"devtools|value_in_this_room\")}</th>\n                    </tr>\n                </thead>\n                <tbody>\n                    {allSettings.map((i) => (\n                        <tr key={i}>\n                            <td>\n                                <AccessibleButton\n                                    kind=\"link_inline\"\n                                    className=\"mx_DevTools_SettingsExplorer_setting\"\n                                    onClick={() => onView(i)}\n                                >\n                                    <code>{i}</code>\n                                </AccessibleButton>\n                                <AccessibleButton\n                                    title={_t(\"devtools|edit_setting\")}\n                                    onClick={() => onEdit(i)}\n                                    className=\"mx_DevTools_SettingsExplorer_edit\"\n                                >\n                                    ✏\n                                </AccessibleButton>\n                            </td>\n                            <td>\n                                <code>{renderSettingValue(SettingsStore.getValue(i))}</code>\n                            </td>\n                            <td>\n                                <code>{renderSettingValue(SettingsStore.getValue(i, context.room.roomId))}</code>\n                            </td>\n                        </tr>\n                    ))}\n                </tbody>\n            </table>\n        </BaseTool>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\nCopyright 2022 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useContext, useState } from \"react\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { useEventEmitterState } from \"../../../../hooks/useEventEmitter\";\nimport { _t } from \"../../../../languageHandler\";\nimport BaseTool, { DevtoolsContext, type IDevtoolsProps } from \"./BaseTool\";\nimport WidgetStore, { type IApp } from \"../../../../stores/WidgetStore\";\nimport { UPDATE_EVENT } from \"../../../../stores/AsyncStore\";\nimport FilteredList from \"./FilteredList\";\nimport { StateEventEditor } from \"./RoomState\";\n\nconst WidgetExplorer: React.FC<IDevtoolsProps> = ({ onBack }) => {\n    const context = useContext(DevtoolsContext);\n    const [query, setQuery] = useState(\"\");\n    const [widget, setWidget] = useState<IApp | null>(null);\n\n    const widgets = useEventEmitterState(WidgetStore.instance, UPDATE_EVENT, () => {\n        return WidgetStore.instance.getApps(context.room.roomId);\n    });\n\n    if (widget && widgets.includes(widget)) {\n        const onBack = (): void => {\n            setWidget(null);\n        };\n\n        const allState = Array.from(\n            Array.from(context.room.currentState.events.values()).map((e: Map<string, MatrixEvent>) => {\n                return e.values();\n            }),\n        ).reduce((p, c) => {\n            p.push(...c);\n            return p;\n        }, [] as MatrixEvent[]);\n        const event = allState.find((ev) => ev.getId() === widget.eventId);\n        if (!event) {\n            // \"should never happen\"\n            return <BaseTool onBack={onBack}>{_t(\"devtools|failed_to_find_widget\")}</BaseTool>;\n        }\n\n        return <StateEventEditor mxEvent={event} onBack={onBack} />;\n    }\n\n    return (\n        <BaseTool onBack={onBack}>\n            <FilteredList query={query} onChange={setQuery}>\n                {widgets.map((w) => (\n                    <button className=\"mx_DevTools_button\" key={w.url + w.eventId} onClick={() => setWidget(w)}>\n                        {w.url}\n                    </button>\n                ))}\n            </FilteredList>\n        </BaseTool>\n    );\n};\n\nexport default WidgetExplorer;\n","/*\n * Copyright 2025 New Vector Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\n/**\n * @file Devtool for viewing room members and their devices.\n */\n\nimport React, { type JSX, useContext, useState } from \"react\";\nimport { type Device, type RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { type CryptoApi } from \"matrix-js-sdk/src/crypto-api\";\nimport { Form, SettingsToggleInput } from \"@vector-im/compound-web\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport BaseTool, { DevtoolsContext, type IDevtoolsProps } from \"./BaseTool\";\nimport FilteredList from \"./FilteredList\";\nimport { useAsyncMemo } from \"../../../../hooks/useAsyncMemo\";\nimport CopyableText from \"../../elements/CopyableText\";\nimport E2EIcon from \"../../rooms/E2EIcon\";\nimport { E2EStatus } from \"../../../../utils/ShieldUtils\";\n\n/**\n * Replacement function for `<i>` tags in translation strings.\n */\nfunction i(sub: string): JSX.Element {\n    return <i>{sub}</i>;\n}\n\n/**\n * Shows a list of users in the room, and allows selecting a user to view.\n *\n * Initially, filters to only show joined users, but offers the user an option to show all users.\n *\n * Once the user chooses a specific member, delegates to {@link UserView} to view a single user.\n */\nexport const UserList: React.FC<Pick<IDevtoolsProps, \"onBack\">> = ({ onBack }) => {\n    const context = useContext(DevtoolsContext);\n    const [query, setQuery] = useState(\"\");\n    // Show only joined users or all users with member events?\n    const [showOnlyJoined, setShowOnlyJoined] = useState(true);\n    // The `RoomMember` for the selected user (if any)\n    const [member, setMember] = useState<RoomMember | null>(null);\n\n    if (member) {\n        return <UserView member={member} onBack={() => setMember(null)} />;\n    }\n\n    const members = showOnlyJoined ? context.room.getJoinedMembers() : context.room.getMembers();\n\n    return (\n        <BaseTool onBack={onBack}>\n            <FilteredList query={query} onChange={setQuery}>\n                {members.map((member) => (\n                    <UserButton key={member.userId} member={member} onClick={() => setMember(member)} />\n                ))}\n            </FilteredList>\n            <Form.Root\n                onSubmit={(evt) => {\n                    evt.preventDefault();\n                    evt.stopPropagation();\n                }}\n            >\n                <SettingsToggleInput\n                    name=\"only_joined_members\"\n                    label={_t(\"devtools|only_joined_members\")}\n                    onChange={(e) => {\n                        setShowOnlyJoined(e.target.checked);\n                    }}\n                    checked={showOnlyJoined}\n                />\n            </Form.Root>\n        </BaseTool>\n    );\n};\n\ninterface UserButtonProps {\n    member: RoomMember;\n    onClick(): void;\n}\n\n/**\n * Button to select a user to view.\n */\nconst UserButton: React.FC<UserButtonProps> = ({ member, onClick }) => {\n    return (\n        <button className=\"mx_DevTools_button\" onClick={onClick}>\n            {member.userId}\n        </button>\n    );\n};\n\ninterface UserProps extends Pick<IDevtoolsProps, \"onBack\"> {\n    member: RoomMember;\n}\n\n/**\n * Shows a single user to view, and allows selecting a device to view.\n *\n * Once the user chooses a specific device, delegates to {@link DeviceView} to show a single device.\n */\nconst UserView: React.FC<UserProps> = ({ member, onBack }) => {\n    const context = useContext(DevtoolsContext);\n    const crypto = context.room.client.getCrypto();\n    // An element to show the verification status of the device (unknown,\n    // unverified, verified by cross signing, signed by owner).  The element\n    // will show text as well as an icon.  If crypto is not available, the value\n    // will be `null`.\n    const verificationStatus = useAsyncMemo(\n        async () => {\n            if (!crypto) {\n                return null;\n            }\n            const status = await crypto.getUserVerificationStatus(member.userId);\n            if (status.isCrossSigningVerified()) {\n                const e2eIcon = (): JSX.Element => (\n                    <E2EIcon\n                        isUser={true}\n                        hideTooltip={true}\n                        status={E2EStatus.Verified}\n                        className=\"mx_E2EIcon_inline\"\n                    />\n                );\n                return _t(\"devtools|user_verification_status|verified\", {}, { E2EIcon: e2eIcon });\n            } else if (status.wasCrossSigningVerified()) {\n                const e2eIcon = (): JSX.Element => (\n                    <E2EIcon\n                        isUser={true}\n                        hideTooltip={true}\n                        status={E2EStatus.Warning}\n                        className=\"mx_E2EIcon_inline\"\n                    />\n                );\n                return _t(\"devtools|user_verification_status|was_verified\", {}, { E2EIcon: e2eIcon });\n            } else if (status.needsUserApproval) {\n                const e2eIcon = (): JSX.Element => (\n                    <E2EIcon\n                        isUser={true}\n                        hideTooltip={true}\n                        status={E2EStatus.Warning}\n                        className=\"mx_E2EIcon_inline\"\n                    />\n                );\n                return _t(\"devtools|user_verification_status|identity_changed\", {}, { E2EIcon: e2eIcon });\n            } else {\n                const e2eIcon = (): JSX.Element => (\n                    <E2EIcon isUser={true} hideTooltip={true} status={E2EStatus.Normal} className=\"mx_E2EIcon_inline\" />\n                );\n                return _t(\"devtools|user_verification_status|unverified\", {}, { E2EIcon: e2eIcon });\n            }\n        },\n        [context, member],\n        _t(\"common|loading\"),\n    );\n    // The user's devices, as a Map from device ID to device information (see\n    // the `Device` type in `matrix-js-sdk/src/models/device.ts`).\n    const devices = useAsyncMemo(\n        async () => {\n            const devices = await crypto?.getUserDeviceInfo([member.userId]);\n            return devices?.get(member.userId) ?? new Map();\n        },\n        [context, member],\n        new Map(),\n    );\n    // The device to show, if any.\n    const [device, setDevice] = useState<Device | null>(null);\n\n    if (device) {\n        return <DeviceView crypto={crypto!} device={device} onBack={() => setDevice(null)} />;\n    }\n\n    const avatarUrl = member.getMxcAvatarUrl();\n    const memberEventContent = member.events.member?.getContent();\n\n    return (\n        <BaseTool onBack={onBack}>\n            <ul>\n                <li>\n                    <CopyableText getTextToCopy={() => member.userId} border={false}>\n                        {_t(\"devtools|user_id\", { userId: member.userId })}\n                    </CopyableText>\n                </li>\n                <li>{_t(\"devtools|user_room_membership\", { membership: member.membership ?? \"leave\" })}</li>\n                <li>\n                    {memberEventContent && \"displayname\" in memberEventContent\n                        ? _t(\"devtools|user_displayname\", { displayname: member.rawDisplayName })\n                        : _t(\"devtools|user_no_displayname\", {}, { i })}\n                </li>\n                <li>\n                    {avatarUrl !== undefined ? (\n                        <CopyableText getTextToCopy={() => avatarUrl} border={false}>\n                            {_t(\"devtools|user_avatar\", { avatar: avatarUrl })}\n                        </CopyableText>\n                    ) : (\n                        _t(\"devtools|user_no_avatar\", {}, { i })\n                    )}\n                </li>\n                <li>{verificationStatus}</li>\n            </ul>\n            <section>\n                <h2>{_t(\"devtools|devices\", { count: devices.size })}</h2>\n                <ul>\n                    {Array.from(devices.values()).map((device) => (\n                        <li key={device.deviceId}>\n                            <DeviceButton crypto={crypto!} device={device} onClick={() => setDevice(device)} />\n                        </li>\n                    ))}\n                </ul>\n            </section>\n        </BaseTool>\n    );\n};\n\ninterface DeviceButtonProps {\n    crypto: CryptoApi;\n    device: Device;\n    onClick(): void;\n}\n\n/**\n * Button to select a user to view.\n */\nconst DeviceButton: React.FC<DeviceButtonProps> = ({ crypto, device, onClick }) => {\n    const verificationIcon = useAsyncMemo(\n        async () => {\n            const status = await crypto.getDeviceVerificationStatus(device.userId, device.deviceId);\n            if (!status) {\n                return;\n            } else if (status.crossSigningVerified) {\n                return (\n                    <E2EIcon\n                        isUser={true}\n                        hideTooltip={true}\n                        status={E2EStatus.Verified}\n                        className=\"mx_E2EIcon_inline\"\n                    />\n                );\n            } else if (status.signedByOwner) {\n                return (\n                    <E2EIcon isUser={true} hideTooltip={true} status={E2EStatus.Normal} className=\"mx_E2EIcon_inline\" />\n                );\n            } else {\n                return (\n                    <E2EIcon\n                        isUser={true}\n                        hideTooltip={true}\n                        status={E2EStatus.Warning}\n                        className=\"mx_E2EIcon_inline\"\n                    />\n                );\n            }\n        },\n        [crypto, device],\n        null,\n    );\n    return (\n        <button className=\"mx_DevTools_button\" onClick={onClick}>\n            {verificationIcon}\n            {device.deviceId}\n        </button>\n    );\n};\n\ninterface DeviceProps extends Pick<IDevtoolsProps, \"onBack\"> {\n    crypto: CryptoApi;\n    device: Device;\n}\n\n/**\n * Show a single device to view.\n */\nconst DeviceView: React.FC<DeviceProps> = ({ crypto, device, onBack }) => {\n    // An element to show the verification status of the device (unknown,\n    // unverified, verified by cross signing, signed by owner).  The element\n    // will show text as well as an icon if applicable.\n    const verificationStatus = useAsyncMemo(\n        async () => {\n            const status = await crypto.getDeviceVerificationStatus(device.userId, device.deviceId);\n            if (!status) {\n                // `status` will be `null` if the device is unknown or if the\n                // device doesn't have device keys.  In either case, it's not a\n                // security issue since we won't be sending it decryption keys.\n                return _t(\"devtools|device_verification_status|unknown\");\n            } else if (status.crossSigningVerified) {\n                const e2eIcon = (): JSX.Element => (\n                    <E2EIcon\n                        isUser={true}\n                        hideTooltip={true}\n                        status={E2EStatus.Verified}\n                        className=\"mx_E2EIcon_inline\"\n                    />\n                );\n                return _t(\"devtools|device_verification_status|verified\", {}, { E2EIcon: e2eIcon });\n            } else if (status.signedByOwner) {\n                const e2eIcon = (): JSX.Element => (\n                    <E2EIcon isUser={true} hideTooltip={true} status={E2EStatus.Normal} className=\"mx_E2EIcon_inline\" />\n                );\n                return _t(\"devtools|device_verification_status|signed_by_owner\", {}, { E2EIcon: e2eIcon });\n            } else {\n                const e2eIcon = (): JSX.Element => (\n                    <E2EIcon\n                        isUser={true}\n                        hideTooltip={true}\n                        status={E2EStatus.Warning}\n                        className=\"mx_E2EIcon_inline\"\n                    />\n                );\n                return _t(\"devtools|device_verification_status|unverified\", {}, { E2EIcon: e2eIcon });\n            }\n        },\n        [crypto, device],\n        _t(\"common|loading\"),\n    );\n\n    const keyIdSuffix = \":\" + device.deviceId;\n    const deviceKeys = (\n        <ul>\n            {Array.from(device.keys.entries()).map(([keyId, key]) => {\n                if (keyId.endsWith(keyIdSuffix)) {\n                    return (\n                        <li key={keyId}>\n                            <CopyableText getTextToCopy={() => key} border={false}>\n                                {keyId.slice(0, -keyIdSuffix.length)}: {key}\n                            </CopyableText>\n                        </li>\n                    );\n                } else {\n                    return (\n                        <li key={keyId}>\n                            <i>{_t(\"devtools|invalid_device_key_id\")}</i>: {keyId}: {key}\n                        </li>\n                    );\n                }\n            })}\n        </ul>\n    );\n\n    return (\n        <BaseTool onBack={onBack}>\n            <ul>\n                <li>\n                    <CopyableText getTextToCopy={() => device.userId} border={false}>\n                        {_t(\"devtools|user_id\", { userId: device.userId })}\n                    </CopyableText>\n                </li>\n                <li>\n                    <CopyableText getTextToCopy={() => device.deviceId} border={false}>\n                        {_t(\"devtools|device_id\", { deviceId: device.deviceId })}\n                    </CopyableText>\n                </li>\n                <li>\n                    {\"displayName\" in device\n                        ? _t(\"devtools|user_displayname\", { displayname: device.displayName })\n                        : _t(\"devtools|user_no_displayname\", {}, { i })}\n                </li>\n                <li>{verificationStatus}</li>\n                <li>\n                    {device.dehydrated ? _t(\"devtools|device_dehydrated_yes\") : _t(\"devtools|device_dehydrated_no\")}\n                </li>\n                <li>\n                    {_t(\"devtools|device_keys\")}\n                    {deviceKeys}\n                </li>\n            </ul>\n        </BaseTool>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\nCopyright 2022 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useContext, useMemo, useState } from \"react\";\nimport {\n    type AccountDataEvents,\n    type IContent,\n    type MatrixEvent,\n    type RoomAccountDataEvents,\n} from \"matrix-js-sdk/src/matrix\";\n\nimport BaseTool, { DevtoolsContext, type IDevtoolsProps } from \"./BaseTool\";\nimport MatrixClientContext from \"../../../../contexts/MatrixClientContext\";\nimport { EventEditor, EventViewer, eventTypeField, type IEditorProps, stringify } from \"./Event\";\nimport FilteredList from \"./FilteredList\";\nimport { _td } from \"../../../../languageHandler\";\n\nexport const AccountDataEventEditor: React.FC<IEditorProps> = ({ mxEvent, onBack }) => {\n    const cli = useContext(MatrixClientContext);\n\n    const fields = useMemo(() => [eventTypeField(mxEvent?.getType())], [mxEvent]);\n\n    const onSend = async ([eventType]: Array<keyof AccountDataEvents>, content?: IContent): Promise<void> => {\n        await cli.setAccountData(eventType, content || {});\n    };\n\n    const defaultContent = mxEvent ? stringify(mxEvent.getContent()) : undefined;\n    return <EventEditor fieldDefs={fields} defaultContent={defaultContent} onSend={onSend} onBack={onBack} />;\n};\n\nexport const RoomAccountDataEventEditor: React.FC<IEditorProps> = ({ mxEvent, onBack }) => {\n    const context = useContext(DevtoolsContext);\n    const cli = useContext(MatrixClientContext);\n\n    const fields = useMemo(() => [eventTypeField(mxEvent?.getType())], [mxEvent]);\n\n    const onSend = async ([eventType]: Array<keyof RoomAccountDataEvents>, content?: IContent): Promise<void> => {\n        await cli.setRoomAccountData(context.room.roomId, eventType, content || {});\n    };\n\n    const defaultContent = mxEvent ? stringify(mxEvent.getContent()) : undefined;\n    return <EventEditor fieldDefs={fields} defaultContent={defaultContent} onSend={onSend} onBack={onBack} />;\n};\n\ninterface IProps extends IDevtoolsProps {\n    events: Map<string, MatrixEvent>;\n    Editor: React.FC<IEditorProps>;\n    actionLabel: TranslationKey;\n}\n\nconst BaseAccountDataExplorer: React.FC<IProps> = ({ events, Editor, actionLabel, onBack, setTool }) => {\n    const [query, setQuery] = useState(\"\");\n    const [event, setEvent] = useState<MatrixEvent | null>(null);\n\n    if (event) {\n        const onBack = (): void => {\n            setEvent(null);\n        };\n        return <EventViewer mxEvent={event} onBack={onBack} Editor={Editor} />;\n    }\n\n    const onAction = async (): Promise<void> => {\n        setTool(actionLabel, Editor);\n    };\n\n    return (\n        <BaseTool onBack={onBack} actionLabel={actionLabel} onAction={onAction}>\n            <FilteredList query={query} onChange={setQuery}>\n                {Array.from(events.entries()).map(([eventType, ev]) => {\n                    const onClick = (): void => {\n                        setEvent(ev);\n                    };\n\n                    return (\n                        <button className=\"mx_DevTools_button\" key={eventType} onClick={onClick}>\n                            {eventType}\n                        </button>\n                    );\n                })}\n            </FilteredList>\n        </BaseTool>\n    );\n};\n\nexport const AccountDataExplorer: React.FC<IDevtoolsProps> = ({ onBack, setTool }) => {\n    const cli = useContext(MatrixClientContext);\n\n    return (\n        <BaseAccountDataExplorer\n            events={cli.store.accountData}\n            Editor={AccountDataEventEditor}\n            actionLabel={_td(\"devtools|send_custom_account_data_event\")}\n            onBack={onBack}\n            setTool={setTool}\n        />\n    );\n};\n\nexport const RoomAccountDataExplorer: React.FC<IDevtoolsProps> = ({ onBack, setTool }) => {\n    const context = useContext(DevtoolsContext);\n\n    return (\n        <BaseAccountDataExplorer\n            events={context.room.accountData}\n            Editor={RoomAccountDataEventEditor}\n            actionLabel={_td(\"devtools|send_custom_room_account_data_event\")}\n            onBack={onBack}\n            setTool={setTool}\n        />\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { NotificationCountType, type Room, type Thread, ReceiptType } from \"matrix-js-sdk/src/matrix\";\nimport React, { type JSX, useContext } from \"react\";\nimport { type ReadReceipt } from \"matrix-js-sdk/src/models/read-receipt\";\n\nimport MatrixClientContext from \"../../../../contexts/MatrixClientContext\";\nimport { useNotificationState } from \"../../../../hooks/useRoomNotificationState\";\nimport { _t, _td } from \"../../../../languageHandler\";\nimport { determineUnreadState } from \"../../../../RoomNotifs\";\nimport { humanReadableNotificationLevel } from \"../../../../stores/notifications/NotificationLevel\";\nimport { doesRoomOrThreadHaveUnreadMessages } from \"../../../../Unread\";\nimport BaseTool, { DevtoolsContext, type IDevtoolsProps } from \"./BaseTool\";\nimport { useIsEncrypted } from \"../../../../hooks/useIsEncrypted.ts\";\n\nfunction UserReadUpTo({ target }: { target: ReadReceipt<any, any> }): JSX.Element {\n    const cli = useContext(MatrixClientContext);\n    const userId = cli.getSafeUserId();\n    const hasPrivate = !!target.getReadReceiptForUserId(userId, false, ReceiptType.ReadPrivate);\n    return (\n        <>\n            <li>\n                {_t(\"devtools|user_read_up_to\")}\n                <strong>{target.getReadReceiptForUserId(userId)?.eventId ?? _t(\"devtools|no_receipt_found\")}</strong>\n            </li>\n            <li>\n                {_t(\"devtools|user_read_up_to_ignore_synthetic\")}\n                <strong>\n                    {target.getReadReceiptForUserId(userId, true)?.eventId ?? _t(\"devtools|no_receipt_found\")}\n                </strong>\n            </li>\n            {hasPrivate && (\n                <>\n                    <li>\n                        {_t(\"devtools|user_read_up_to_private\")}\n                        <strong>\n                            {target.getReadReceiptForUserId(userId, false, ReceiptType.ReadPrivate)?.eventId ??\n                                _t(\"devtools|no_receipt_found\")}\n                        </strong>\n                    </li>\n                    <li>\n                        {_t(\"devtools|user_read_up_to_private_ignore_synthetic\")}\n                        <strong>\n                            {target.getReadReceiptForUserId(userId, true, ReceiptType.ReadPrivate)?.eventId ??\n                                _t(\"devtools|no_receipt_found\")}\n                        </strong>\n                    </li>\n                </>\n            )}\n        </>\n    );\n}\n\nexport default function RoomNotifications({ onBack }: IDevtoolsProps): JSX.Element {\n    const { room } = useContext(DevtoolsContext);\n    const cli = useContext(MatrixClientContext);\n    const isRoomEncrypted = useIsEncrypted(cli, room);\n\n    const { level, count } = determineUnreadState(room, undefined, false);\n    const [notificationState] = useNotificationState(room);\n\n    return (\n        <BaseTool onBack={onBack}>\n            <section>\n                <h2>{_t(\"devtools|room_status\")}</h2>\n                <ul>\n                    <li>\n                        {_t(\n                            \"devtools|room_unread_status_count\",\n                            {\n                                status: humanReadableNotificationLevel(level),\n                                count,\n                            },\n                            {\n                                strong: (sub) => <strong>{sub}</strong>,\n                            },\n                        )}\n                    </li>\n                    <li>\n                        {_t(\n                            \"devtools|notification_state\",\n                            {\n                                notificationState,\n                            },\n                            {\n                                strong: (sub) => <strong>{sub}</strong>,\n                            },\n                        )}\n                    </li>\n                    <li>\n                        {_t(\n                            isRoomEncrypted ? _td(\"devtools|room_encrypted\") : _td(\"devtools|room_not_encrypted\"),\n                            {},\n                            {\n                                strong: (sub) => <strong>{sub}</strong>,\n                            },\n                        )}\n                    </li>\n                </ul>\n            </section>\n\n            <section>\n                <h2>{_t(\"devtools|main_timeline\")}</h2>\n\n                <ul>\n                    <li>\n                        {_t(\"devtools|room_notifications_total\")}{\" \"}\n                        {room.getRoomUnreadNotificationCount(NotificationCountType.Total)}\n                    </li>\n                    <li>\n                        {_t(\"devtools|room_notifications_highlight\")}{\" \"}\n                        {room.getRoomUnreadNotificationCount(NotificationCountType.Highlight)}\n                    </li>\n                    <li>\n                        {_t(\"devtools|room_notifications_dot\")} {doesRoomOrThreadHaveUnreadMessages(room) + \"\"}\n                    </li>\n                    {roomHasUnread(room) && (\n                        <>\n                            <UserReadUpTo target={room} />\n                            <li>\n                                {_t(\"devtools|room_notifications_last_event\")}\n                                <ul>\n                                    <li>\n                                        {_t(\"devtools|id\")}{\" \"}\n                                        <strong>{room.timeline[room.timeline.length - 1].getId()}</strong>\n                                    </li>\n                                    <li>\n                                        {_t(\"devtools|room_notifications_type\")}{\" \"}\n                                        <strong>{room.timeline[room.timeline.length - 1].getType()}</strong>\n                                    </li>\n                                    <li>\n                                        {_t(\"devtools|room_notifications_sender\")}{\" \"}\n                                        <strong>{room.timeline[room.timeline.length - 1].getSender()}</strong>\n                                    </li>\n                                </ul>\n                            </li>\n                        </>\n                    )}\n                </ul>\n            </section>\n\n            <section>\n                <h2>{_t(\"devtools|threads_timeline\")}</h2>\n                <ul>\n                    {room\n                        .getThreads()\n                        .filter((thread) => threadHasUnread(thread))\n                        .map((thread) => (\n                            <li key={thread.id}>\n                                {_t(\"devtools|room_notifications_thread_id\")} {thread.id}\n                                <ul>\n                                    <li>\n                                        {_t(\"devtools|room_notifications_total\")}\n                                        <strong>\n                                            {room.getThreadUnreadNotificationCount(\n                                                thread.id,\n                                                NotificationCountType.Total,\n                                            )}\n                                        </strong>\n                                    </li>\n                                    <li>\n                                        {_t(\"devtools|room_notifications_highlight\")}\n                                        <strong>\n                                            {room.getThreadUnreadNotificationCount(\n                                                thread.id,\n                                                NotificationCountType.Highlight,\n                                            )}\n                                        </strong>\n                                    </li>\n                                    <li>\n                                        {_t(\"devtools|room_notifications_dot\")}{\" \"}\n                                        <strong>{doesRoomOrThreadHaveUnreadMessages(thread) + \"\"}</strong>\n                                    </li>\n                                    <UserReadUpTo target={thread} />\n                                    <li>\n                                        {_t(\"devtools|room_notifications_last_event\")}\n                                        <ul>\n                                            <li>\n                                                {_t(\"devtools|id\")} <strong>{thread.lastReply()?.getId()}</strong>\n                                            </li>\n                                            <li>\n                                                {_t(\"devtools|room_notifications_type\")}{\" \"}\n                                                <strong>{thread.lastReply()?.getType()}</strong>\n                                            </li>\n                                            <li>\n                                                {_t(\"devtools|room_notifications_sender\")}{\" \"}\n                                                <strong>{thread.lastReply()?.getSender()}</strong>\n                                            </li>\n                                        </ul>\n                                    </li>\n                                </ul>\n                            </li>\n                        ))}\n                </ul>\n            </section>\n        </BaseTool>\n    );\n}\n\nfunction threadHasUnread(thread: Thread): boolean {\n    const total = thread.room.getThreadUnreadNotificationCount(thread.id, NotificationCountType.Total);\n    const highlight = thread.room.getThreadUnreadNotificationCount(thread.id, NotificationCountType.Highlight);\n    const dot = doesRoomOrThreadHaveUnreadMessages(thread);\n\n    return total > 0 || highlight > 0 || dot;\n}\n\nfunction roomHasUnread(room: Room): boolean {\n    const total = room.getRoomUnreadNotificationCount(NotificationCountType.Total);\n    const highlight = room.getRoomUnreadNotificationCount(NotificationCountType.Highlight);\n    const dot = doesRoomOrThreadHaveUnreadMessages(room);\n\n    return total > 0 || highlight > 0 || dot;\n}\n","/*\n * Copyright 2025 New Vector Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport React, { type JSX } from \"react\";\nimport { InlineSpinner } from \"@vector-im/compound-web\";\n\nimport { useMatrixClientContext } from \"../../../../contexts/MatrixClientContext\";\nimport BaseTool from \"./BaseTool\";\nimport { useAsyncMemo } from \"../../../../hooks/useAsyncMemo\";\nimport { _t } from \"../../../../languageHandler\";\nimport Modal from \"../../../../Modal\";\nimport { ManualDeviceKeyVerificationDialog } from \"../ManualDeviceKeyVerificationDialog\";\nimport RestoreKeyBackupDialog from \"../../dialogs/security/RestoreKeyBackupDialog\";\n\ninterface KeyBackupProps {\n    /**\n     * Callback to invoke when the back button is clicked.\n     */\n    onBack(): void;\n}\n\n/**\n * A component that displays information about the key storage and cross-signing.\n */\nexport function Crypto({ onBack }: KeyBackupProps): JSX.Element {\n    const matrixClient = useMatrixClientContext();\n    return (\n        <BaseTool onBack={onBack} className=\"mx_Crypto\">\n            {matrixClient.getCrypto() ? (\n                <>\n                    <KeyStorage />\n                    <CrossSigning />\n                    <Session />\n\n                    <button\n                        type=\"button\"\n                        onClick={() => {\n                            Modal.createDialog(ManualDeviceKeyVerificationDialog);\n                        }}\n                    >\n                        {_t(\"devtools|manual_device_verification\")}\n                    </button>\n                    <button\n                        type=\"button\"\n                        onClick={() => {\n                            Modal.createDialog(\n                                RestoreKeyBackupDialog,\n                                undefined,\n                                undefined,\n                                /* priority = */ true,\n                                /* static = */ true,\n                            );\n                        }}\n                    >\n                        {_t(\"devtools|restore_from_backup\")}\n                    </button>\n                </>\n            ) : (\n                <span>{_t(\"devtools|crypto|crypto_not_available\")}</span>\n            )}\n        </BaseTool>\n    );\n}\n\n/**\n * A component that displays information about the key storage.\n */\nfunction KeyStorage(): JSX.Element {\n    const matrixClient = useMatrixClientContext();\n    const keyStorageData = useAsyncMemo(async () => {\n        const crypto = matrixClient.getCrypto()!;\n\n        // Get all the key storage data that we will display\n        const backupInfo = await crypto.getKeyBackupInfo();\n        const backupKeyStored = Boolean(await matrixClient.isKeyBackupKeyStored());\n        const backupKeyFromCache = await crypto.getSessionBackupPrivateKey();\n        const backupKeyCached = Boolean(backupKeyFromCache);\n        const backupKeyWellFormed = backupKeyFromCache instanceof Uint8Array;\n        const activeBackupVersion = await crypto.getActiveSessionBackupVersion();\n        const secretStorageKeyInAccount = await matrixClient.secretStorage.hasKey();\n        const secretStorageReady = await crypto.isSecretStorageReady();\n\n        return {\n            backupInfo,\n            backupKeyStored,\n            backupKeyCached,\n            backupKeyWellFormed,\n            activeBackupVersion,\n            secretStorageKeyInAccount,\n            secretStorageReady,\n        };\n    }, [matrixClient]);\n\n    // Show a spinner while loading\n    if (keyStorageData === undefined) return <InlineSpinner aria-label={_t(\"common|loading\")} />;\n\n    const {\n        backupInfo,\n        backupKeyStored,\n        backupKeyCached,\n        backupKeyWellFormed,\n        activeBackupVersion,\n        secretStorageKeyInAccount,\n        secretStorageReady,\n    } = keyStorageData;\n\n    return (\n        <table aria-label={_t(\"devtools|crypto|key_storage\")}>\n            <thead>{_t(\"devtools|crypto|key_storage\")}</thead>\n            <tbody>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|key_backup_latest_version\")}</th>\n                    <td>\n                        {backupInfo\n                            ? `${backupInfo.version} (${_t(\"settings|security|key_backup_algorithm\")} ${backupInfo.algorithm})`\n                            : _t(\"devtools|crypto|key_backup_inactive_warning\")}\n                    </td>\n                </tr>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|backup_key_stored_status\")}</th>\n                    <td>\n                        {backupKeyStored\n                            ? _t(\"devtools|crypto|backup_key_stored\")\n                            : _t(\"devtools|crypto|backup_key_not_stored\")}\n                    </td>\n                </tr>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|key_backup_active_version\")}</th>\n                    <td>\n                        {activeBackupVersion === null\n                            ? _t(\"devtools|crypto|key_backup_active_version_none\")\n                            : activeBackupVersion}\n                    </td>\n                </tr>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|backup_key_cached_status\")}</th>\n                    <td>\n                        {`${\n                            backupKeyCached\n                                ? _t(\"devtools|crypto|backup_key_cached\")\n                                : _t(\"devtools|crypto|not_found_locally\")\n                        }, ${\n                            backupKeyWellFormed\n                                ? _t(\"devtools|crypto|backup_key_well_formed\")\n                                : _t(\"devtools|crypto|backup_key_unexpected_type\")\n                        }`}\n                    </td>\n                </tr>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|4s_public_key_status\")}</th>\n                    <td>\n                        {secretStorageKeyInAccount\n                            ? _t(\"devtools|crypto|4s_public_key_in_account_data\")\n                            : _t(\"devtools|crypto|4s_public_key_not_in_account_data\")}\n                    </td>\n                </tr>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|secret_storage_status\")}</th>\n                    <td>\n                        {secretStorageReady\n                            ? _t(\"devtools|crypto|secret_storage_ready\")\n                            : _t(\"devtools|crypto|secret_storage_not_ready\")}\n                    </td>\n                </tr>\n            </tbody>\n        </table>\n    );\n}\n\n/**\n * A component that displays information about cross-signing.\n */\nfunction CrossSigning(): JSX.Element {\n    const matrixClient = useMatrixClientContext();\n    const crossSigningData = useAsyncMemo(async () => {\n        const crypto = matrixClient.getCrypto()!;\n\n        // Get all the cross-signing data that we will display\n        const crossSigningStatus = await crypto.getCrossSigningStatus();\n        const crossSigningPublicKeysOnDevice = crossSigningStatus.publicKeysOnDevice;\n        const crossSigningPrivateKeysInStorage = crossSigningStatus.privateKeysInSecretStorage;\n        const masterPrivateKeyCached = crossSigningStatus.privateKeysCachedLocally.masterKey;\n        const selfSigningPrivateKeyCached = crossSigningStatus.privateKeysCachedLocally.selfSigningKey;\n        const userSigningPrivateKeyCached = crossSigningStatus.privateKeysCachedLocally.userSigningKey;\n        const crossSigningReady = await crypto.isCrossSigningReady();\n\n        return {\n            crossSigningPublicKeysOnDevice,\n            crossSigningPrivateKeysInStorage,\n            masterPrivateKeyCached,\n            selfSigningPrivateKeyCached,\n            userSigningPrivateKeyCached,\n            crossSigningReady,\n        };\n    }, [matrixClient]);\n\n    // Show a spinner while loading\n    if (crossSigningData === undefined) return <InlineSpinner aria-label={_t(\"common|loading\")} />;\n\n    const {\n        crossSigningPublicKeysOnDevice,\n        crossSigningPrivateKeysInStorage,\n        masterPrivateKeyCached,\n        selfSigningPrivateKeyCached,\n        userSigningPrivateKeyCached,\n        crossSigningReady,\n    } = crossSigningData;\n\n    return (\n        <table aria-label={_t(\"devtools|crypto|cross_signing\")}>\n            <thead>{_t(\"devtools|crypto|cross_signing\")}</thead>\n            <tbody>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|cross_signing_status\")}</th>\n                    <td>{getCrossSigningStatus(crossSigningReady, crossSigningPrivateKeysInStorage)}</td>\n                </tr>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|cross_signing_public_keys_on_device_status\")}</th>\n                    <td>\n                        {crossSigningPublicKeysOnDevice\n                            ? _t(\"devtools|crypto|cross_signing_public_keys_on_device\")\n                            : _t(\"devtools|crypto|not_found\")}\n                    </td>\n                </tr>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|cross_signing_private_keys_in_storage_status\")}</th>\n                    <td>\n                        {crossSigningPrivateKeysInStorage\n                            ? _t(\"devtools|crypto|cross_signing_private_keys_in_storage\")\n                            : _t(\"devtools|crypto|cross_signing_private_keys_not_in_storage\")}\n                    </td>\n                </tr>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|master_private_key_cached_status\")}</th>\n                    <td>\n                        {masterPrivateKeyCached\n                            ? _t(\"devtools|crypto|cross_signing_cached\")\n                            : _t(\"devtools|crypto|not_found_locally\")}\n                    </td>\n                </tr>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|self_signing_private_key_cached_status\")}</th>\n                    <td>\n                        {selfSigningPrivateKeyCached\n                            ? _t(\"devtools|crypto|cross_signing_cached\")\n                            : _t(\"devtools|crypto|not_found_locally\")}\n                    </td>\n                </tr>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|user_signing_private_key_cached_status\")}</th>\n                    <td>\n                        {userSigningPrivateKeyCached\n                            ? _t(\"devtools|crypto|cross_signing_cached\")\n                            : _t(\"devtools|crypto|not_found_locally\")}\n                    </td>\n                </tr>\n            </tbody>\n        </table>\n    );\n}\n\n/**\n * Get the cross-signing status.\n * @param crossSigningReady Whether cross-signing is ready.\n * @param crossSigningPrivateKeysInStorage Whether cross-signing private keys are in secret storage.\n */\nfunction getCrossSigningStatus(crossSigningReady: boolean, crossSigningPrivateKeysInStorage: boolean): string {\n    if (crossSigningReady) {\n        return crossSigningPrivateKeysInStorage\n            ? _t(\"devtools|crypto|cross_signing_ready\")\n            : _t(\"devtools|crypto|cross_signing_untrusted\");\n    }\n\n    if (crossSigningPrivateKeysInStorage) {\n        return _t(\"devtools|crypto|cross_signing_not_ready\");\n    }\n\n    return _t(\"devtools|crypto|cross_signing_not_ready\");\n}\n\n/**\n * A component that displays information about the current session.\n */\nfunction Session(): JSX.Element {\n    const matrixClient = useMatrixClientContext();\n    const sessionData = useAsyncMemo(async () => {\n        const crypto = matrixClient.getCrypto()!;\n        const keys = await crypto.getOwnDeviceKeys();\n        return {\n            fingerprint: keys.ed25519,\n            deviceId: matrixClient.deviceId,\n        };\n    }, [matrixClient]);\n\n    // Show a spinner while loading\n    if (sessionData === undefined) {\n        return <InlineSpinner aria-label={_t(\"common|loading\")} />;\n    }\n\n    return (\n        <table aria-label={_t(\"devtools|crypto|session\")}>\n            <thead>{_t(\"devtools|crypto|session\")}</thead>\n            <tbody>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|device_id\")}</th>\n                    <td>{sessionData.deviceId}</td>\n                </tr>\n                <tr>\n                    <th scope=\"row\">{_t(\"devtools|crypto|session_fingerprint\")}</th>\n                    <td>{sessionData.fingerprint}</td>\n                </tr>\n            </tbody>\n        </table>\n    );\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEvent, type JSX, useCallback, useState } from \"react\";\nimport { EditInPlace } from \"@vector-im/compound-web\";\n\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { _t } from \"../../../languageHandler\";\nimport { type SettingLevel } from \"../../../settings/SettingLevel\";\nimport { type StringSettingKey } from \"../../../settings/Settings\";\n\ninterface Props {\n    settingKey: StringSettingKey;\n    level: SettingLevel;\n    roomId?: string; // for per-room settings\n    label?: string;\n    isExplicit?: boolean;\n    onChange?(value: string): void;\n}\n\nconst SettingsField = ({ settingKey, level, roomId, isExplicit, label, onChange: _onSave }: Props): JSX.Element => {\n    const settingsValue = SettingsStore.getValueAt(level, settingKey, roomId, isExplicit);\n    const [value, setValue] = useState(settingsValue);\n    const [busy, setBusy] = useState(false);\n\n    const onChange = useCallback((e: ChangeEvent<HTMLInputElement>) => {\n        setValue(e.target.value);\n    }, []);\n    const onCancel = useCallback(() => {\n        setValue(settingsValue);\n    }, [settingsValue]);\n    const onSave = useCallback(async () => {\n        setBusy(true);\n        await SettingsStore.setValue(settingKey, roomId ?? null, level, value);\n        setBusy(false);\n        _onSave?.(value);\n    }, [level, roomId, settingKey, value, _onSave]);\n\n    return (\n        <EditInPlace\n            label={label ?? SettingsStore.getDisplayName(settingKey, level) ?? \"\"}\n            value={value}\n            saveButtonLabel={_t(\"common|save\")}\n            cancelButtonLabel={_t(\"common|cancel\")}\n            savedLabel={_t(\"common|saved\")}\n            savingLabel={_t(\"common|updating\")}\n            onChange={onChange}\n            onCancel={onCancel}\n            onSave={onSave}\n            disabled={busy}\n        />\n    );\n};\n\nexport default SettingsField;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018-2023 The Matrix.org Foundation C.I.C.\nCopyright 2022 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useState } from \"react\";\nimport { Form } from \"@vector-im/compound-web\";\n\nimport { _t, _td } from \"../../../languageHandler\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport BaseDialog from \"./BaseDialog\";\nimport { TimelineEventEditor } from \"./devtools/Event\";\nimport ServersInRoom from \"./devtools/ServersInRoom\";\nimport SettingExplorer from \"./devtools/SettingExplorer\";\nimport { RoomStateExplorer } from \"./devtools/RoomState\";\nimport BaseTool, { DevtoolsContext, type IDevtoolsProps } from \"./devtools/BaseTool\";\nimport WidgetExplorer from \"./devtools/WidgetExplorer\";\nimport { UserList } from \"./devtools/Users\";\nimport { AccountDataExplorer, RoomAccountDataExplorer } from \"./devtools/AccountData\";\nimport SettingsFlag from \"../elements/SettingsFlag\";\nimport { SettingLevel } from \"../../../settings/SettingLevel\";\nimport ServerInfo from \"./devtools/ServerInfo\";\nimport CopyableText from \"../elements/CopyableText\";\nimport RoomNotifications from \"./devtools/RoomNotifications\";\nimport { Crypto } from \"./devtools/Crypto\";\nimport SettingsField from \"../elements/SettingsField.tsx\";\n\nenum Category {\n    Room,\n    Other,\n}\n\nconst categoryLabels: Record<Category, TranslationKey> = {\n    [Category.Room]: _td(\"devtools|category_room\"),\n    [Category.Other]: _td(\"devtools|category_other\"),\n};\n\nexport type Tool = React.FC<IDevtoolsProps> | ((props: IDevtoolsProps) => JSX.Element);\nconst Tools: Record<Category, [label: TranslationKey, tool: Tool][]> = {\n    [Category.Room]: [\n        [_td(\"devtools|send_custom_timeline_event\"), TimelineEventEditor],\n        [_td(\"devtools|explore_room_state\"), RoomStateExplorer],\n        [_td(\"devtools|explore_room_account_data\"), RoomAccountDataExplorer],\n        [_td(\"devtools|view_servers_in_room\"), ServersInRoom],\n        [_td(\"devtools|notifications_debug\"), RoomNotifications],\n        [_td(\"devtools|active_widgets\"), WidgetExplorer],\n        [_td(\"devtools|users\"), UserList],\n    ],\n    [Category.Other]: [\n        [_td(\"devtools|explore_account_data\"), AccountDataExplorer],\n        [_td(\"devtools|settings_explorer\"), SettingExplorer],\n        [_td(\"devtools|server_info\"), ServerInfo],\n        [_td(\"devtools|crypto|title\"), Crypto],\n    ],\n};\n\ninterface IProps {\n    roomId: string;\n    threadRootId?: string | null;\n    onFinished(finished?: boolean): void;\n}\n\ntype ToolInfo = [label: TranslationKey, tool: Tool];\n\nconst DevtoolsDialog: React.FC<IProps> = ({ roomId, threadRootId, onFinished }) => {\n    const [tool, setTool] = useState<ToolInfo | null>(null);\n\n    let body: JSX.Element;\n    let onBack: () => void;\n\n    if (tool) {\n        onBack = () => {\n            setTool(null);\n        };\n\n        const Tool = tool[1];\n        body = <Tool onBack={onBack} setTool={(label, tool) => setTool([label, tool])} />;\n    } else {\n        const onBack = (): void => {\n            onFinished(false);\n        };\n        body = (\n            <BaseTool onBack={onBack}>\n                {Object.entries(Tools).map(([category, tools]) => (\n                    <div key={category}>\n                        <h2 className=\"mx_DevTools_toolHeading\">\n                            {_t(categoryLabels[category as unknown as Category])}\n                        </h2>\n                        {tools.map(([label, tool]) => {\n                            const onClick = (): void => {\n                                setTool([label, tool]);\n                            };\n                            return (\n                                <button className=\"mx_DevTools_button\" key={label} onClick={onClick}>\n                                    {_t(label)}\n                                </button>\n                            );\n                        })}\n                    </div>\n                ))}\n                <Form.Root\n                    onSubmit={(evt) => {\n                        evt.preventDefault();\n                        evt.stopPropagation();\n                    }}\n                    className=\"mx_DevTools_toggleForm\"\n                >\n                    <h2 className=\"mx_DevTools_toolHeading\">{_t(\"common|options\")}</h2>\n                    <SettingsFlag name=\"developerMode\" level={SettingLevel.ACCOUNT} />\n                    <SettingsFlag name=\"showHiddenEventsInTimeline\" level={SettingLevel.DEVICE} />\n                    <SettingsFlag name=\"enableWidgetScreenshots\" level={SettingLevel.ACCOUNT} />\n                </Form.Root>\n                {/* The settings field needs to be outside `Form.Root` because `SettingsField` will have a inner Form,\n                    Otherwise we end up with a nester `Form` and that prohibits `preventDefault` so setting the value\n                    will reload the page.\n                 */}\n                <SettingsField\n                    settingKey=\"Developer.elementCallUrl\"\n                    level={SettingLevel.DEVICE}\n                    aria-label=\"elementCallUrl\"\n                />\n            </BaseTool>\n        );\n    }\n\n    const label = tool ? _t(tool[0]) : _t(\"devtools|toolbox\");\n    return (\n        <BaseDialog className=\"mx_QuestionDialog\" onFinished={onFinished} title={_t(\"devtools|developer_tools\")}>\n            <MatrixClientContext.Consumer>\n                {(cli) => (\n                    <>\n                        <div className=\"mx_DevTools_label_left\">{label}</div>\n                        <CopyableText className=\"mx_DevTools_label_right\" getTextToCopy={() => roomId} border={false}>\n                            {_t(\"devtools|room_id\", { roomId })}\n                        </CopyableText>\n                        {!threadRootId ? null : (\n                            <CopyableText\n                                className=\"mx_DevTools_label_right\"\n                                getTextToCopy={() => threadRootId}\n                                border={false}\n                            >\n                                {_t(\"devtools|thread_root_id\", { threadRootId })}\n                            </CopyableText>\n                        )}\n                        <div className=\"mx_DevTools_label_bottom\" />\n                        {cli.getRoom(roomId) && (\n                            <DevtoolsContext.Provider value={{ room: cli.getRoom(roomId)!, threadRootId }}>\n                                {body}\n                            </DevtoolsContext.Provider>\n                        )}\n                    </>\n                )}\n            </MatrixClientContext.Consumer>\n        </BaseDialog>\n    );\n};\n\nexport default DevtoolsDialog;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/*\n * Usage:\n * Modal.createDialog(ErrorDialog, {\n *   title: \"some text\", (default: \"Error\")\n *   description: \"some more text\",\n *   button: \"Button Text\",\n *   onFinished: someFunction,\n *   focus: true|false (default: true)\n * });\n */\n\nimport React from \"react\";\n\nimport { _t, UserFriendlyError } from \"../../../languageHandler\";\nimport BaseDialog from \"./BaseDialog\";\n\n/**\n * Get a user friendly error message string from a given error. Useful for the\n * `description` prop of the `ErrorDialog`\n * @param err Error object in question to extract a useful message from. To make it easy\n * to use with try/catch, this is typed as `any` because try/catch will type\n * the error as `unknown`. And in any case we can use the fallback message.\n * @param translatedFallbackMessage The fallback message to be used if the error doesn't have any message\n * @returns a user friendly error message string from a given error\n */\nexport function extractErrorMessageFromError(err: any, translatedFallbackMessage: string): string {\n    return (\n        (err instanceof UserFriendlyError && err.translatedMessage) ||\n        (err instanceof Error && err.message) ||\n        translatedFallbackMessage\n    );\n}\n\ninterface IProps {\n    onFinished: (success?: boolean) => void;\n    title?: string;\n    description?: React.ReactNode;\n    button?: string;\n    focus?: boolean;\n    headerImage?: string;\n}\n\ninterface IState {\n    onFinished: (success: boolean) => void;\n}\n\nexport default class ErrorDialog extends React.Component<IProps, IState> {\n    public static defaultProps: Partial<IProps> = {\n        focus: true,\n    };\n\n    private onClick = (): void => {\n        this.props.onFinished(true);\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <BaseDialog\n                className=\"mx_ErrorDialog\"\n                onFinished={this.props.onFinished}\n                title={this.props.title || _t(\"common|error\")}\n                headerImage={this.props.headerImage}\n                contentId=\"mx_Dialog_content\"\n            >\n                <div className=\"mx_Dialog_content\" id=\"mx_Dialog_content\">\n                    {this.props.description || _t(\"error|dialog_description_default\")}\n                </div>\n                <div className=\"mx_Dialog_buttons\">\n                    <button className=\"mx_Dialog_primary\" onClick={this.onClick} autoFocus={this.props.focus}>\n                        {this.props.button || _t(\"action|ok\")}\n                    </button>\n                </div>\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\nCopyright 2019 Bastian Masanek, Noxware IT <matrix@noxware.de>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode } from \"react\";\nimport classNames from \"classnames\";\n\nimport { _t } from \"../../../languageHandler\";\nimport BaseDialog from \"./BaseDialog\";\nimport DialogButtons from \"../elements/DialogButtons\";\n\ninterface IProps {\n    top?: ReactNode;\n    title?: string;\n    description?: ReactNode;\n    className?: string;\n    button?: boolean | string;\n    hasCloseButton?: boolean;\n    fixedWidth?: boolean;\n    onKeyDown?(event: KeyboardEvent | React.KeyboardEvent): void;\n    onFinished(): void;\n}\n\nexport default class InfoDialog extends React.Component<IProps> {\n    public static defaultProps: Partial<IProps> = {\n        title: \"\",\n        description: \"\",\n        hasCloseButton: false,\n    };\n\n    private onFinished = (): void => {\n        this.props.onFinished();\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <BaseDialog\n                className=\"mx_InfoDialog\"\n                onFinished={this.props.onFinished}\n                top={this.props.top}\n                title={this.props.title}\n                contentId=\"mx_Dialog_content\"\n                hasCancel={this.props.hasCloseButton}\n                onKeyDown={this.props.onKeyDown}\n                fixedWidth={this.props.fixedWidth}\n            >\n                <div className={classNames(\"mx_Dialog_content\", this.props.className)} id=\"mx_Dialog_content\">\n                    {this.props.description}\n                </div>\n                {this.props.button !== false && (\n                    <DialogButtons\n                        primaryButton={this.props.button || _t(\"action|ok\")}\n                        onPrimaryButtonClick={this.onFinished}\n                        hasCancel={false}\n                    />\n                )}\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Vector Creations Ltd\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { type AuthType } from \"matrix-js-sdk/src/interactive-auth\";\n\nimport { _t } from \"../../../languageHandler\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport InteractiveAuth, {\n    ERROR_USER_CANCELLED,\n    type InteractiveAuthCallback,\n    type InteractiveAuthProps,\n} from \"../../structures/InteractiveAuth\";\nimport { type ContinueKind, SSOAuthEntry } from \"../auth/InteractiveAuthEntryComponents\";\nimport BaseDialog from \"./BaseDialog\";\nimport { Linkify } from \"../../../Linkify\";\n\ntype DialogAesthetics = Partial<{\n    [x in AuthType]: {\n        [x: number]: {\n            title: string;\n            body: string;\n            continueText: string;\n            continueKind: ContinueKind;\n        };\n    };\n}>;\n\nexport interface InteractiveAuthDialogProps<T = unknown> extends Pick<\n    InteractiveAuthProps<T>,\n    \"makeRequest\" | \"authData\"\n> {\n    // matrix client to use for UI auth requests\n    matrixClient: MatrixClient;\n\n    // Optional title and body to show when not showing a particular stage\n    title?: string;\n    body?: string;\n\n    // Optional title and body pairs for particular stages and phases within\n    // those stages. Object structure/example is:\n    // {\n    //     \"org.example.stage_type\": {\n    //         1: {\n    //             \"body\": \"This is a body for phase 1\" of org.example.stage_type,\n    //             \"title\": \"Title for phase 1 of org.example.stage_type\"\n    //         },\n    //         2: {\n    //             \"body\": \"This is a body for phase 2 of org.example.stage_type\",\n    //             \"title\": \"Title for phase 2 of org.example.stage_type\"\n    //             \"continueText\": \"Confirm identity with Example Auth\",\n    //             \"continueKind\": \"danger\"\n    //         }\n    //     }\n    // }\n    //\n    // Default is defined in _getDefaultDialogAesthetics()\n    aestheticsForStagePhases?: DialogAesthetics;\n\n    onFinished(success?: boolean, result?: T | Error | null): void;\n}\n\ninterface IState {\n    authError: Error | null;\n\n    // See _onUpdateStagePhase()\n    uiaStage: AuthType | null;\n    uiaStagePhase: number | null;\n}\n\nexport default class InteractiveAuthDialog<T> extends React.Component<InteractiveAuthDialogProps<T>, IState> {\n    public constructor(props: InteractiveAuthDialogProps<T>) {\n        super(props);\n\n        this.state = {\n            authError: null,\n\n            // See _onUpdateStagePhase()\n            uiaStage: null,\n            uiaStagePhase: null,\n        };\n    }\n\n    private getDefaultDialogAesthetics(): DialogAesthetics {\n        const ssoAesthetics = {\n            [SSOAuthEntry.PHASE_PREAUTH]: {\n                title: _t(\"auth|uia|sso_title\"),\n                body: _t(\"auth|uia|sso_preauth_body\"),\n                continueText: _t(\"auth|sso\"),\n                continueKind: \"primary\",\n            },\n            [SSOAuthEntry.PHASE_POSTAUTH]: {\n                title: _t(\"auth|uia|sso_postauth_title\"),\n                body: _t(\"auth|uia|sso_postauth_body\"),\n                continueText: _t(\"action|confirm\"),\n                continueKind: \"primary\",\n            },\n        };\n\n        return {\n            [SSOAuthEntry.LOGIN_TYPE]: ssoAesthetics,\n            [SSOAuthEntry.UNSTABLE_LOGIN_TYPE]: ssoAesthetics,\n        };\n    }\n\n    private onAuthFinished: InteractiveAuthCallback<T> = async (success, result): Promise<void> => {\n        if (success) {\n            this.props.onFinished(true, result as T);\n        } else {\n            if (result === ERROR_USER_CANCELLED) {\n                this.props.onFinished(false, null);\n            } else {\n                this.setState({\n                    authError: result as Error,\n                });\n            }\n        }\n    };\n\n    private onUpdateStagePhase = (newStage: AuthType, newPhase: number): void => {\n        // We copy the stage and stage phase params into state for title selection in render()\n        this.setState({ uiaStage: newStage, uiaStagePhase: newPhase });\n    };\n\n    private onDismissClick = (): void => {\n        this.props.onFinished(false);\n    };\n\n    public render(): React.ReactNode {\n        // Let's pick a title, body, and other params text that we'll show to the user. The order\n        // is most specific first, so stagePhase > our props > defaults.\n\n        let title = this.state.authError ? \"Error\" : (this.props.title ?? _t(\"common|authentication\"));\n        let body = this.state.authError ? null : this.props.body;\n        let continueText: string | undefined;\n        let continueKind: ContinueKind | undefined;\n        const dialogAesthetics = this.props.aestheticsForStagePhases || this.getDefaultDialogAesthetics();\n        if (!this.state.authError && dialogAesthetics) {\n            if (\n                this.state.uiaStage !== null &&\n                this.state.uiaStagePhase !== null &&\n                dialogAesthetics[this.state.uiaStage]\n            ) {\n                const aesthetics = dialogAesthetics[this.state.uiaStage]![this.state.uiaStagePhase];\n                if (aesthetics) {\n                    if (aesthetics.title) title = aesthetics.title;\n                    if (aesthetics.body) body = aesthetics.body;\n                    if (aesthetics.continueText) continueText = aesthetics.continueText;\n                    if (aesthetics.continueKind) continueKind = aesthetics.continueKind;\n                }\n            }\n        }\n\n        let content: JSX.Element;\n        if (this.state.authError) {\n            content = (\n                <div id=\"mx_Dialog_content\">\n                    <Linkify>\n                        <div role=\"alert\">{this.state.authError.message || this.state.authError.toString()}</div>\n                    </Linkify>\n                    <br />\n                    <AccessibleButton onClick={this.onDismissClick} className=\"mx_GeneralButton\" autoFocus={true}>\n                        {_t(\"action|dismiss\")}\n                    </AccessibleButton>\n                </div>\n            );\n        } else {\n            content = (\n                <div id=\"mx_Dialog_content\">\n                    {body}\n                    <InteractiveAuth\n                        matrixClient={this.props.matrixClient}\n                        authData={this.props.authData}\n                        makeRequest={this.props.makeRequest}\n                        onAuthFinished={this.onAuthFinished}\n                        onStagePhaseChange={this.onUpdateStagePhase}\n                        continueText={continueText}\n                        continueKind={continueKind}\n                    />\n                </div>\n            );\n        }\n\n        return (\n            <BaseDialog\n                className=\"mx_InteractiveAuthDialog\"\n                onFinished={this.props.onFinished}\n                title={title}\n                contentId=\"mx_Dialog_content\"\n            >\n                {content}\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef, type JSX, type ReactNode, type SyntheticEvent } from \"react\";\nimport { EventType, MatrixError, type Room, RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { type MatrixCall } from \"matrix-js-sdk/src/webrtc/call\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { uniqBy } from \"lodash\";\nimport { RichList, RichItem, PillInput, Pill } from \"@element-hq/web-shared-components\";\nimport { DialPadIcon, UserProfileSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { Icon as EmailPillAvatarIcon } from \"../../../../res/img/icon-email-pill-avatar.svg\";\nimport { _t, _td } from \"../../../languageHandler\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { makeRoomPermalink, makeUserPermalink } from \"../../../utils/permalinks/Permalinks\";\nimport DMRoomMap from \"../../../utils/DMRoomMap\";\nimport * as Email from \"../../../email\";\nimport { getDefaultIdentityServerUrl, setToDefaultIdentityServer } from \"../../../utils/IdentityServerUtils\";\nimport { buildActivityScores, buildMemberScores, compareMembers } from \"../../../utils/SortMembers\";\nimport { abbreviateUrl } from \"../../../utils/UrlUtils\";\nimport IdentityAuthClient from \"../../../IdentityAuthClient\";\nimport { type IInviteResult, inviteMultipleToRoom, showAnyInviteErrors } from \"../../../RoomInvite\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { DefaultTagID } from \"../../../stores/room-list/models\";\nimport RoomListStore from \"../../../stores/room-list/RoomListStore\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { UIFeature } from \"../../../settings/UIFeature\";\nimport { mediaFromMxc } from \"../../../customisations/Media\";\nimport BaseAvatar from \"../avatars/BaseAvatar\";\nimport { SearchResultAvatar } from \"../avatars/SearchResultAvatar\";\nimport AccessibleButton, { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport { selectText } from \"../../../utils/strings\";\nimport Field from \"../elements/Field\";\nimport TabbedView, { Tab, TabLocation } from \"../../structures/TabbedView\";\nimport Dialpad from \"../voip/DialPad\";\nimport QuestionDialog from \"./QuestionDialog\";\nimport BaseDialog from \"./BaseDialog\";\nimport DialPadBackspaceButton from \"../elements/DialPadBackspaceButton\";\nimport LegacyCallHandler from \"../../../LegacyCallHandler\";\nimport UserIdentifierCustomisations from \"../../../customisations/UserIdentifier\";\nimport CopyableText from \"../elements/CopyableText\";\nimport { type ScreenName } from \"../../../PosthogTrackers\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport {\n    DirectoryMember,\n    type IDMUserTileProps,\n    type Member,\n    startDmOnFirstMessage,\n    ThreepidMember,\n} from \"../../../utils/direct-messages\";\nimport { InviteKind } from \"./InviteDialogTypes\";\nimport Modal from \"../../../Modal\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { privateShouldBeEncrypted } from \"../../../utils/rooms\";\nimport { type NonEmptyArray } from \"../../../@types/common\";\nimport { UNKNOWN_PROFILE_ERRORS } from \"../../../utils/MultiInviter\";\nimport AskInviteAnywayDialog, { type UnknownProfiles } from \"./AskInviteAnywayDialog\";\nimport { SdkContextClass } from \"../../../contexts/SDKContext\";\nimport { type UserProfilesStore } from \"../../../stores/UserProfilesStore\";\nimport InviteProgressBody from \"./InviteProgressBody.tsx\";\n\n// we have a number of types defined from the Matrix spec which can't reasonably be altered here.\n/* eslint-disable camelcase */\n\nconst extractTargetUnknownProfiles = async (\n    targets: Member[],\n    profilesStores: UserProfilesStore,\n): Promise<UnknownProfiles> => {\n    const directoryMembers = targets.filter((t): t is DirectoryMember => t instanceof DirectoryMember);\n    await Promise.all(directoryMembers.map((t) => profilesStores.getOrFetchProfile(t.userId)));\n    return directoryMembers.reduce<UnknownProfiles>((unknownProfiles: UnknownProfiles, target: DirectoryMember) => {\n        const lookupError = profilesStores.getProfileLookupError(target.userId);\n\n        if (\n            lookupError instanceof MatrixError &&\n            lookupError.errcode &&\n            UNKNOWN_PROFILE_ERRORS.includes(lookupError.errcode)\n        ) {\n            unknownProfiles.push({\n                userId: target.userId,\n                errorText: lookupError.data.error || \"\",\n            });\n        }\n\n        return unknownProfiles;\n    }, []);\n};\n\ninterface Result {\n    userId: string;\n    user: Member;\n    lastActive?: number;\n}\n\nconst INITIAL_ROOMS_SHOWN = 3; // Number of rooms to show at first\nconst INCREMENT_ROOMS_SHOWN = 5; // Number of rooms to add when 'show more' is clicked\n\nenum TabId {\n    UserDirectory = \"users\",\n    DialPad = \"dialpad\",\n}\n\nclass DMUserTile extends React.PureComponent<IDMUserTileProps> {\n    private onRemove = (e: ButtonEvent): void => {\n        // Stop the browser from highlighting text\n        e.preventDefault();\n        e.stopPropagation();\n\n        this.props.onRemove!(this.props.member);\n    };\n\n    public render(): React.ReactNode {\n        const avatarSize = \"20px\";\n        const avatar = <SearchResultAvatar user={this.props.member} size={avatarSize} />;\n\n        return (\n            <Pill label={this.props.member.name} onClick={this.onRemove}>\n                {avatar}\n            </Pill>\n        );\n    }\n}\n\n/**\n * Converts a RoomMember to a Member.\n * Returns the Member if it is already a Member.\n */\nconst toMember = (member: RoomMember | Member): Member => {\n    return member instanceof RoomMember\n        ? new DirectoryMember({\n              user_id: member.userId,\n              display_name: member.name,\n              avatar_url: member.getMxcAvatarUrl(),\n          })\n        : member;\n};\n\ninterface IDMRoomTileProps {\n    member: Member;\n    lastActiveTs?: number;\n    onToggle(member: Member): void;\n    isSelected: boolean;\n}\n\nclass DMRoomTile extends React.PureComponent<IDMRoomTileProps> {\n    private onClick = (e: ButtonEvent): void => {\n        // Stop the browser from highlighting text\n        e.preventDefault();\n        e.stopPropagation();\n\n        this.props.onToggle(this.props.member);\n    };\n\n    public render(): React.ReactNode {\n        const avatarSize = \"32px\";\n        const avatar = (this.props.member as ThreepidMember).isEmail ? (\n            <EmailPillAvatarIcon width={avatarSize} height={avatarSize} />\n        ) : (\n            <BaseAvatar\n                url={\n                    this.props.member.getMxcAvatarUrl()\n                        ? mediaFromMxc(this.props.member.getMxcAvatarUrl()!).getSquareThumbnailHttp(\n                              parseInt(avatarSize, 10),\n                          )\n                        : null\n                }\n                name={this.props.member.name}\n                idName={this.props.member.userId}\n                size={avatarSize}\n            />\n        );\n\n        const userIdentifier = UserIdentifierCustomisations.getDisplayUserIdentifier(this.props.member.userId, {\n            withDisplayName: true,\n        });\n\n        const caption = (this.props.member as ThreepidMember).isEmail\n            ? _t(\"invite|email_caption\")\n            : userIdentifier || this.props.member.userId;\n\n        return (\n            <RichItem\n                avatar={avatar}\n                title={this.props.member.name}\n                description={caption}\n                timestamp={this.props.lastActiveTs}\n                onClick={this.onClick}\n                selected={this.props.isSelected}\n            />\n        );\n    }\n}\n\ninterface BaseProps {\n    // Takes a boolean which is true if a user / users were invited /\n    // a call transfer was initiated or false if the dialog was cancelled\n    // with no action taken.\n    onFinished: (success?: boolean) => void;\n\n    // Initial value to populate the filter with\n    initialText?: string;\n}\n\ninterface InviteDMProps extends BaseProps {\n    // The kind of invite being performed. Assumed to be InviteKind.Dm if not provided.\n    kind?: InviteKind.Dm;\n}\n\ninterface InviteRoomProps extends BaseProps {\n    kind: InviteKind.Invite;\n\n    // The room ID this dialog is for. Only required for InviteKind.Invite.\n    roomId: string;\n}\n\nfunction isRoomInvite(props: Props): props is InviteRoomProps {\n    return props.kind === InviteKind.Invite;\n}\n\ninterface InviteCallProps extends BaseProps {\n    kind: InviteKind.CallTransfer;\n\n    // The call to transfer. Only required for InviteKind.CallTransfer.\n    call: MatrixCall;\n}\n\ntype Props = InviteDMProps | InviteRoomProps | InviteCallProps;\n\ninterface IInviteDialogState {\n    targets: Member[]; // array of Member objects (see interface above)\n    filterText: string;\n    recents: Result[];\n    numRecentsShown: number;\n    suggestions: Result[];\n    numSuggestionsShown: number;\n    serverResultsMixin: Result[];\n    threepidResultsMixin: Result[];\n    canUseIdentityServer: boolean;\n    tryingIdentityServer: boolean;\n    consultFirst: boolean;\n    dialPadValue: string;\n    currentTabId: TabId;\n\n    /**\n     * True if we are sending the invites.\n     *\n     * We will grey out the action button, hide the suggestions, and display a spinner.\n     */\n    busy: boolean;\n\n    /** Error from the last attempt to send invites. */\n    errorText?: string;\n}\n\nexport default class InviteDialog extends React.PureComponent<Props, IInviteDialogState> {\n    public static defaultProps: Partial<Props> = {\n        kind: InviteKind.Dm,\n        initialText: \"\",\n    };\n\n    private debounceTimer: number | null = null; // actually number because we're in the browser\n    private editorRef = createRef<HTMLInputElement>();\n    private numberEntryFieldRef = createRef<Field>();\n    private unmounted = false;\n    private encryptionByDefault = false;\n    private profilesStore: UserProfilesStore;\n\n    public constructor(props: Props) {\n        super(props);\n\n        if (props.kind === InviteKind.Invite && !props.roomId) {\n            throw new Error(\"When using InviteKind.Invite a roomId is required for an InviteDialog\");\n        } else if (props.kind === InviteKind.CallTransfer && !props.call) {\n            throw new Error(\"When using InviteKind.CallTransfer a call is required for an InviteDialog\");\n        }\n\n        this.profilesStore = SdkContextClass.instance.userProfilesStore;\n        const cli = MatrixClientPeg.safeGet();\n\n        const excludedIds = new Set([cli.getSafeUserId()]);\n        if (isRoomInvite(props)) {\n            const room = cli.getRoom(props.roomId);\n            if (!room) throw new Error(\"Room ID given to InviteDialog does not look like a room\");\n            const isFederated = room?.currentState.getStateEvents(EventType.RoomCreate, \"\")?.getContent()[\"m.federate\"];\n            room.getMembersWithMembership(KnownMembership.Invite).forEach((m) => excludedIds.add(m.userId));\n            room.getMembersWithMembership(KnownMembership.Join).forEach((m) => excludedIds.add(m.userId));\n            // add banned users, so we don't try to invite them\n            room.getMembersWithMembership(KnownMembership.Ban).forEach((m) => excludedIds.add(m.userId));\n            const ourHomeserver = cli.getDomain();\n            if (isFederated === false && ourHomeserver) {\n                // If this room isn't federated, we must be on the same server.\n                // exclude users from external servers\n                this.excludeExternals(ourHomeserver, excludedIds);\n            }\n        }\n\n        this.state = {\n            targets: [], // array of Member objects (see interface above)\n            filterText: this.props.initialText || \"\",\n            // Mutates alreadyInvited set so that buildSuggestions doesn't duplicate any users\n            recents: InviteDialog.buildRecents(excludedIds),\n            numRecentsShown: INITIAL_ROOMS_SHOWN,\n            suggestions: this.buildSuggestions(excludedIds),\n            numSuggestionsShown: INITIAL_ROOMS_SHOWN,\n            serverResultsMixin: [],\n            threepidResultsMixin: [],\n            canUseIdentityServer: !!cli.getIdentityServerUrl(),\n            tryingIdentityServer: false,\n            consultFirst: false,\n            dialPadValue: \"\",\n            currentTabId: TabId.UserDirectory,\n\n            // These two flags are used for the 'Go' button to communicate what is going on.\n            busy: false,\n        };\n    }\n\n    public componentDidMount(): void {\n        this.unmounted = false;\n        this.encryptionByDefault = privateShouldBeEncrypted(MatrixClientPeg.safeGet());\n\n        if (this.props.initialText) {\n            this.updateSuggestions(this.props.initialText);\n        }\n    }\n\n    public componentWillUnmount(): void {\n        this.unmounted = true;\n    }\n\n    private onConsultFirstChange = (ev: React.ChangeEvent<HTMLInputElement>): void => {\n        this.setState({ consultFirst: ev.target.checked });\n    };\n\n    private excludeExternals(homeserver: string, excludedTargetIds: Set<string>): void {\n        const client = MatrixClientPeg.safeGet();\n        // users with room membership\n        const members = Object.values(buildMemberScores(client)).map(({ member }) => member.userId);\n        // users with dm membership\n        const roomMembers = Object.keys(DMRoomMap.shared().getUniqueRoomsWithIndividuals());\n        roomMembers.forEach((id) => members.push(id));\n        // filter duplicates and user IDs from external servers\n        const externals = new Set(members.filter((id) => !id.includes(homeserver)));\n        externals.forEach((id) => excludedTargetIds.add(id));\n    }\n\n    public static buildRecents(excludedTargetIds: Set<string>): Result[] {\n        const rooms = DMRoomMap.shared().getUniqueRoomsWithIndividuals(); // map of userId => js-sdk Room\n\n        // Also pull in all the rooms tagged as DefaultTagID.DM so we don't miss anything. Sometimes the\n        // room list doesn't tag the room for the DMRoomMap, but does for the room list.\n        const dmTaggedRooms = RoomListStore.instance.orderedLists[DefaultTagID.DM] || [];\n        const myUserId = MatrixClientPeg.safeGet().getUserId();\n        for (const dmRoom of dmTaggedRooms) {\n            const otherMembers = dmRoom.getJoinedMembers().filter((u) => u.userId !== myUserId);\n            for (const member of otherMembers) {\n                if (rooms[member.userId]) continue; // already have a room\n\n                logger.warn(`Adding DM room for ${member.userId} as ${dmRoom.roomId} from tag, not DM map`);\n                rooms[member.userId] = dmRoom;\n            }\n        }\n\n        const recents: {\n            userId: string;\n            user: Member;\n            lastActive: number;\n        }[] = [];\n\n        for (const userId in rooms) {\n            // Filter out user IDs that are already in the room / should be excluded\n            if (excludedTargetIds.has(userId)) {\n                logger.warn(`[Invite:Recents] Excluding ${userId} from recents`);\n                continue;\n            }\n\n            const room = rooms[userId];\n            const roomMember = room.getMember(userId);\n            if (!roomMember) {\n                // just skip people who don't have memberships for some reason\n                logger.warn(`[Invite:Recents] ${userId} is missing a member object in their own DM (${room.roomId})`);\n                continue;\n            }\n\n            // Find the last timestamp for a message event\n            const searchTypes = [\"m.room.message\", \"m.room.encrypted\", \"m.sticker\"];\n            const maxSearchEvents = 20; // to prevent traversing history\n            let lastEventTs = 0;\n            if (room.timeline && room.timeline.length) {\n                for (let i = room.timeline.length - 1; i >= 0; i--) {\n                    const ev = room.timeline[i];\n                    if (searchTypes.includes(ev.getType())) {\n                        lastEventTs = ev.getTs();\n                        break;\n                    }\n                    if (room.timeline.length - i > maxSearchEvents) break;\n                }\n            }\n            if (!lastEventTs) {\n                // something weird is going on with this room\n                logger.warn(`[Invite:Recents] ${userId} (${room.roomId}) has a weird last timestamp: ${lastEventTs}`);\n                continue;\n            }\n\n            recents.push({ userId, user: toMember(roomMember), lastActive: lastEventTs });\n            // We mutate the given set so that any later callers avoid duplicating these users\n            excludedTargetIds.add(userId);\n        }\n        if (recents.length === 0) logger.warn(\"[Invite:Recents] No recents to suggest!\");\n\n        // Sort the recents by last active to save us time later\n        recents.sort((a, b) => b.lastActive - a.lastActive);\n\n        return recents;\n    }\n\n    private buildSuggestions(excludedTargetIds: Set<string>): { userId: string; user: Member }[] {\n        const cli = MatrixClientPeg.safeGet();\n        const activityScores = buildActivityScores(cli);\n        const memberScores = buildMemberScores(cli);\n\n        const memberComparator = compareMembers(activityScores, memberScores);\n\n        return Object.values(memberScores)\n            .map(({ member }) => member)\n            .filter((member) => !excludedTargetIds.has(member.userId))\n            .sort(memberComparator)\n            .map((member) => ({ userId: member.userId, user: toMember(member) }));\n    }\n\n    private shouldAbortAfterInviteError(result: IInviteResult, room: Room): boolean {\n        this.setState({ busy: false });\n        const userMap = new Map<string, Member>(this.state.targets.map((member) => [member.userId, member]));\n        return !showAnyInviteErrors(result.states, room, result.inviter, userMap);\n    }\n\n    private convertFilter(): Member[] {\n        // Check to see if there's anything to convert first\n        if (!this.state.filterText || !this.state.filterText.includes(\"@\")) return this.state.targets || [];\n\n        if (!this.canInviteMore()) {\n            // There should only be one third-party invite → do not allow more targets\n            return this.state.targets;\n        }\n\n        let newMember: Member | undefined;\n        if (this.state.filterText.startsWith(\"@\")) {\n            // Assume mxid\n            newMember = new DirectoryMember({ user_id: this.state.filterText });\n        } else if (SettingsStore.getValue(UIFeature.IdentityServer)) {\n            // Assume email\n            if (this.canInviteThirdParty()) {\n                newMember = new ThreepidMember(this.state.filterText);\n            }\n        }\n        if (!newMember) return this.state.targets;\n\n        const newTargets = [...(this.state.targets || []), newMember];\n        this.setState({ targets: newTargets, filterText: \"\" });\n        return newTargets;\n    }\n\n    /**\n     * Check if there are unknown profiles if promptBeforeInviteUnknownUsers setting is enabled.\n     * If so show the \"invite anyway?\" dialog. Otherwise directly create the DM local room.\n     */\n    private checkProfileAndStartDm = async (): Promise<void> => {\n        this.setBusy(true);\n        const targets = this.convertFilter();\n\n        if (SettingsStore.getValue(\"promptBeforeInviteUnknownUsers\")) {\n            const unknownProfileUsers = await extractTargetUnknownProfiles(targets, this.profilesStore);\n\n            if (unknownProfileUsers.length) {\n                this.showAskInviteAnywayDialog(unknownProfileUsers);\n                return;\n            }\n        }\n\n        await this.startDm();\n    };\n\n    private startDm = async (): Promise<void> => {\n        this.setBusy(true);\n\n        try {\n            const cli = MatrixClientPeg.safeGet();\n            const targets = this.convertFilter();\n            await startDmOnFirstMessage(cli, targets);\n            this.props.onFinished(true);\n        } catch (err) {\n            logger.error(err);\n            this.setState({\n                busy: false,\n                errorText: _t(\"invite|error_dm\"),\n            });\n        }\n    };\n\n    private setBusy(busy: boolean): void {\n        this.setState({\n            busy,\n        });\n    }\n\n    private showAskInviteAnywayDialog(unknownProfileUsers: { userId: string; errorText: string }[]): void {\n        Modal.createDialog(AskInviteAnywayDialog, {\n            unknownProfileUsers,\n            onInviteAnyways: () => this.startDm(),\n            onGiveUp: () => {\n                this.setBusy(false);\n            },\n            description: _t(\"invite|ask_anyway_description\"),\n            inviteNeverWarnLabel: _t(\"invite|ask_anyway_never_warn_label\"),\n            inviteLabel: _t(\"invite|ask_anyway_label\"),\n        });\n    }\n\n    private inviteUsers = async (): Promise<void> => {\n        if (this.props.kind !== InviteKind.Invite) return;\n        this.setState({ busy: true });\n        this.convertFilter();\n        const targets = this.convertFilter();\n        const targetIds = targets.map((t) => t.userId);\n\n        const cli = MatrixClientPeg.safeGet();\n        const room = cli.getRoom(this.props.roomId);\n        if (!room) {\n            logger.error(\"Failed to find the room to invite users to\");\n            this.setState({\n                busy: false,\n                errorText: _t(\"invite|error_find_room\"),\n            });\n            return;\n        }\n\n        try {\n            const result = await inviteMultipleToRoom(cli, this.props.roomId, targetIds, {\n                // We show our own progress body, so don't pop up a separate dialog.\n                inhibitProgressDialog: true,\n            });\n            if (!this.shouldAbortAfterInviteError(result, room)) {\n                // handles setting error message too\n                this.props.onFinished(true);\n            }\n        } catch (err) {\n            logger.error(err);\n            this.setState({\n                busy: false,\n                errorText: _t(\"invite|error_invite\"),\n            });\n        }\n    };\n\n    private transferCall = async (): Promise<void> => {\n        if (this.props.kind !== InviteKind.CallTransfer) return;\n        if (this.state.currentTabId == TabId.UserDirectory) {\n            this.convertFilter();\n            const targets = this.convertFilter();\n            const targetIds = targets.map((t) => t.userId);\n            if (targetIds.length > 1) {\n                this.setState({\n                    errorText: _t(\"invite|error_transfer_multiple_target\"),\n                });\n                return;\n            }\n\n            LegacyCallHandler.instance.startTransferToMatrixID(this.props.call, targetIds[0], this.state.consultFirst);\n        } else {\n            LegacyCallHandler.instance.startTransferToPhoneNumber(\n                this.props.call,\n                this.state.dialPadValue,\n                this.state.consultFirst,\n            );\n        }\n        this.props.onFinished(true);\n    };\n\n    private onKeyDown = (e: React.KeyboardEvent<HTMLInputElement>): void => {\n        if (this.state.busy) return;\n\n        let handled = false;\n        const value = e.currentTarget.value.trim();\n        const action = getKeyBindingsManager().getAccessibilityAction(e);\n\n        switch (action) {\n            case KeyBindingAction.Space:\n                if (!value || !value.includes(\"@\") || value.includes(\" \")) break;\n\n                // when the user hits space and their input looks like an e-mail/MXID then try to convert it\n                this.convertFilter();\n                handled = true;\n                break;\n            case KeyBindingAction.Enter:\n                if (!value) break;\n\n                // when the user hits enter with something in their field try to convert it\n                this.convertFilter();\n                handled = true;\n                break;\n        }\n\n        if (handled) {\n            e.preventDefault();\n        }\n    };\n\n    private onCancel = (): void => {\n        this.props.onFinished(false);\n    };\n\n    private updateSuggestions = async (term: string): Promise<void> => {\n        MatrixClientPeg.safeGet()\n            .searchUserDirectory({ term })\n            .then(async (r): Promise<void> => {\n                if (term !== this.state.filterText) {\n                    // Discard the results - we were probably too slow on the server-side to make\n                    // these results useful. This is a race we want to avoid because we could overwrite\n                    // more accurate results.\n                    return;\n                }\n\n                if (!r.results) r.results = [];\n\n                // While we're here, try and autocomplete a search result for the mxid itself\n                // if there's no matches (and the input looks like a mxid).\n                if (term[0] === \"@\" && term.indexOf(\":\") > 1) {\n                    try {\n                        const profile = await this.profilesStore.getOrFetchProfile(term, { shouldThrow: true });\n\n                        if (profile) {\n                            // If we have a profile, we have enough information to assume that\n                            // the mxid can be invited - add it to the list. We stick it at the\n                            // top so it is most obviously presented to the user.\n                            r.results.splice(0, 0, {\n                                user_id: term,\n                                display_name: profile[\"displayname\"],\n                                avatar_url: profile[\"avatar_url\"],\n                            });\n                        }\n                    } catch (e) {\n                        logger.warn(\"Non-fatal error trying to make an invite for a user ID\", e);\n                    }\n                }\n\n                this.setState({\n                    serverResultsMixin: r.results.map((u) => ({\n                        userId: u.user_id,\n                        user: new DirectoryMember(u),\n                    })),\n                });\n            })\n            .catch((e) => {\n                logger.error(\"Error searching user directory:\");\n                logger.error(e);\n                this.setState({ serverResultsMixin: [] }); // clear results because it's moderately fatal\n            });\n\n        // Whenever we search the directory, also try to search the identity server. It's\n        // all debounced the same anyways.\n        if (!this.state.canUseIdentityServer) {\n            // The user doesn't have an identity server set - warn them of that.\n            this.setState({ tryingIdentityServer: true });\n            return;\n        }\n        if (Email.looksValid(term) && this.canInviteThirdParty() && SettingsStore.getValue(UIFeature.IdentityServer)) {\n            // Start off by suggesting the plain email while we try and resolve it\n            // to a real account.\n            this.setState({\n                // per above: the userId is a lie here - it's just a regular identifier\n                threepidResultsMixin: [{ user: new ThreepidMember(term), userId: term }],\n            });\n            try {\n                const authClient = new IdentityAuthClient();\n                const token = await authClient.getAccessToken();\n                // No token → unable to try a lookup\n                if (!token) return;\n\n                if (term !== this.state.filterText) return; // abandon hope\n\n                const lookup = await MatrixClientPeg.safeGet().lookupThreePid(\"email\", term, token);\n                if (term !== this.state.filterText) return; // abandon hope\n\n                if (!lookup || !(\"mxid\" in lookup)) {\n                    // We weren't able to find anyone - we're already suggesting the plain email\n                    // as an alternative, so do nothing.\n                    return;\n                }\n\n                // We append the user suggestion to give the user an option to click\n                // the email anyways, and so we don't cause things to jump around. In\n                // theory, the user would see the user pop up and think \"ah yes, that\n                // person!\"\n                const profile = await this.profilesStore.getOrFetchProfile(lookup.mxid);\n                if (term !== this.state.filterText || !profile) return; // abandon hope\n                this.setState({\n                    threepidResultsMixin: [\n                        ...this.state.threepidResultsMixin,\n                        {\n                            user: new DirectoryMember({\n                                user_id: lookup.mxid,\n                                display_name: profile.displayname,\n                                avatar_url: profile.avatar_url,\n                            }),\n                            // Use the search term as identifier, so that it shows up in suggestions.\n                            userId: term,\n                        },\n                    ],\n                });\n            } catch (e) {\n                logger.error(\"Error searching identity server:\");\n                logger.error(e);\n                this.setState({ threepidResultsMixin: [] }); // clear results because it's moderately fatal\n            }\n        }\n    };\n\n    private updateFilter = (e: React.ChangeEvent<HTMLInputElement>): void => {\n        const term = e.target.value;\n        this.setState({ filterText: term });\n\n        // Debounce server lookups to reduce spam. We don't clear the existing server\n        // results because they might still be vaguely accurate, likewise for races which\n        // could happen here.\n        if (this.debounceTimer) {\n            clearTimeout(this.debounceTimer);\n        }\n        this.debounceTimer = window.setTimeout(() => {\n            this.updateSuggestions(term);\n        }, 150); // 150ms debounce (human reaction time + some)\n    };\n\n    private showMoreRecents = (): void => {\n        this.setState({ numRecentsShown: this.state.numRecentsShown + INCREMENT_ROOMS_SHOWN });\n    };\n\n    private showMoreSuggestions = (): void => {\n        this.setState({ numSuggestionsShown: this.state.numSuggestionsShown + INCREMENT_ROOMS_SHOWN });\n    };\n\n    private toggleMember = (member: Member): void => {\n        if (!this.state.busy) {\n            let filterText = this.state.filterText;\n            let targets = this.state.targets.map((t) => t); // cheap clone for mutation\n            const idx = targets.findIndex((m) => m.userId === member.userId);\n            if (idx >= 0) {\n                targets.splice(idx, 1);\n            } else {\n                if (this.props.kind === InviteKind.CallTransfer && targets.length > 0) {\n                    targets = [];\n                }\n                targets.push(member);\n                filterText = \"\"; // clear the filter when the user accepts a suggestion\n            }\n            this.setState({ targets, filterText });\n\n            if (this.editorRef && this.editorRef.current) {\n                this.editorRef.current.focus();\n            }\n        }\n    };\n\n    private removeMember = (member: Member): void => {\n        const targets = this.state.targets.map((t) => t); // cheap clone for mutation\n        const idx = targets.indexOf(member);\n        if (idx >= 0) {\n            targets.splice(idx, 1);\n            this.setState({ targets });\n        }\n\n        if (this.editorRef && this.editorRef.current) {\n            this.editorRef.current.focus();\n        }\n    };\n\n    private parseFilter(filter: string): string[] {\n        return filter\n            .split(/[\\s,]+/)\n            .map((p) => p.trim())\n            .filter((p) => !!p); // filter empty strings\n    }\n\n    private onPaste = async (e: React.ClipboardEvent): Promise<void> => {\n        if (this.state.filterText) {\n            // if the user has already typed something, just let them\n            // paste normally.\n            return;\n        }\n\n        const text = e.clipboardData.getData(\"text\");\n        const potentialAddresses = this.parseFilter(text);\n        // one search term which is not a mxid or email address\n        if (potentialAddresses.length === 1 && !potentialAddresses[0].includes(\"@\")) {\n            return;\n        }\n\n        // Prevent the text being pasted into the input\n        e.preventDefault();\n\n        // Process it as a list of addresses to add instead\n        const possibleMembers = [\n            // If we can avoid hitting the profile endpoint, we should.\n            ...this.state.recents,\n            ...this.state.suggestions,\n            ...this.state.serverResultsMixin,\n            ...this.state.threepidResultsMixin,\n        ];\n        const toAdd: Member[] = [];\n        const failed: string[] = [];\n\n        // Addresses that could not be added.\n        // Will be displayed as filter text to provide feedback.\n        const unableToAddMore: string[] = [];\n\n        for (const address of potentialAddresses) {\n            const member = possibleMembers.find((m) => m.userId === address);\n            if (member) {\n                if (this.canInviteMore([...this.state.targets, ...toAdd])) {\n                    toAdd.push(member.user);\n                } else {\n                    // Invite not possible for current targets and pasted targets.\n                    unableToAddMore.push(address);\n                }\n                continue;\n            }\n\n            if (Email.looksValid(address)) {\n                if (this.canInviteThirdParty([...this.state.targets, ...toAdd])) {\n                    toAdd.push(new ThreepidMember(address));\n                } else {\n                    // Third-party invite not possible for current targets and pasted targets.\n                    unableToAddMore.push(address);\n                }\n                continue;\n            }\n\n            if (address[0] !== \"@\") {\n                failed.push(address); // not a user ID\n                continue;\n            }\n\n            try {\n                const profile = await this.profilesStore.getOrFetchProfile(address);\n                toAdd.push(\n                    new DirectoryMember({\n                        user_id: address,\n                        display_name: profile?.displayname,\n                        avatar_url: profile?.avatar_url,\n                    }),\n                );\n            } catch (e) {\n                logger.error(\"Error looking up profile for \" + address);\n                logger.error(e);\n                failed.push(address);\n            }\n        }\n        if (this.unmounted) return;\n\n        if (failed.length > 0) {\n            Modal.createDialog(QuestionDialog, {\n                title: _t(\"invite|error_find_user_title\"),\n                description: _t(\"invite|error_find_user_description\", { csvNames: failed.join(\", \") }),\n                button: _t(\"action|ok\"),\n            });\n        }\n\n        if (unableToAddMore) {\n            this.setState({\n                filterText: unableToAddMore.join(\" \"),\n                targets: uniqBy([...this.state.targets, ...toAdd], (t) => t.userId),\n            });\n        } else {\n            this.setState({\n                targets: uniqBy([...this.state.targets, ...toAdd], (t) => t.userId),\n            });\n        }\n    };\n\n    private onUseDefaultIdentityServerClick = (e: ButtonEvent): void => {\n        e.preventDefault();\n\n        // Update the IS in account data. Actually using it may trigger terms.\n        // eslint-disable-next-line react-hooks/rules-of-hooks\n        setToDefaultIdentityServer(MatrixClientPeg.safeGet());\n        this.setState({ canUseIdentityServer: true, tryingIdentityServer: false });\n    };\n\n    private onManageSettingsClick = (e: ButtonEvent): void => {\n        e.preventDefault();\n        dis.fire(Action.ViewUserSettings);\n        this.props.onFinished(false);\n    };\n\n    private renderSection(kind: \"recents\" | \"suggestions\"): ReactNode {\n        let sourceMembers = kind === \"recents\" ? this.state.recents : this.state.suggestions;\n        let showNum = kind === \"recents\" ? this.state.numRecentsShown : this.state.numSuggestionsShown;\n        const showMoreFn = kind === \"recents\" ? this.showMoreRecents.bind(this) : this.showMoreSuggestions.bind(this);\n        const lastActive = (m: Result): number | undefined => (kind === \"recents\" ? m.lastActive : undefined);\n        let sectionName = kind === \"recents\" ? _t(\"invite|recents_section\") : _t(\"common|suggestions\");\n\n        if (this.props.kind === InviteKind.Invite) {\n            sectionName = kind === \"recents\" ? _t(\"invite|suggestions_section\") : _t(\"common|suggestions\");\n        }\n\n        // Mix in the server results if we have any, but only if we're searching. We track the additional\n        // members separately because we want to filter sourceMembers but trust the mixin arrays to have\n        // the right members in them.\n        let priorityAdditionalMembers: Result[] = []; // Shows up before our own suggestions, higher quality\n        let otherAdditionalMembers: Result[] = []; // Shows up after our own suggestions, lower quality\n        const hasMixins = this.state.serverResultsMixin || this.state.threepidResultsMixin;\n        if (this.state.filterText && hasMixins && kind === \"suggestions\") {\n            // We don't want to duplicate members though, so just exclude anyone we've already seen.\n            // The type of u is a pain to define but members of both mixins have the 'userId' property\n            const notAlreadyExists = (u: any): boolean => {\n                return (\n                    !this.state.recents.some((m) => m.userId === u.userId) &&\n                    !sourceMembers.some((m) => m.userId === u.userId) &&\n                    !priorityAdditionalMembers.some((m) => m.userId === u.userId) &&\n                    !otherAdditionalMembers.some((m) => m.userId === u.userId)\n                );\n            };\n\n            otherAdditionalMembers = this.state.serverResultsMixin.filter(notAlreadyExists);\n            priorityAdditionalMembers = this.state.threepidResultsMixin.filter(notAlreadyExists);\n        }\n        const hasAdditionalMembers = priorityAdditionalMembers.length > 0 || otherAdditionalMembers.length > 0;\n\n        // Hide the section if there's nothing to filter by\n        if (sourceMembers.length === 0 && !hasAdditionalMembers) return null;\n\n        if (!this.canInviteThirdParty()) {\n            // It is currently not allowed to add more third-party invites. Filter them out.\n            priorityAdditionalMembers = priorityAdditionalMembers.filter((s) => s instanceof ThreepidMember);\n        }\n\n        // Do some simple filtering on the input before going much further. If we get no results, say so.\n        if (this.state.filterText) {\n            const filterBy = this.state.filterText.toLowerCase();\n            sourceMembers = sourceMembers.filter(\n                (m) => m.user.name.toLowerCase().includes(filterBy) || m.userId.toLowerCase().includes(filterBy),\n            );\n\n            if (sourceMembers.length === 0 && !hasAdditionalMembers) {\n                return (\n                    <div className=\"mx_InviteDialog_section\">\n                        <RichList\n                            title={sectionName}\n                            titleAttributes={{ \"role\": \"heading\", \"aria-level\": 3 }}\n                            isEmpty={true}\n                        >\n                            {_t(\"common|no_results\")}\n                        </RichList>\n                    </div>\n                );\n            }\n        }\n\n        // Now we mix in the additional members. Again, we presume these have already been filtered. We\n        // also assume they are more relevant than our suggestions and prepend them to the list.\n        sourceMembers = [...priorityAdditionalMembers, ...sourceMembers, ...otherAdditionalMembers];\n\n        // If we're going to hide one member behind 'show more', just use up the space of the button\n        // with the member's tile instead.\n        if (showNum === sourceMembers.length - 1) showNum++;\n\n        // .slice() will return an incomplete array but won't error on us if we go too far\n        const toRender = sourceMembers.slice(0, showNum);\n        const hasMore = toRender.length < sourceMembers.length;\n\n        let showMore: JSX.Element | undefined;\n        if (hasMore) {\n            showMore = (\n                <div className=\"mx_InviteDialog_section_showMore\">\n                    <AccessibleButton onClick={showMoreFn} kind=\"link\">\n                        {_t(\"common|show_more\")}\n                    </AccessibleButton>\n                </div>\n            );\n        }\n\n        const tiles = toRender.map((r) => (\n            <DMRoomTile\n                member={r.user}\n                lastActiveTs={lastActive(r)}\n                key={r.user.userId}\n                onToggle={this.toggleMember}\n                isSelected={this.state.targets.some((t) => t.userId === r.userId)}\n            />\n        ));\n\n        return (\n            <div className=\"mx_InviteDialog_section\">\n                <RichList title={sectionName} titleAttributes={{ \"role\": \"heading\", \"aria-level\": 3 }}>\n                    {tiles}\n                </RichList>\n                {showMore}\n            </div>\n        );\n    }\n\n    private renderEditor(): JSX.Element {\n        const targets = this.state.targets.map((t) => (\n            <DMUserTile member={t} onRemove={this.state.busy ? undefined : this.removeMember} key={t.userId} />\n        ));\n\n        return (\n            <PillInput\n                data-testid=\"invite-dialog-input-wrapper\"\n                className=\"mx_InviteDialog_editor\"\n                inputProps={{\n                    \"ref\": this.editorRef,\n                    \"value\": this.state.filterText,\n                    \"onKeyDown\": this.onKeyDown,\n                    \"onChange\": this.updateFilter,\n                    \"onPaste\": this.onPaste,\n                    \"placeholder\": _t(\"action|search\"),\n                    \"autoFocus\": true,\n                    \"disabled\":\n                        this.state.busy ||\n                        (this.props.kind == InviteKind.CallTransfer && this.state.targets.length > 0),\n                    \"data-testid\": \"invite-dialog-input\",\n                }}\n                onRemoveChildren={() =>\n                    !this.state.busy && this.removeMember(this.state.targets[this.state.targets.length - 1])\n                }\n            >\n                {targets}\n            </PillInput>\n        );\n    }\n\n    private renderIdentityServerWarning(): ReactNode {\n        if (\n            !this.state.tryingIdentityServer ||\n            this.state.canUseIdentityServer ||\n            !SettingsStore.getValue(UIFeature.IdentityServer)\n        ) {\n            return null;\n        }\n\n        const defaultIdentityServerUrl = getDefaultIdentityServerUrl();\n        if (defaultIdentityServerUrl) {\n            return (\n                <div className=\"mx_InviteDialog_identityServer\">\n                    {_t(\n                        \"invite|email_use_default_is\",\n                        {\n                            defaultIdentityServerName: abbreviateUrl(defaultIdentityServerUrl),\n                        },\n                        {\n                            default: (sub) => (\n                                <AccessibleButton kind=\"link_inline\" onClick={this.onUseDefaultIdentityServerClick}>\n                                    {sub}\n                                </AccessibleButton>\n                            ),\n                            settings: (sub) => (\n                                <AccessibleButton kind=\"link_inline\" onClick={this.onManageSettingsClick}>\n                                    {sub}\n                                </AccessibleButton>\n                            ),\n                        },\n                    )}\n                </div>\n            );\n        } else {\n            return (\n                <div className=\"mx_InviteDialog_identityServer\">\n                    {_t(\n                        \"invite|email_use_is\",\n                        {},\n                        {\n                            settings: (sub) => (\n                                <AccessibleButton kind=\"link_inline\" onClick={this.onManageSettingsClick}>\n                                    {sub}\n                                </AccessibleButton>\n                            ),\n                        },\n                    )}\n                </div>\n            );\n        }\n    }\n\n    private onDialFormSubmit = (ev: SyntheticEvent): void => {\n        ev.preventDefault();\n        this.transferCall();\n    };\n\n    private onDialChange = (ev: React.ChangeEvent<HTMLInputElement>): void => {\n        this.setState({ dialPadValue: ev.currentTarget.value });\n    };\n\n    private onDigitPress = (digit: string, ev: ButtonEvent): void => {\n        this.setState({ dialPadValue: this.state.dialPadValue + digit });\n\n        // Keep the number field focused so that keyboard entry is still available\n        // However, don't focus if this wasn't the result of directly clicking on the button,\n        // i.e someone using keyboard navigation.\n        if (ev.type === \"click\") {\n            this.numberEntryFieldRef.current?.focus();\n        }\n    };\n\n    private onDeletePress = (ev: ButtonEvent): void => {\n        if (this.state.dialPadValue.length === 0) return;\n        this.setState({ dialPadValue: this.state.dialPadValue.slice(0, -1) });\n\n        // Keep the number field focused so that keyboard entry is still available\n        // However, don't focus if this wasn't the result of directly clicking on the button,\n        // i.e someone using keyboard navigation.\n        if (ev.type === \"click\") {\n            this.numberEntryFieldRef.current?.focus();\n        }\n    };\n\n    private onTabChange = (tabId: TabId): void => {\n        this.setState({ currentTabId: tabId });\n    };\n\n    private async onLinkClick(e: React.MouseEvent<HTMLAnchorElement>): Promise<void> {\n        e.preventDefault();\n        selectText(e.currentTarget);\n    }\n\n    private get screenName(): ScreenName | undefined {\n        switch (this.props.kind) {\n            case InviteKind.Dm:\n                return \"StartChat\";\n            default:\n                return undefined;\n        }\n    }\n\n    /**\n     * If encryption by default is enabled, third-party invites should be encrypted as well.\n     * For encryption to work, the other side requires a device.\n     * To achieve this Element implements a waiting room until all have joined.\n     * Waiting for many users degrades the UX → only one email invite is allowed at a time.\n     *\n     * @param targets - Optional member list to check. Uses targets from state if not provided.\n     */\n    private canInviteMore(targets?: (Member | RoomMember)[]): boolean {\n        targets = targets || this.state.targets;\n        return this.canInviteThirdParty(targets) || !targets.some((t) => t instanceof ThreepidMember);\n    }\n\n    /**\n     * A third-party invite is possible if\n     * - this is a non-DM dialog or\n     * - there are no invites yet or\n     * - encryption by default is not enabled\n     *\n     * Also see {@link InviteDialog#canInviteMore}.\n     *\n     * @param targets - Optional member list to check. Uses targets from state if not provided.\n     */\n    private canInviteThirdParty(targets?: (Member | RoomMember)[]): boolean {\n        targets = targets || this.state.targets;\n        return this.props.kind !== InviteKind.Dm || targets.length === 0 || !this.encryptionByDefault;\n    }\n\n    private hasFilterAtLeastOneEmail(): boolean {\n        if (!this.state.filterText) return false;\n\n        return this.parseFilter(this.state.filterText).some((address: string) => {\n            return Email.looksValid(address);\n        });\n    }\n\n    private hasSelection(): boolean {\n        return this.state.targets.length > 0 || (!!this.state.filterText && this.state.filterText.includes(\"@\"));\n    }\n\n    /**\n     * Render the \"suggestions\" section, which shows a list of people you might want to invite, together with any\n     * errors from the previous iteration.\n     */\n    private renderSuggestions(): JSX.Element {\n        // If we're starting a DM, add a footer which showing our matrix.to link, for copying & pasting.\n        let footer;\n        if (this.props.kind === InviteKind.Dm) {\n            const link = makeUserPermalink(MatrixClientPeg.safeGet().getSafeUserId());\n            footer = (\n                <div className=\"mx_InviteDialog_footer\">\n                    <h3>{_t(\"invite|send_link_prompt\")}</h3>\n                    <CopyableText getTextToCopy={() => makeUserPermalink(MatrixClientPeg.safeGet().getSafeUserId())}>\n                        <a className=\"mx_InviteDialog_footer_link\" href={link} onClick={this.onLinkClick}>\n                            {link}\n                        </a>\n                    </CopyableText>\n                </div>\n            );\n        }\n\n        let results: React.ReactNode | null = null;\n        let onlyOneThreepidNote: React.ReactNode | null = null;\n\n        if (!this.canInviteMore() || (this.hasFilterAtLeastOneEmail() && !this.canInviteThirdParty())) {\n            // We are in DM case here, because of the checks in canInviteMore() / canInviteThirdParty().\n            // Show a note saying \"Invites by email can only be sent one at a time\".\n            onlyOneThreepidNote = <div className=\"mx_InviteDialog_oneThreepid\">{_t(\"invite|email_limit_one\")}</div>;\n        } else {\n            let extraSection;\n            if (this.props.kind === InviteKind.Dm) {\n                // Some extra words saying \"Some suggestions may be hidden for privacy\"\n                extraSection = (\n                    <div className=\"mx_InviteDialog_section_hidden_suggestions_disclaimer\">\n                        <span>{_t(\"invite|suggestions_disclaimer\")}</span>\n                        <p>{_t(\"invite|suggestions_disclaimer_prompt\")}</p>\n                    </div>\n                );\n            }\n\n            results = (\n                <div className=\"mx_InviteDialog_userSections\">\n                    {this.renderSection(\"recents\")}\n                    {this.renderSection(\"suggestions\")}\n                    {extraSection}\n                </div>\n            );\n        }\n\n        return (\n            <React.Fragment>\n                {this.renderIdentityServerWarning()}\n                <div className=\"error\">{this.state.errorText}</div>\n                {onlyOneThreepidNote}\n                {results}\n                {footer}\n            </React.Fragment>\n        );\n    }\n\n    /**\n     * Render content of the common \"users\" tab that is shown whether we have a regular invite dialog or a\n     * \"CallTransfer\" one.\n     */\n    private renderMainTab(): JSX.Element {\n        let helpText;\n        let buttonText;\n        let goButtonFn: (() => Promise<void>) | null = null;\n\n        const identityServersEnabled = SettingsStore.getValue(UIFeature.IdentityServer);\n\n        const cli = MatrixClientPeg.safeGet();\n        const userId = cli.getUserId()!;\n        if (this.props.kind === InviteKind.Dm) {\n            if (identityServersEnabled) {\n                helpText = _t(\n                    \"invite|start_conversation_name_email_mxid_prompt\",\n                    {},\n                    {\n                        userId: () => {\n                            return (\n                                <a href={makeUserPermalink(userId)} rel=\"noreferrer noopener\" target=\"_blank\">\n                                    {userId}\n                                </a>\n                            );\n                        },\n                    },\n                );\n            } else {\n                helpText = _t(\n                    \"invite|start_conversation_name_mxid_prompt\",\n                    {},\n                    {\n                        userId: () => {\n                            return (\n                                <a href={makeUserPermalink(userId)} rel=\"noreferrer noopener\" target=\"_blank\">\n                                    {userId}\n                                </a>\n                            );\n                        },\n                    },\n                );\n            }\n\n            buttonText = _t(\"action|go\");\n            goButtonFn = this.checkProfileAndStartDm;\n        } else if (this.props.kind === InviteKind.Invite) {\n            const roomId = this.props.roomId;\n            const room = MatrixClientPeg.get()?.getRoom(roomId);\n            const isSpace = room?.isSpaceRoom();\n\n            let helpTextUntranslated;\n            if (isSpace) {\n                if (identityServersEnabled) {\n                    helpTextUntranslated = _td(\"invite|name_email_mxid_share_space\");\n                } else {\n                    helpTextUntranslated = _td(\"invite|name_mxid_share_space\");\n                }\n            } else {\n                if (identityServersEnabled) {\n                    helpTextUntranslated = _td(\"invite|name_email_mxid_share_room\");\n                } else {\n                    helpTextUntranslated = _td(\"invite|name_mxid_share_room\");\n                }\n            }\n\n            helpText = _t(\n                helpTextUntranslated,\n                {},\n                {\n                    userId: () => (\n                        <a\n                            className=\"mx_InviteDialog_helpText_userId\"\n                            href={makeUserPermalink(userId)}\n                            rel=\"noreferrer noopener\"\n                            target=\"_blank\"\n                        >\n                            {userId}\n                        </a>\n                    ),\n                    a: (sub) => (\n                        <a href={makeRoomPermalink(cli, roomId)} rel=\"noreferrer noopener\" target=\"_blank\">\n                            {sub}\n                        </a>\n                    ),\n                },\n            );\n\n            buttonText = _t(\"action|invite\");\n            goButtonFn = this.inviteUsers;\n        }\n\n        const goButton =\n            this.props.kind == InviteKind.CallTransfer ? null : (\n                <AccessibleButton\n                    kind=\"primary\"\n                    onClick={goButtonFn}\n                    className=\"mx_InviteDialog_goButton\"\n                    disabled={this.state.busy || !this.hasSelection()}\n                >\n                    {buttonText}\n                </AccessibleButton>\n            );\n\n        return (\n            <React.Fragment>\n                <p className=\"mx_InviteDialog_helpText\">{helpText}</p>\n                <div className=\"mx_InviteDialog_addressBar\">\n                    {this.renderEditor()}\n                    {goButton}\n                </div>\n                {this.state.busy ? <InviteProgressBody /> : this.renderSuggestions()}\n            </React.Fragment>\n        );\n    }\n\n    /**\n     * Render the complete dialog, given this is not a call transfer dialog.\n     *\n     * See also: {@link renderCallTransferDialog}.\n     */\n    private renderRegularDialog(): React.ReactNode {\n        let title;\n        if (this.props.kind === InviteKind.Dm) {\n            title = _t(\"space|add_existing_room_space|dm_heading\");\n        } else if (this.props.kind === InviteKind.Invite) {\n            const roomId = this.props.roomId;\n            const room = MatrixClientPeg.get()?.getRoom(roomId);\n            const isSpace = room?.isSpaceRoom();\n            title = isSpace\n                ? _t(\"invite|to_space\", {\n                      spaceName: room?.name || _t(\"common|unnamed_space\"),\n                  })\n                : _t(\"invite|to_room\", {\n                      roomName: room?.name || _t(\"common|unnamed_room\"),\n                  });\n        }\n\n        return (\n            <BaseDialog\n                className=\"mx_InviteDialog_other\"\n                hasCancel={true}\n                onFinished={this.props.onFinished}\n                title={title}\n                screenName={this.screenName}\n            >\n                <div className=\"mx_InviteDialog_content\">{this.renderMainTab()}</div>\n            </BaseDialog>\n        );\n    }\n\n    /**\n     * Render the complete call transfer dialog.\n     *\n     * See also: {@link renderRegularDialog}.\n     */\n    private renderCallTransferDialog(): React.ReactNode {\n        const usersSection = this.renderMainTab();\n\n        const tabs: NonEmptyArray<Tab<TabId>> = [\n            new Tab(\n                TabId.UserDirectory,\n                _td(\"invite|transfer_user_directory_tab\"),\n                <UserProfileSolidIcon />,\n                usersSection,\n            ),\n        ];\n\n        const backspaceButton = <DialPadBackspaceButton onBackspacePress={this.onDeletePress} />;\n\n        // Only show the backspace button if the field has content\n        let dialPadField;\n        if (this.state.dialPadValue.length !== 0) {\n            dialPadField = (\n                <Field\n                    ref={this.numberEntryFieldRef}\n                    className=\"mx_InviteDialog_dialPadField\"\n                    id=\"dialpad_number\"\n                    value={this.state.dialPadValue}\n                    autoFocus={true}\n                    onChange={this.onDialChange}\n                    postfixComponent={backspaceButton}\n                />\n            );\n        } else {\n            dialPadField = (\n                <Field\n                    ref={this.numberEntryFieldRef}\n                    className=\"mx_InviteDialog_dialPadField\"\n                    id=\"dialpad_number\"\n                    value={this.state.dialPadValue}\n                    autoFocus={true}\n                    onChange={this.onDialChange}\n                />\n            );\n        }\n\n        const dialPadSection = (\n            <div className=\"mx_InviteDialog_dialPad\">\n                <form onSubmit={this.onDialFormSubmit}>{dialPadField}</form>\n                <Dialpad hasDial={false} onDigitPress={this.onDigitPress} onDeletePress={this.onDeletePress} />\n            </div>\n        );\n        tabs.push(new Tab(TabId.DialPad, _td(\"invite|transfer_dial_pad_tab\"), <DialPadIcon />, dialPadSection));\n\n        const consultConnectSection = (\n            <div className=\"mx_InviteDialog_transferConsultConnect\">\n                <label>\n                    <input type=\"checkbox\" checked={this.state.consultFirst} onChange={this.onConsultFirstChange} />\n                    {_t(\"voip|transfer_consult_first_label\")}\n                </label>\n                <AccessibleButton\n                    kind=\"secondary\"\n                    onClick={this.onCancel}\n                    className=\"mx_InviteDialog_transferConsultConnect_pushRight\"\n                >\n                    {_t(\"action|cancel\")}\n                </AccessibleButton>\n                <AccessibleButton\n                    kind=\"primary\"\n                    onClick={this.transferCall}\n                    disabled={!this.hasSelection() && this.state.dialPadValue === \"\"}\n                >\n                    {_t(\"action|transfer\")}\n                </AccessibleButton>\n            </div>\n        );\n\n        const dialogContent = (\n            <React.Fragment>\n                <TabbedView<TabId>\n                    tabs={tabs}\n                    activeTabId={this.state.currentTabId}\n                    tabLocation={TabLocation.TOP}\n                    onChange={this.onTabChange}\n                />\n                {consultConnectSection}\n            </React.Fragment>\n        );\n\n        return (\n            <BaseDialog\n                className=\"mx_InviteDialog_transfer\"\n                hasCancel={true}\n                onFinished={this.props.onFinished}\n                title={_t(\"action|transfer\")}\n                screenName={this.screenName}\n            >\n                <div className=\"mx_InviteDialog_content\">{dialogContent}</div>\n            </BaseDialog>\n        );\n    }\n\n    public render(): React.ReactNode {\n        if (this.props.kind === InviteKind.CallTransfer) {\n            return this.renderCallTransferDialog();\n        } else {\n            return this.renderRegularDialog();\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport enum InviteKind {\n    Dm = \"dm\",\n    Invite = \"invite\",\n    // NB. This dialog needs the 'mx_InviteDialog_transferWrapper' wrapper class to have the correct\n    // padding on the bottom (because all modals have 24px padding on all sides), so this needs to\n    // be passed when creating the modal\n    CallTransfer = \"call_transfer\",\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport InlineSpinner from \"../elements/InlineSpinner\";\nimport { _t } from \"../../../languageHandler\";\n\n/** The common body of components that show the progress of sending room invites. */\nconst InviteProgressBody: React.FC = () => {\n    return (\n        <div className=\"mx_InviteProgressBody\">\n            <InlineSpinner w={32} h={32} />\n            <h1>{_t(\"invite|progress|preparing\")}</h1>\n            {_t(\"invite|progress|dont_close\")}\n        </div>\n    );\n};\n\nexport default InviteProgressBody;\n","/*\nCopyright 2024-2025 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 New Vector Ltd\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2017 Vector Creations Ltd\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEvent, type JSX, useCallback, useState } from \"react\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t, UserFriendlyError } from \"../../../languageHandler\";\nimport { getDeviceCryptoInfo } from \"../../../utils/crypto/deviceInfo\";\nimport QuestionDialog from \"./QuestionDialog\";\nimport Modal from \"../../../Modal\";\nimport InfoDialog from \"./InfoDialog\";\nimport Field from \"../elements/Field\";\nimport ErrorDialog from \"./ErrorDialog\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\n\ninterface Props {\n    onFinished(confirm?: boolean): void;\n}\n\n/**\n * A dialog to allow us to verify devices logged in with clients that can't do\n * the verification themselves. Intended for use as a dev tool.\n *\n * Requires entering the fingerprint (\"session key\") of the device in an attempt\n * to prevent users being tricked into verifying a malicious device.\n */\nexport function ManualDeviceKeyVerificationDialog({ onFinished }: Readonly<Props>): JSX.Element {\n    const [deviceId, setDeviceId] = useState(\"\");\n    const [fingerprint, setFingerprint] = useState(\"\");\n\n    const client = MatrixClientPeg.safeGet();\n\n    const onDialogFinished = useCallback(\n        async (confirm: boolean) => {\n            if (confirm) {\n                await manuallyVerifyDevice(client, deviceId, fingerprint);\n            }\n            onFinished(confirm);\n        },\n        [client, deviceId, fingerprint, onFinished],\n    );\n\n    const onDeviceIdChange = useCallback((e: ChangeEvent<HTMLInputElement>) => {\n        setDeviceId(e.target.value);\n    }, []);\n\n    const onFingerprintChange = useCallback((e: ChangeEvent<HTMLInputElement>) => {\n        setFingerprint(e.target.value);\n    }, []);\n\n    const body = (\n        <div>\n            <p>{_t(\"encryption|verification|manual|text\")}</p>\n            <div className=\"mx_DeviceVerifyDialog_cryptoSection\">\n                <Field\n                    className=\"mx_TextInputDialog_input\"\n                    type=\"text\"\n                    label={_t(\"encryption|verification|manual|device_id\")}\n                    value={deviceId}\n                    onChange={onDeviceIdChange}\n                />\n                <Field\n                    className=\"mx_TextInputDialog_input\"\n                    type=\"text\"\n                    label={_t(\"encryption|verification|manual|fingerprint\")}\n                    value={fingerprint}\n                    onChange={onFingerprintChange}\n                />\n            </div>\n        </div>\n    );\n\n    return (\n        <QuestionDialog\n            title={_t(\"settings|sessions|verify_session\")}\n            description={body}\n            button={_t(\"settings|sessions|verify_session\")}\n            onFinished={onDialogFinished}\n        />\n    );\n}\n\n/**\n * Check the supplied fingerprint matches the fingerprint (\"session key\") of the\n * device with the supplied device ID, and if so, mark the device as verified.\n */\nexport async function manuallyVerifyDevice(client: MatrixClient, deviceId: string, fingerprint: string): Promise<void> {\n    try {\n        await doManuallyVerifyDevice(client, deviceId, fingerprint);\n\n        // Tell the user we verified everything\n        Modal.createDialog(InfoDialog, {\n            title: _t(\"encryption|verification|manual|success_title\"),\n            description: (\n                <div>\n                    <p>{_t(\"encryption|verification|manual|success_description\", { deviceId })}</p>\n                </div>\n            ),\n        });\n    } catch (e: any) {\n        // Display an error\n        const error = e instanceof UserFriendlyError ? e.translatedMessage : e.toString();\n        Modal.createDialog(ErrorDialog, {\n            title: _t(\"encryption|verification|manual|failure_title\"),\n            description: (\n                <div>\n                    <p>{_t(\"encryption|verification|manual|failure_description\", { deviceId, error })}</p>\n                </div>\n            ),\n        });\n    }\n}\n\nasync function doManuallyVerifyDevice(client: MatrixClient, deviceId: string, fingerprint: string): Promise<void> {\n    const userId = client.getUserId();\n    if (!userId) {\n        throw new UserFriendlyError(\"encryption|verification|manual|no_userid\", {\n            cause: undefined,\n        });\n    }\n\n    const crypto = client.getCrypto();\n    if (!crypto) {\n        throw new UserFriendlyError(\"encryption|verification|manual|no_crypto\");\n    }\n\n    const device = await getDeviceCryptoInfo(client, userId, deviceId);\n    if (!device) {\n        throw new UserFriendlyError(\"encryption|verification|manual|no_device\", {\n            deviceId,\n            cause: undefined,\n        });\n    }\n    const deviceTrust = await crypto.getDeviceVerificationStatus(userId, deviceId);\n\n    if (deviceTrust?.isVerified()) {\n        if (device.getFingerprint() === fingerprint) {\n            throw new UserFriendlyError(\"encryption|verification|manual|already_verified\", {\n                deviceId,\n                cause: undefined,\n            });\n        } else {\n            throw new UserFriendlyError(\"encryption|verification|manual|already_verified_and_wrong_fingerprint\", {\n                deviceId,\n                cause: undefined,\n            });\n        }\n    }\n\n    if (device.getFingerprint() !== fingerprint) {\n        const fprint = device.getFingerprint();\n        throw new UserFriendlyError(\"encryption|verification|manual|wrong_fingerprint\", {\n            fprint,\n            deviceId,\n            fingerprint,\n            cause: undefined,\n        });\n    }\n\n    // We've passed all the checks - do the device verification\n    await crypto.crossSignDevice(deviceId);\n}\n","/*\nCopyright 2017-2024 New Vector Ltd.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport classNames from \"classnames\";\n\nimport { _t } from \"../../../languageHandler\";\nimport BaseDialog from \"./BaseDialog\";\nimport DialogButtons from \"../elements/DialogButtons\";\n\nexport interface IQuestionDialogProps {\n    title?: string;\n    description?: React.ReactNode;\n    extraButtons?: React.ReactNode;\n    button?: string;\n    buttonDisabled?: boolean;\n    danger?: boolean;\n    focus?: boolean;\n    headerImage?: string;\n    quitOnly?: boolean; // quitOnly doesn't show the cancel button just the quit [x].\n    fixedWidth?: boolean;\n    className?: string;\n    hasCancelButton?: boolean;\n    cancelButton?: React.ReactNode;\n    onFinished(ok?: boolean): void;\n}\n\nexport default class QuestionDialog extends React.Component<IQuestionDialogProps> {\n    public static defaultProps: Partial<IQuestionDialogProps> = {\n        title: \"\",\n        description: \"\",\n        extraButtons: null,\n        focus: true,\n        hasCancelButton: true,\n        danger: false,\n        quitOnly: false,\n    };\n\n    private onOk = (): void => {\n        this.props.onFinished(true);\n    };\n\n    private onCancel = (): void => {\n        this.props.onFinished(false);\n    };\n\n    public render(): React.ReactNode {\n        let primaryButtonClass = \"\";\n        if (this.props.danger) {\n            primaryButtonClass = \"danger\";\n        }\n        return (\n            <BaseDialog\n                className={classNames(\"mx_QuestionDialog\", this.props.className)}\n                onFinished={this.props.onFinished}\n                title={this.props.title}\n                contentId=\"mx_Dialog_content\"\n                headerImage={this.props.headerImage}\n                hasCancel={this.props.hasCancelButton}\n                fixedWidth={this.props.fixedWidth}\n            >\n                <div className=\"mx_Dialog_content\" id=\"mx_Dialog_content\">\n                    {this.props.description}\n                </div>\n                <DialogButtons\n                    primaryButton={this.props.button || _t(\"action|ok\")}\n                    primaryButtonClass={primaryButtonClass}\n                    primaryDisabled={this.props.buttonDisabled}\n                    cancelButton={this.props.cancelButton}\n                    hasCancel={this.props.hasCancelButton && !this.props.quitOnly}\n                    onPrimaryButtonClick={this.onOk}\n                    focus={this.props.focus}\n                    onCancel={this.onCancel}\n                >\n                    {this.props.extraButtons}\n                </DialogButtons>\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2019-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef } from \"react\";\nimport classNames from \"classnames\";\nimport { ContentHelpers, EventType, type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport Field from \"../elements/Field\";\nimport AccessibleButton, { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport AvatarSetting from \"../settings/AvatarSetting\";\nimport { htmlSerializeFromMdIfNeeded } from \"../../../editor/serialize\";\nimport DMRoomMap from \"../../../utils/DMRoomMap\";\nimport { LocalRoom } from \"../../../models/LocalRoom\";\n\ninterface IProps {\n    roomId: string;\n}\n\ninterface IState {\n    originalDisplayName: string;\n    displayName: string;\n    originalAvatarUrl: string | null;\n    avatarFile: File | null;\n    // If true, the user has indicated that they wish to remove the avatar and this should happen on save.\n    avatarRemovalPending: boolean;\n    originalTopic: string;\n    topic: string;\n    profileFieldsTouched: Record<string, boolean>;\n    canSetName: boolean;\n    canSetTopic: boolean;\n    canSetAvatar: boolean;\n}\n\nfunction idNameForRoom(room: Room): string {\n    const dmMapUserId = DMRoomMap.shared().getUserIdForRoomId(room.roomId);\n    // If the room is a DM, we use the other user's ID for the color hash\n    // in order to match the room avatar with their avatar\n    if (dmMapUserId) return dmMapUserId;\n\n    if (room instanceof LocalRoom && room.targets.length === 1) {\n        return room.targets[0].userId;\n    }\n\n    return room.roomId;\n}\n\n// TODO: Merge with ProfileSettings?\nexport default class RoomProfileSettings extends React.Component<IProps, IState> {\n    private avatarUpload = createRef<HTMLInputElement>();\n\n    public constructor(props: IProps) {\n        super(props);\n\n        const client = MatrixClientPeg.safeGet();\n        const room = client.getRoom(props.roomId);\n        if (!room) throw new Error(`Expected a room for ID: ${props.roomId}`);\n\n        const avatarEvent = room.currentState.getStateEvents(EventType.RoomAvatar, \"\");\n        const avatarUrl = avatarEvent?.getContent()[\"url\"] ?? null;\n\n        const topicEvent = room.currentState.getStateEvents(EventType.RoomTopic, \"\");\n        const topic = (topicEvent && ContentHelpers.parseTopicContent(topicEvent.getContent()).text) || \"\";\n\n        const nameEvent = room.currentState.getStateEvents(EventType.RoomName, \"\");\n        const name = nameEvent && nameEvent.getContent() ? nameEvent.getContent()[\"name\"] : \"\";\n\n        const userId = client.getSafeUserId();\n        this.state = {\n            originalDisplayName: name,\n            displayName: name,\n            originalAvatarUrl: avatarUrl,\n            avatarFile: null,\n            avatarRemovalPending: false,\n            originalTopic: topic,\n            topic: topic,\n            profileFieldsTouched: {},\n            canSetName: room.currentState.maySendStateEvent(EventType.RoomName, userId),\n            canSetTopic: room.currentState.maySendStateEvent(EventType.RoomTopic, userId),\n            canSetAvatar: room.currentState.maySendStateEvent(EventType.RoomAvatar, userId),\n        };\n    }\n\n    private onAvatarChanged = (file: File): void => {\n        this.setState({\n            avatarFile: file,\n            avatarRemovalPending: false,\n            profileFieldsTouched: {\n                ...this.state.profileFieldsTouched,\n                avatar: true,\n            },\n        });\n    };\n\n    private removeAvatar = (): void => {\n        // clear file upload field so same file can be selected\n        if (this.avatarUpload.current) this.avatarUpload.current.value = \"\";\n        this.setState({\n            avatarFile: null,\n            avatarRemovalPending: true,\n            profileFieldsTouched: {\n                ...this.state.profileFieldsTouched,\n                avatar: true,\n            },\n        });\n    };\n\n    private isSaveEnabled = (): boolean => {\n        return Boolean(Object.values(this.state.profileFieldsTouched).length);\n    };\n\n    private cancelProfileChanges = async (e: ButtonEvent): Promise<void> => {\n        e.stopPropagation();\n        e.preventDefault();\n\n        if (!this.isSaveEnabled()) return;\n        this.setState({\n            profileFieldsTouched: {},\n            displayName: this.state.originalDisplayName,\n            topic: this.state.originalTopic,\n            avatarFile: null,\n            avatarRemovalPending: false,\n        });\n    };\n\n    private saveProfile = async (e: React.FormEvent): Promise<void> => {\n        e.stopPropagation();\n        e.preventDefault();\n\n        if (!this.isSaveEnabled()) return;\n        this.setState({ profileFieldsTouched: {} });\n\n        const client = MatrixClientPeg.safeGet();\n        const newState: Partial<IState> = {};\n\n        // TODO: What do we do about errors?\n        const displayName = this.state.displayName.trim();\n        if (this.state.originalDisplayName !== this.state.displayName) {\n            await client.setRoomName(this.props.roomId, displayName);\n            newState.originalDisplayName = displayName;\n            newState.displayName = displayName;\n        }\n\n        if (this.state.avatarFile) {\n            const { content_uri: uri } = await client.uploadContent(this.state.avatarFile);\n            await client.sendStateEvent(this.props.roomId, EventType.RoomAvatar, { url: uri }, \"\");\n            newState.originalAvatarUrl = uri;\n            newState.avatarFile = null;\n        } else if (this.state.avatarRemovalPending) {\n            await client.sendStateEvent(this.props.roomId, EventType.RoomAvatar, {}, \"\");\n            newState.avatarRemovalPending = false;\n            newState.originalAvatarUrl = null;\n        }\n\n        if (this.state.originalTopic !== this.state.topic) {\n            const html = htmlSerializeFromMdIfNeeded(this.state.topic, { forceHTML: false });\n            // XXX: Note that we deliberately send an empty string on an empty topic rather\n            // than a clearer `undefined` value. Synapse still requires a string in a topic.\n            await client.setRoomTopic(this.props.roomId, this.state.topic, html);\n            newState.originalTopic = this.state.topic;\n        }\n\n        this.setState(newState as IState);\n    };\n\n    private onDisplayNameChanged = (e: React.ChangeEvent<HTMLInputElement>): void => {\n        this.setState({ displayName: e.target.value });\n        if (this.state.originalDisplayName === e.target.value) {\n            this.setState({\n                profileFieldsTouched: {\n                    ...this.state.profileFieldsTouched,\n                    name: false,\n                },\n            });\n        } else {\n            this.setState({\n                profileFieldsTouched: {\n                    ...this.state.profileFieldsTouched,\n                    name: true,\n                },\n            });\n        }\n    };\n\n    private onTopicChanged = (e: React.ChangeEvent<HTMLTextAreaElement>): void => {\n        this.setState({ topic: e.target.value });\n        if (this.state.originalTopic === e.target.value) {\n            this.setState({\n                profileFieldsTouched: {\n                    ...this.state.profileFieldsTouched,\n                    topic: false,\n                },\n            });\n        } else {\n            this.setState({\n                profileFieldsTouched: {\n                    ...this.state.profileFieldsTouched,\n                    topic: true,\n                },\n            });\n        }\n    };\n\n    public render(): React.ReactNode {\n        let profileSettingsButtons;\n        if (this.state.canSetName || this.state.canSetTopic || this.state.canSetAvatar) {\n            profileSettingsButtons = (\n                <div className=\"mx_RoomProfileSettings_buttons\">\n                    <AccessibleButton\n                        onClick={this.cancelProfileChanges}\n                        kind=\"primary_outline\"\n                        disabled={!this.isSaveEnabled()}\n                    >\n                        {_t(\"action|cancel\")}\n                    </AccessibleButton>\n                    <AccessibleButton onClick={this.saveProfile} kind=\"primary\" disabled={!this.isSaveEnabled()}>\n                        {_t(\"action|save\")}\n                    </AccessibleButton>\n                </div>\n            );\n        }\n\n        const canRemove = this.state.profileFieldsTouched.avatar\n            ? Boolean(this.state.avatarFile)\n            : Boolean(this.state.originalAvatarUrl);\n\n        return (\n            <form onSubmit={this.saveProfile} autoComplete=\"off\" noValidate={true} className=\"mx_RoomProfileSettings\">\n                <div className=\"mx_RoomProfileSettings_profile\">\n                    <div className=\"mx_RoomProfileSettings_profile_controls\">\n                        <Field\n                            label={_t(\"room_settings|general|name_field_label\")}\n                            type=\"text\"\n                            value={this.state.displayName}\n                            autoComplete=\"off\"\n                            onChange={this.onDisplayNameChanged}\n                            disabled={!this.state.canSetName}\n                        />\n                        <Field\n                            className={classNames(\n                                \"mx_RoomProfileSettings_profile_controls_topic\",\n                                \"mx_RoomProfileSettings_profile_controls_topic--room\",\n                            )}\n                            id=\"profileTopic\" // See: NewRoomIntro.tsx\n                            label={_t(\"room_settings|general|topic_field_label\")}\n                            disabled={!this.state.canSetTopic}\n                            type=\"text\"\n                            value={this.state.topic}\n                            autoComplete=\"off\"\n                            onChange={this.onTopicChanged}\n                            element=\"textarea\"\n                        />\n                    </div>\n                    <AvatarSetting\n                        avatar={\n                            this.state.avatarRemovalPending\n                                ? undefined\n                                : (this.state.avatarFile ?? this.state.originalAvatarUrl ?? undefined)\n                        }\n                        avatarAccessibleName={_t(\"room_settings|general|avatar_field_label\")}\n                        disabled={!this.state.canSetAvatar}\n                        onChange={this.onAvatarChanged}\n                        removeAvatar={canRemove ? this.removeAvatar : undefined}\n                        placeholderId={idNameForRoom(MatrixClientPeg.safeGet().getRoom(this.props.roomId)!)}\n                        placeholderName={MatrixClientPeg.safeGet().getRoom(this.props.roomId)!.name}\n                    />\n                </div>\n                {profileSettingsButtons}\n            </form>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018, 2019 New Vector Ltd\nCopyright 2017 Travis Ralston\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode, type JSX } from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { InlineSpinner } from \"@vector-im/compound-web\";\n\nimport { _t } from \"../../../languageHandler\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { SettingLevel } from \"../../../settings/SettingLevel\";\nimport SettingsFlag from \"../elements/SettingsFlag\";\nimport SettingsFieldset from \"../settings/SettingsFieldset\";\nimport AccessibleButton, { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport { useIsEncrypted } from \"../../../hooks/useIsEncrypted.ts\";\nimport { useMatrixClientContext } from \"../../../contexts/MatrixClientContext.tsx\";\nimport { useSettingValueAt } from \"../../../hooks/useSettings.ts\";\n\n/**\n * The URL preview settings for a room\n */\ninterface UrlPreviewSettingsProps {\n    /**\n     * The room.\n     */\n    room: Room;\n}\n\nexport function UrlPreviewSettings({ room }: UrlPreviewSettingsProps): JSX.Element {\n    const { roomId } = room;\n    const matrixClient = useMatrixClientContext();\n    const isEncrypted = useIsEncrypted(matrixClient, room);\n    const isLoading = isEncrypted === null;\n\n    return (\n        <SettingsFieldset\n            legend={_t(\"room_settings|general|url_previews_section\")}\n            description={!isLoading && <Description isEncrypted={isEncrypted} />}\n        >\n            {isLoading ? (\n                <InlineSpinner />\n            ) : (\n                <>\n                    <PreviewsForRoom isEncrypted={isEncrypted} roomId={roomId} />\n                    <SettingsFlag\n                        name={isEncrypted ? \"urlPreviewsEnabled_e2ee\" : \"urlPreviewsEnabled\"}\n                        level={SettingLevel.ROOM_DEVICE}\n                        roomId={roomId}\n                    />\n                </>\n            )}\n        </SettingsFieldset>\n    );\n}\n\n/**\n * Click handler for the user settings link\n * @param e\n */\nfunction onClickUserSettings(e: ButtonEvent): void {\n    e.preventDefault();\n    e.stopPropagation();\n    dis.fire(Action.ViewUserSettings);\n}\n\n/**\n * The description for the URL preview settings\n */\ninterface DescriptionProps {\n    /**\n     * Whether the room is encrypted\n     */\n    isEncrypted: boolean;\n}\n\nfunction Description({ isEncrypted }: DescriptionProps): JSX.Element {\n    const urlPreviewsEnabled = useSettingValueAt(SettingLevel.ACCOUNT, \"urlPreviewsEnabled\");\n\n    let previewsForAccount: ReactNode | undefined;\n    if (isEncrypted) {\n        previewsForAccount = _t(\"room_settings|general|url_preview_encryption_warning\");\n    } else {\n        const button = {\n            a: (sub: string) => (\n                <AccessibleButton kind=\"link_inline\" onClick={onClickUserSettings}>\n                    {sub}\n                </AccessibleButton>\n            ),\n        };\n\n        previewsForAccount = urlPreviewsEnabled\n            ? _t(\"room_settings|general|user_url_previews_default_on\", {}, button)\n            : _t(\"room_settings|general|user_url_previews_default_off\", {}, button);\n    }\n\n    return (\n        <>\n            <p>{_t(\"room_settings|general|url_preview_explainer\")}</p>\n            <p>{previewsForAccount}</p>\n        </>\n    );\n}\n\n/**\n * The description for the URL preview settings\n */\ninterface PreviewsForRoomProps {\n    /**\n     * Whether the room is encrypted\n     */\n    isEncrypted: boolean;\n    /**\n     * The room ID\n     */\n    roomId: string;\n}\n\nfunction PreviewsForRoom({ isEncrypted, roomId }: PreviewsForRoomProps): JSX.Element | null {\n    const urlPreviewsEnabled = useSettingValueAt(\n        SettingLevel.ACCOUNT,\n        \"urlPreviewsEnabled\",\n        roomId,\n        /*explicit=*/ true,\n    );\n    if (isEncrypted) return null;\n\n    let previewsForRoom: ReactNode;\n    if (SettingsStore.canSetValue(\"urlPreviewsEnabled\", roomId, SettingLevel.ROOM)) {\n        previewsForRoom = (\n            <SettingsFlag name=\"urlPreviewsEnabled\" level={SettingLevel.ROOM} roomId={roomId} isExplicit={true} />\n        );\n    } else {\n        previewsForRoom = (\n            <div>\n                {urlPreviewsEnabled\n                    ? _t(\"room_settings|general|default_url_previews_on\")\n                    : _t(\"room_settings|general|default_url_previews_off\")}\n            </div>\n        );\n    }\n\n    return previewsForRoom;\n}\n","/*\nCopyright 2019-2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ContextType } from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { Form } from \"@vector-im/compound-web\";\n\nimport { _t } from \"../../../../../languageHandler\";\nimport RoomProfileSettings from \"../../../room_settings/RoomProfileSettings\";\nimport AccessibleButton, { type ButtonEvent } from \"../../../elements/AccessibleButton\";\nimport dis from \"../../../../../dispatcher/dispatcher\";\nimport MatrixClientContext from \"../../../../../contexts/MatrixClientContext\";\nimport SettingsStore from \"../../../../../settings/SettingsStore\";\nimport { UIFeature } from \"../../../../../settings/UIFeature\";\nimport AliasSettings from \"../../../room_settings/AliasSettings\";\nimport PosthogTrackers from \"../../../../../PosthogTrackers\";\nimport { SettingsSubsection } from \"../../shared/SettingsSubsection\";\nimport SettingsTab from \"../SettingsTab\";\nimport { SettingsSection } from \"../../shared/SettingsSection\";\nimport { UrlPreviewSettings } from \"../../../room_settings/UrlPreviewSettings\";\nimport { MediaPreviewAccountSettings } from \"../user/MediaPreviewAccountSettings\";\n\ninterface IProps {\n    room: Room;\n}\n\ninterface IState {\n    isRoomPublished: boolean;\n}\n\nexport default class GeneralRoomSettingsTab extends React.Component<IProps, IState> {\n    public static contextType = MatrixClientContext;\n    declare public context: ContextType<typeof MatrixClientContext>;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            isRoomPublished: false, // loaded async\n        };\n    }\n\n    private onLeaveClick = (ev: ButtonEvent): void => {\n        dis.dispatch({\n            action: \"leave_room\",\n            room_id: this.props.room.roomId,\n        });\n\n        PosthogTrackers.trackInteraction(\"WebRoomSettingsLeaveButton\", ev);\n    };\n\n    public render(): React.ReactNode {\n        const client = this.context;\n        const room = this.props.room;\n\n        const canSetAliases = true; // Previously, we arbitrarily only allowed admins to do this\n        const canSetCanonical = room.currentState.mayClientSendStateEvent(\"m.room.canonical_alias\", client);\n        const canonicalAliasEv = room.currentState.getStateEvents(\"m.room.canonical_alias\", \"\") ?? undefined;\n\n        const urlPreviewSettings = SettingsStore.getValue(UIFeature.URLPreviews) ? (\n            <UrlPreviewSettings room={room} />\n        ) : null;\n\n        let leaveSection;\n        if (room.getMyMembership() === KnownMembership.Join) {\n            leaveSection = (\n                <SettingsSubsection heading={_t(\"action|leave_room\")}>\n                    <AccessibleButton kind=\"danger\" onClick={this.onLeaveClick}>\n                        {_t(\"action|leave_room\")}\n                    </AccessibleButton>\n                </SettingsSubsection>\n            );\n        }\n\n        return (\n            <SettingsTab data-testid=\"General\">\n                <Form.Root\n                    onSubmit={(evt) => {\n                        evt.preventDefault();\n                        evt.stopPropagation();\n                    }}\n                >\n                    <SettingsSection heading={_t(\"common|general\")}>\n                        <RoomProfileSettings roomId={room.roomId} />\n                    </SettingsSection>\n\n                    <SettingsSection heading={_t(\"room_settings|general|aliases_section\")}>\n                        <AliasSettings\n                            roomId={room.roomId}\n                            canSetCanonicalAlias={canSetCanonical}\n                            canSetAliases={canSetAliases}\n                            canonicalAliasEvent={canonicalAliasEv}\n                        />\n                    </SettingsSection>\n\n                    <SettingsSection heading={_t(\"room_settings|general|other_section\")}>\n                        {urlPreviewSettings}\n                        <SettingsSubsection heading={_t(\"common|moderation_and_safety\")} legacy={false}>\n                            <MediaPreviewAccountSettings roomId={room.roomId} />\n                        </SettingsSubsection>\n                        {leaveSection}\n                    </SettingsSection>\n                </Form.Root>\n            </SettingsTab>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEventHandler, type JSX, type ReactNode } from \"react\";\nimport {\n    GuestAccess,\n    HistoryVisibility,\n    JoinRule,\n    type MatrixEvent,\n    RoomStateEvent,\n    type Room,\n    EventType,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { Form, InlineSpinner, SettingsToggleInput } from \"@vector-im/compound-web\";\nimport { WarningIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../../../languageHandler\";\nimport Modal from \"../../../../../Modal\";\nimport QuestionDialog from \"../../../dialogs/QuestionDialog\";\nimport StyledRadioGroup from \"../../../elements/StyledRadioGroup\";\nimport { SettingLevel } from \"../../../../../settings/SettingLevel\";\nimport SettingsStore from \"../../../../../settings/SettingsStore\";\nimport { UIFeature } from \"../../../../../settings/UIFeature\";\nimport AccessibleButton from \"../../../elements/AccessibleButton\";\nimport SettingsFlag from \"../../../elements/SettingsFlag\";\nimport createRoom from \"../../../../../createRoom\";\nimport CreateRoomDialog from \"../../../dialogs/CreateRoomDialog\";\nimport JoinRuleSettings from \"../../JoinRuleSettings\";\nimport ErrorDialog from \"../../../dialogs/ErrorDialog\";\nimport SettingsFieldset from \"../../SettingsFieldset\";\nimport ExternalLink from \"../../../elements/ExternalLink\";\nimport PosthogTrackers from \"../../../../../PosthogTrackers\";\nimport MatrixClientContext from \"../../../../../contexts/MatrixClientContext\";\nimport { SettingsSection } from \"../../shared/SettingsSection\";\nimport SettingsTab from \"../SettingsTab\";\nimport SdkConfig from \"../../../../../SdkConfig\";\nimport { shouldForceDisableEncryption } from \"../../../../../utils/crypto/shouldForceDisableEncryption\";\nimport { Caption } from \"../../../typography/Caption\";\nimport { MEGOLM_ENCRYPTION_ALGORITHM } from \"../../../../../utils/crypto\";\n\ninterface IProps {\n    room: Room;\n    closeSettingsFn: () => void;\n}\n\ninterface IState {\n    guestAccess: GuestAccess;\n    history: HistoryVisibility;\n    hasAliases: boolean;\n    encrypted: boolean | null;\n    stateEncrypted: boolean | null;\n    showAdvancedSection: boolean;\n}\n\nexport default class SecurityRoomSettingsTab extends React.Component<IProps, IState> {\n    public static contextType = MatrixClientContext;\n    declare public context: React.ContextType<typeof MatrixClientContext>;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        const state = this.props.room.currentState;\n\n        this.state = {\n            guestAccess: this.pullContentPropertyFromEvent<GuestAccess>(\n                state?.getStateEvents(EventType.RoomGuestAccess, \"\"),\n                \"guest_access\",\n                GuestAccess.Forbidden,\n            ),\n            history: this.pullContentPropertyFromEvent<HistoryVisibility>(\n                state?.getStateEvents(EventType.RoomHistoryVisibility, \"\"),\n                \"history_visibility\",\n                HistoryVisibility.Shared,\n            ),\n            hasAliases: false, // async loaded in componentDidMount\n            encrypted: null, // async loaded in componentDidMount\n            stateEncrypted: null, // async loaded in componentDidMount\n            showAdvancedSection: false,\n        };\n    }\n\n    public async componentDidMount(): Promise<void> {\n        this.context.on(RoomStateEvent.Events, this.onStateEvent);\n\n        this.setState({\n            hasAliases: await this.hasAliases(),\n            encrypted: Boolean(await this.context.getCrypto()?.isEncryptionEnabledInRoom(this.props.room.roomId)),\n            stateEncrypted: Boolean(\n                await this.context.getCrypto()?.isStateEncryptionEnabledInRoom(this.props.room.roomId),\n            ),\n        });\n    }\n\n    private pullContentPropertyFromEvent<T>(event: MatrixEvent | null | undefined, key: string, defaultValue: T): T {\n        return event?.getContent()[key] || defaultValue;\n    }\n\n    public componentWillUnmount(): void {\n        this.context.removeListener(RoomStateEvent.Events, this.onStateEvent);\n    }\n\n    private onStateEvent = (e: MatrixEvent): void => {\n        const refreshWhenTypes: EventType[] = [\n            EventType.RoomJoinRules,\n            EventType.RoomGuestAccess,\n            EventType.RoomHistoryVisibility,\n            EventType.RoomEncryption,\n        ];\n        if (refreshWhenTypes.includes(e.getType() as EventType)) this.forceUpdate();\n    };\n\n    private onEncryptionChange = async (): Promise<void> => {\n        if (this.props.room.getJoinRule() === JoinRule.Public) {\n            const dialog = Modal.createDialog(QuestionDialog, {\n                title: _t(\"room_settings|security|enable_encryption_public_room_confirm_title\"),\n                description: (\n                    <div>\n                        <p>\n                            {\" \"}\n                            {_t(\n                                \"room_settings|security|enable_encryption_public_room_confirm_description_1\",\n                                undefined,\n                                { b: (sub) => <strong>{sub}</strong> },\n                            )}{\" \"}\n                        </p>\n                        <p>\n                            {\" \"}\n                            {_t(\n                                \"room_settings|security|enable_encryption_public_room_confirm_description_2\",\n                                undefined,\n                                {\n                                    a: (sub) => (\n                                        <AccessibleButton\n                                            kind=\"link_inline\"\n                                            onClick={() => {\n                                                dialog.close();\n                                                this.createNewRoom(false, true);\n                                            }}\n                                        >\n                                            {\" \"}\n                                            {sub}{\" \"}\n                                        </AccessibleButton>\n                                    ),\n                                },\n                            )}{\" \"}\n                        </p>\n                    </div>\n                ),\n            });\n\n            const { finished } = dialog;\n            const [confirm] = await finished;\n            if (!confirm) return;\n        }\n\n        const { finished } = Modal.createDialog(QuestionDialog, {\n            title: _t(\"room_settings|security|enable_encryption_confirm_title\"),\n            description: _t(\n                \"room_settings|security|enable_encryption_confirm_description\",\n                {},\n                {\n                    a: (sub) => <ExternalLink href={SdkConfig.get(\"help_encryption_url\")}>{sub}</ExternalLink>,\n                },\n            ),\n        });\n        finished.then(([confirm]) => {\n            if (!confirm) {\n                this.setState({ encrypted: false });\n                return;\n            }\n\n            const beforeEncrypted = this.state.encrypted;\n            this.setState({ encrypted: true });\n            this.context\n                .sendStateEvent(this.props.room.roomId, EventType.RoomEncryption, {\n                    algorithm: MEGOLM_ENCRYPTION_ALGORITHM,\n                })\n                .catch((e) => {\n                    logger.error(e);\n                    this.setState({ encrypted: beforeEncrypted });\n                });\n        });\n    };\n\n    private onGuestAccessChange: ChangeEventHandler<HTMLInputElement> = (evt): void => {\n        const allowed = evt.target.checked;\n        const guestAccess = allowed ? GuestAccess.CanJoin : GuestAccess.Forbidden;\n        const beforeGuestAccess = this.state.guestAccess;\n        if (beforeGuestAccess === guestAccess) return;\n\n        this.setState({ guestAccess });\n\n        this.context\n            .sendStateEvent(\n                this.props.room.roomId,\n                EventType.RoomGuestAccess,\n                {\n                    guest_access: guestAccess,\n                },\n                \"\",\n            )\n            .catch((e) => {\n                logger.error(e);\n                this.setState({ guestAccess: beforeGuestAccess });\n            });\n    };\n\n    private createNewRoom = async (defaultPublic: boolean, defaultEncrypted: boolean): Promise<boolean> => {\n        const modal = Modal.createDialog(CreateRoomDialog, { defaultPublic, defaultEncrypted });\n\n        PosthogTrackers.trackInteraction(\"WebRoomSettingsSecurityTabCreateNewRoomButton\");\n\n        const [shouldCreate, opts] = await modal.finished;\n        if (shouldCreate) {\n            await createRoom(this.context, opts!);\n        }\n        return shouldCreate ?? false;\n    };\n\n    private onHistoryRadioToggle = (history: HistoryVisibility): void => {\n        const beforeHistory = this.state.history;\n        if (beforeHistory === history) return;\n\n        this.setState({ history: history });\n        this.context\n            .sendStateEvent(\n                this.props.room.roomId,\n                EventType.RoomHistoryVisibility,\n                {\n                    history_visibility: history,\n                },\n                \"\",\n            )\n            .catch((e) => {\n                logger.error(e);\n                this.setState({ history: beforeHistory });\n            });\n    };\n\n    private updateBlacklistDevicesFlag = (checked: boolean): void => {\n        this.props.room.setBlacklistUnverifiedDevices(checked);\n    };\n\n    private async hasAliases(): Promise<boolean> {\n        const cli = this.context;\n        const response = await cli.getLocalAliases(this.props.room.roomId);\n        const localAliases = response.aliases;\n        return Array.isArray(localAliases) && localAliases.length !== 0;\n    }\n\n    private renderJoinRule(): JSX.Element {\n        const room = this.props.room;\n        const isPublic = room.getJoinRule() === JoinRule.Public;\n        const description = (\n            <>\n                <p>\n                    {_t(\"room_settings|security|join_rule_description\", {\n                        roomName: room.name,\n                    })}\n                </p>\n                {isPublic && this.state.history === HistoryVisibility.WorldReadable && (\n                    <div className=\"mx_SecurityRoomSettingsTab_warning\">\n                        <WarningIcon width={15} height={15} />\n                        <span>{_t(\"room_settings|security|join_rule_world_readable_description\")}</span>\n                    </div>\n                )}\n                {isPublic && !this.state.hasAliases && (\n                    <div className=\"mx_SecurityRoomSettingsTab_warning\">\n                        <WarningIcon width={15} height={15} />\n                        <span>{_t(\"room_settings|security|public_without_alias_warning\")}</span>\n                    </div>\n                )}\n            </>\n        );\n\n        let advanced: JSX.Element | undefined;\n        if (room.getJoinRule() === JoinRule.Public) {\n            advanced = (\n                <div>\n                    <AccessibleButton\n                        onClick={this.toggleAdvancedSection}\n                        kind=\"link\"\n                        className=\"mx_SettingsTab_showAdvanced\"\n                        aria-expanded={this.state.showAdvancedSection}\n                    >\n                        {this.state.showAdvancedSection ? _t(\"action|hide_advanced\") : _t(\"action|show_advanced\")}\n                    </AccessibleButton>\n                    {this.state.showAdvancedSection && this.renderAdvanced()}\n                </div>\n            );\n        }\n\n        return (\n            <SettingsFieldset legend={_t(\"room_settings|access|title\")} description={description}>\n                <JoinRuleSettings\n                    room={room}\n                    beforeChange={this.onBeforeJoinRuleChange}\n                    onError={this.onJoinRuleChangeError}\n                    closeSettingsFn={this.props.closeSettingsFn}\n                    promptUpgrade={true}\n                />\n                {advanced}\n            </SettingsFieldset>\n        );\n    }\n\n    private onJoinRuleChangeError = (error: Error): void => {\n        Modal.createDialog(ErrorDialog, {\n            title: _t(\"room_settings|security|error_join_rule_change_title\"),\n            description: error.message ?? _t(\"room_settings|security|error_join_rule_change_unknown\"),\n        });\n    };\n\n    private onBeforeJoinRuleChange = async (joinRule: JoinRule): Promise<boolean> => {\n        if (this.state.encrypted && joinRule === JoinRule.Public) {\n            const dialog = Modal.createDialog(QuestionDialog, {\n                title: _t(\"room_settings|security|encrypted_room_public_confirm_title\"),\n                description: (\n                    <div>\n                        <p>\n                            {\" \"}\n                            {_t(\"room_settings|security|encrypted_room_public_confirm_description_1\", undefined, {\n                                b: (sub) => <strong>{sub}</strong>,\n                            })}{\" \"}\n                        </p>\n                        <p>\n                            {\" \"}\n                            {_t(\"room_settings|security|encrypted_room_public_confirm_description_2\", undefined, {\n                                a: (sub) => (\n                                    <AccessibleButton\n                                        kind=\"link_inline\"\n                                        onClick={(): void => {\n                                            dialog.close();\n                                            this.createNewRoom(true, false);\n                                        }}\n                                    >\n                                        {\" \"}\n                                        {sub}{\" \"}\n                                    </AccessibleButton>\n                                ),\n                            })}{\" \"}\n                        </p>\n                    </div>\n                ),\n            });\n\n            const { finished } = dialog;\n            const [confirm] = await finished;\n            if (!confirm) return false;\n        }\n\n        // If the room is going from public to private AND the room is join readable, we want to encourage the user\n        // to change the history visibility.\n        const currentlyPublic = this.props.room.getJoinRule() === JoinRule.Public;\n        if (this.state.history === HistoryVisibility.WorldReadable && currentlyPublic && joinRule !== JoinRule.Public) {\n            const client = this.context;\n            const canChangeHistory = this.props.room.currentState?.mayClientSendStateEvent(\n                EventType.RoomHistoryVisibility,\n                client,\n            );\n\n            // If we can't change the history visibility, then don't allow the join rule transition. This is a unlikely occurance\n            // and if this is the case, a room administator should step in.\n            if (!canChangeHistory) {\n                const dialog = Modal.createDialog(ErrorDialog, {\n                    title: _t(\n                        \"room_settings|security|cannot_change_to_private_due_to_missing_history_visiblity_permissions|title\",\n                    ),\n                    description: (\n                        <p>\n                            {_t(\n                                \"room_settings|security|cannot_change_to_private_due_to_missing_history_visiblity_permissions|description\",\n                            )}\n                        </p>\n                    ),\n                });\n                await dialog.finished;\n                return false;\n            }\n\n            // Adjust the history visibility first.\n            try {\n                await this.context.sendStateEvent(\n                    this.props.room.roomId,\n                    EventType.RoomHistoryVisibility,\n                    {\n                        history_visibility: HistoryVisibility.Shared,\n                    },\n                    \"\",\n                );\n                this.setState({ history: HistoryVisibility.Shared });\n            } catch (ex) {\n                logger.error(\"Failed to change history visibility\", ex);\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"common|error\"),\n                    description: _t(\"error|update_history_visibility\"),\n                });\n                // If we fail to update the history visibility\n                return false;\n            }\n        }\n\n        return true;\n    };\n\n    private renderHistory(): ReactNode {\n        if (!SettingsStore.getValue(UIFeature.RoomHistorySettings)) {\n            return null;\n        }\n\n        const client = this.context;\n        const history = this.state.history;\n        const state = this.props.room.currentState;\n        const canChangeHistory = state?.mayClientSendStateEvent(EventType.RoomHistoryVisibility, client);\n\n        // Map 'joined' to 'invited' for display purposes\n        const displayHistory = history === HistoryVisibility.Joined ? HistoryVisibility.Invited : history;\n\n        const isPublicRoom = this.props.room.getJoinRule() === JoinRule.Public;\n        const isEncrypted = this.state.encrypted;\n\n        const options: Array<{ value: HistoryVisibility; label: string }> = [];\n\n        // Show \"invited\" when room's join rule is NOT public OR E2EE is turned on, or if currently selected\n        if (\n            !isPublicRoom ||\n            isEncrypted ||\n            history === HistoryVisibility.Invited ||\n            history === HistoryVisibility.Joined\n        ) {\n            options.push({\n                value: HistoryVisibility.Invited,\n                label: _t(\"room_settings|security|history_visibility_invited\"),\n            });\n        }\n\n        // Always show \"shared\" option\n        options.push({\n            value: HistoryVisibility.Shared,\n            label: _t(\"room_settings|security|history_visibility_shared\"),\n        });\n\n        // Show \"world_readable\" when (is public AND not encrypted) OR currently selected\n        if ((isPublicRoom && !isEncrypted) || history === HistoryVisibility.WorldReadable) {\n            options.push({\n                value: HistoryVisibility.WorldReadable,\n                label: _t(\"room_settings|security|history_visibility_world_readable\"),\n            });\n        }\n\n        const description = (\n            <>\n                {_t(\n                    \"room_settings|security|history_visibility_warning\",\n                    {},\n                    {\n                        a: (sub) => (\n                            <ExternalLink href=\"https://element.io/en/help#e2ee-history-sharing\">{sub}</ExternalLink>\n                        ),\n                    },\n                )}\n            </>\n        );\n\n        return (\n            <SettingsFieldset legend={_t(\"room_settings|security|history_visibility_legend\")} description={description}>\n                <StyledRadioGroup\n                    name=\"historyVis\"\n                    value={displayHistory}\n                    onChange={this.onHistoryRadioToggle}\n                    disabled={!canChangeHistory}\n                    definitions={options}\n                />\n            </SettingsFieldset>\n        );\n    }\n\n    private toggleAdvancedSection = (): void => {\n        this.setState({ showAdvancedSection: !this.state.showAdvancedSection });\n    };\n\n    private renderAdvanced(): JSX.Element {\n        const client = this.context;\n        const guestAccess = this.state.guestAccess;\n        const state = this.props.room.currentState;\n        const canSetGuestAccess = state?.mayClientSendStateEvent(EventType.RoomGuestAccess, client);\n\n        return (\n            <div className=\"mx_SecurityRoomSettingsTab_advancedSection\">\n                <SettingsToggleInput\n                    name=\"guest-access\"\n                    checked={guestAccess === GuestAccess.CanJoin}\n                    onChange={this.onGuestAccessChange}\n                    disabled={!canSetGuestAccess}\n                    label={_t(\"room_settings|visibility|guest_access_label\")}\n                    helpMessage={_t(\"room_settings|security|guest_access_warning\")}\n                />\n            </div>\n        );\n    }\n\n    public render(): React.ReactNode {\n        const client = this.context;\n        const room = this.props.room;\n        const isEncrypted = this.state.encrypted;\n        const isStateEncrypted = this.state.stateEncrypted;\n        const isEncryptionLoading = isEncrypted === null;\n        const hasEncryptionPermission = room.currentState.mayClientSendStateEvent(EventType.RoomEncryption, client);\n        const isEncryptionForceDisabled = shouldForceDisableEncryption(client);\n        const canEnableEncryption = !isEncrypted && !isEncryptionForceDisabled && hasEncryptionPermission;\n\n        let encryptionSettings: JSX.Element | undefined;\n        if (\n            isEncrypted &&\n            SettingsStore.canSetValue(\"blacklistUnverifiedDevices\", this.props.room.roomId, SettingLevel.ROOM_DEVICE)\n        ) {\n            encryptionSettings = (\n                <SettingsFlag\n                    name=\"blacklistUnverifiedDevices\"\n                    level={SettingLevel.ROOM_DEVICE}\n                    onChange={this.updateBlacklistDevicesFlag}\n                    roomId={this.props.room.roomId}\n                />\n            );\n        }\n\n        const historySection = this.renderHistory();\n\n        return (\n            <SettingsTab>\n                <Form.Root\n                    onSubmit={(evt) => {\n                        evt.preventDefault();\n                        evt.stopPropagation();\n                    }}\n                >\n                    <SettingsSection heading={_t(\"room_settings|security|title\")}>\n                        <SettingsFieldset\n                            legend={_t(\"settings|security|encryption_section\")}\n                            description={\n                                isEncryptionForceDisabled && !isEncrypted\n                                    ? undefined\n                                    : _t(\"room_settings|security|encryption_permanent\")\n                            }\n                        >\n                            {isEncryptionLoading ? (\n                                <InlineSpinner />\n                            ) : (\n                                <>\n                                    <SettingsToggleInput\n                                        name=\"enable-encryption\"\n                                        checked={isEncrypted}\n                                        onChange={this.onEncryptionChange}\n                                        label={_t(\"common|encrypted\")}\n                                        disabled={!canEnableEncryption}\n                                    />\n                                    {isEncryptionForceDisabled && !isEncrypted && (\n                                        <Caption>{_t(\"room_settings|security|encryption_forced\")}</Caption>\n                                    )}\n                                    {isStateEncrypted && (\n                                        <SettingsToggleInput\n                                            name=\"enable-state-encryption\"\n                                            checked={isStateEncrypted}\n                                            label={_t(\"common|state_encryption_enabled\")}\n                                            disabled={true}\n                                        />\n                                    )}\n                                    {encryptionSettings}\n                                </>\n                            )}\n                        </SettingsFieldset>\n                        {this.renderJoinRule()}\n                        {historySection}\n                    </SettingsSection>\n                </Form.Root>\n            </SettingsTab>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, createRef } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { _t } from \"../../../../../languageHandler\";\nimport AccessibleButton, { type ButtonEvent } from \"../../../elements/AccessibleButton\";\nimport Notifier from \"../../../../../Notifier\";\nimport SettingsStore from \"../../../../../settings/SettingsStore\";\nimport { SettingLevel } from \"../../../../../settings/SettingLevel\";\nimport { type RoomEchoChamber } from \"../../../../../stores/local-echo/RoomEchoChamber\";\nimport { EchoChamber } from \"../../../../../stores/local-echo/EchoChamber\";\nimport MatrixClientContext from \"../../../../../contexts/MatrixClientContext\";\nimport StyledRadioGroup from \"../../../elements/StyledRadioGroup\";\nimport { RoomNotifState } from \"../../../../../RoomNotifs\";\nimport defaultDispatcher from \"../../../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../../../dispatcher/actions\";\nimport { UserTab } from \"../../../dialogs/UserTab\";\nimport { chromeFileInputFix } from \"../../../../../utils/BrowserWorkarounds\";\nimport SettingsTab from \"../SettingsTab\";\nimport { SettingsSection } from \"../../shared/SettingsSection\";\nimport { SettingsSubsection } from \"../../shared/SettingsSubsection\";\n\ninterface IProps {\n    roomId: string;\n    closeSettingsFn(): void;\n}\n\ninterface IState {\n    currentSound: string;\n    uploadedFile: File | null;\n}\n\nexport default class NotificationsSettingsTab extends React.Component<IProps, IState> {\n    private readonly roomProps: RoomEchoChamber;\n    private soundUpload = createRef<HTMLInputElement>();\n\n    public static contextType = MatrixClientContext;\n    declare public context: React.ContextType<typeof MatrixClientContext>;\n\n    public constructor(props: IProps, context: React.ContextType<typeof MatrixClientContext>) {\n        super(props, context);\n\n        this.roomProps = EchoChamber.forRoom(context.getRoom(this.props.roomId)!);\n\n        let currentSound = \"default\";\n        const soundData = Notifier.getSoundForRoom(this.props.roomId);\n        if (soundData) {\n            currentSound = soundData.name || soundData.url;\n        }\n\n        this.state = {\n            currentSound,\n            uploadedFile: null,\n        };\n    }\n\n    private triggerUploader = async (e: ButtonEvent): Promise<void> => {\n        e.stopPropagation();\n        e.preventDefault();\n\n        this.soundUpload.current?.click();\n    };\n\n    private onSoundUploadChanged = (e: React.ChangeEvent<HTMLInputElement>): void => {\n        if (!e.target.files || !e.target.files.length) {\n            this.setState({\n                uploadedFile: null,\n            });\n            return;\n        }\n\n        const file = e.target.files[0];\n        this.setState({\n            uploadedFile: file,\n        });\n    };\n\n    private onClickSaveSound = async (e: ButtonEvent): Promise<void> => {\n        e.stopPropagation();\n        e.preventDefault();\n\n        try {\n            await this.saveSound();\n        } catch (ex) {\n            logger.error(`Unable to save notification sound for ${this.props.roomId}`);\n            logger.error(ex);\n        }\n    };\n\n    private async saveSound(): Promise<void> {\n        if (!this.state.uploadedFile) {\n            return;\n        }\n\n        let type = this.state.uploadedFile.type;\n        if (type === \"video/ogg\") {\n            // XXX: I've observed browsers allowing users to pick a audio/ogg files,\n            // and then calling it a video/ogg. This is a lame hack, but man browsers\n            // suck at detecting mimetypes.\n            type = \"audio/ogg\";\n        }\n\n        const { content_uri: url } = await this.context.uploadContent(this.state.uploadedFile, {\n            type,\n        });\n\n        await SettingsStore.setValue(\"notificationSound\", this.props.roomId, SettingLevel.ROOM_ACCOUNT, {\n            name: this.state.uploadedFile.name,\n            type: type,\n            size: this.state.uploadedFile.size,\n            url,\n        });\n\n        this.setState({\n            uploadedFile: null,\n            currentSound: this.state.uploadedFile.name,\n        });\n    }\n\n    private clearSound = (e: ButtonEvent): void => {\n        e.stopPropagation();\n        e.preventDefault();\n        SettingsStore.setValue(\"notificationSound\", this.props.roomId, SettingLevel.ROOM_ACCOUNT, null);\n\n        this.setState({\n            currentSound: \"default\",\n        });\n    };\n\n    private onRoomNotificationChange = (value: RoomNotifState): void => {\n        this.roomProps.notificationVolume = value;\n        this.forceUpdate();\n    };\n\n    private onOpenSettingsClick = (event: ButtonEvent): void => {\n        // avoid selecting the radio button\n        event.preventDefault();\n        this.props.closeSettingsFn();\n        defaultDispatcher.dispatch({\n            action: Action.ViewUserSettings,\n            initialTabId: UserTab.Notifications,\n        });\n    };\n\n    public render(): React.ReactNode {\n        let currentUploadedFile: JSX.Element | undefined;\n        if (this.state.uploadedFile) {\n            currentUploadedFile = (\n                <div>\n                    <span>\n                        {_t(\"room_settings|notifications|uploaded_sound\")}: <code>{this.state.uploadedFile.name}</code>\n                    </span>\n                </div>\n            );\n        }\n\n        return (\n            <SettingsTab>\n                <SettingsSection heading={_t(\"notifications|enable_prompt_toast_title\")}>\n                    <div className=\"mx_NotificationSettingsTab_notificationsSection\">\n                        <StyledRadioGroup\n                            name=\"roomNotificationSetting\"\n                            definitions={[\n                                {\n                                    value: RoomNotifState.AllMessages,\n                                    label: (\n                                        <>\n                                            {_t(\"notifications|default\")}\n                                            <div className=\"mx_NotificationSettingsTab_microCopy\">\n                                                {_t(\n                                                    \"room_settings|notifications|settings_link\",\n                                                    {},\n                                                    {\n                                                        a: (sub) => (\n                                                            <AccessibleButton\n                                                                kind=\"link_inline\"\n                                                                onClick={this.onOpenSettingsClick}\n                                                            >\n                                                                {sub}\n                                                            </AccessibleButton>\n                                                        ),\n                                                    },\n                                                )}\n                                            </div>\n                                        </>\n                                    ),\n                                },\n                                {\n                                    value: RoomNotifState.AllMessagesLoud,\n                                    label: (\n                                        <>\n                                            {_t(\"notifications|all_messages\")}\n                                            <div className=\"mx_NotificationSettingsTab_microCopy\">\n                                                {_t(\"notifications|all_messages_description\")}\n                                            </div>\n                                        </>\n                                    ),\n                                },\n                                {\n                                    value: RoomNotifState.MentionsOnly,\n                                    label: (\n                                        <>\n                                            {_t(\"notifications|mentions_and_keywords\")}\n                                            <div className=\"mx_NotificationSettingsTab_microCopy\">\n                                                {_t(\n                                                    \"notifications|mentions_and_keywords_description\",\n                                                    {},\n                                                    {\n                                                        a: (sub) => (\n                                                            <AccessibleButton\n                                                                kind=\"link_inline\"\n                                                                onClick={this.onOpenSettingsClick}\n                                                            >\n                                                                {sub}\n                                                            </AccessibleButton>\n                                                        ),\n                                                    },\n                                                )}\n                                            </div>\n                                        </>\n                                    ),\n                                },\n                                {\n                                    value: RoomNotifState.Mute,\n                                    label: (\n                                        <>\n                                            {_t(\"common|off\")}\n                                            <div className=\"mx_NotificationSettingsTab_microCopy\">\n                                                {_t(\"notifications|mute_description\")}\n                                            </div>\n                                        </>\n                                    ),\n                                },\n                            ]}\n                            onChange={this.onRoomNotificationChange}\n                            value={this.roomProps.notificationVolume}\n                        />\n                    </div>\n\n                    <SettingsSubsection heading={_t(\"room_settings|notifications|sounds_section\")}>\n                        <div>\n                            <div className=\"mx_SettingsTab_subsectionText\">\n                                <span>\n                                    {_t(\"room_settings|notifications|notification_sound\")}:{\" \"}\n                                    <code>{this.state.currentSound}</code>\n                                </span>\n                            </div>\n                            <AccessibleButton\n                                className=\"mx_NotificationSound_resetSound\"\n                                disabled={this.state.currentSound == \"default\"}\n                                onClick={this.clearSound}\n                                kind=\"primary\"\n                            >\n                                {_t(\"action|reset\")}\n                            </AccessibleButton>\n                        </div>\n                        <div>\n                            <h4 className=\"mx_Heading_h4\">{_t(\"room_settings|notifications|custom_sound_prompt\")}</h4>\n                            <div className=\"mx_SettingsFlag\">\n                                <form autoComplete=\"off\" noValidate={true}>\n                                    <input\n                                        ref={this.soundUpload}\n                                        className=\"mx_NotificationSound_soundUpload\"\n                                        type=\"file\"\n                                        onClick={chromeFileInputFix}\n                                        onChange={this.onSoundUploadChanged}\n                                        accept=\"audio/*\"\n                                        aria-label={_t(\"room_settings|notifications|upload_sound_label\")}\n                                    />\n                                </form>\n\n                                {currentUploadedFile}\n                            </div>\n\n                            <AccessibleButton\n                                className=\"mx_NotificationSound_browse\"\n                                onClick={this.triggerUploader}\n                                kind=\"primary\"\n                            >\n                                {_t(\"room_settings|notifications|browse_button\")}\n                            </AccessibleButton>\n\n                            <AccessibleButton\n                                className=\"mx_NotificationSound_save\"\n                                disabled={this.state.uploadedFile == null}\n                                onClick={this.onClickSaveSound}\n                                kind=\"primary\"\n                            >\n                                {_t(\"action|save\")}\n                            </AccessibleButton>\n                            <br />\n                        </div>\n                    </SettingsSubsection>\n                </SettingsSection>\n            </SettingsTab>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode } from \"react\";\nimport { type MatrixEvent, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { Pill, PillType } from \"../elements/Pill\";\nimport { makeUserPermalink } from \"../../../utils/permalinks/Permalinks\";\nimport BaseAvatar from \"../avatars/BaseAvatar\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { isUrlPermitted } from \"../../../HtmlUtils\";\nimport { mediaFromMxc } from \"../../../customisations/Media\";\n\ninterface IProps {\n    ev: MatrixEvent;\n    room: Room;\n}\n\n/**\n * This should match https://github.com/matrix-org/matrix-doc/blob/hs/msc-bridge-inf/proposals/2346-bridge-info-state-event.md#mbridge\n */\ninterface IBridgeStateEvent {\n    bridgebot: string;\n    creator?: string;\n    protocol: {\n        id: string;\n        displayname?: string;\n        // eslint-disable-next-line camelcase\n        avatar_url?: string;\n        // eslint-disable-next-line camelcase\n        external_url?: string;\n    };\n    network?: {\n        id: string;\n        displayname?: string;\n        // eslint-disable-next-line camelcase\n        avatar_url?: string;\n        // eslint-disable-next-line camelcase\n        external_url?: string;\n    };\n    channel: {\n        id: string;\n        displayname?: string;\n        // eslint-disable-next-line camelcase\n        avatar_url?: string;\n        // eslint-disable-next-line camelcase\n        external_url?: string;\n    };\n}\n\nexport default class BridgeTile extends React.PureComponent<IProps> {\n    public render(): React.ReactNode {\n        const content: IBridgeStateEvent = this.props.ev.getContent();\n        // Validate\n        if (!content.channel?.id || !content.protocol?.id) {\n            logger.warn(`Bridge info event ${this.props.ev.getId()} has missing content. Tile will not render`);\n            return null;\n        }\n        if (!content.bridgebot) {\n            // Bridgebot was not required previously, so in order to not break rooms we are allowing\n            // the sender to be used in place. When the proposal is merged, this should be removed.\n            logger.warn(\n                `Bridge info event ${this.props.ev.getId()} does not provide a 'bridgebot' key which` +\n                    \"is deprecated behaviour. Using sender for now.\",\n            );\n            content.bridgebot = this.props.ev.getSender()!;\n        }\n        const { channel, network, protocol } = content;\n        const protocolName = protocol.displayname || protocol.id;\n        const channelName = channel.displayname || channel.id;\n\n        let creator: JSX.Element | undefined;\n        if (content.creator) {\n            creator = (\n                <li>\n                    {_t(\n                        \"labs|bridge_state_creator\",\n                        {},\n                        {\n                            user: () => (\n                                <Pill\n                                    type={PillType.UserMention}\n                                    room={this.props.room}\n                                    url={makeUserPermalink(content.creator!)}\n                                    shouldShowPillAvatar={SettingsStore.getValue(\"Pill.shouldShowPillAvatar\")}\n                                />\n                            ),\n                        },\n                    )}\n                </li>\n            );\n        }\n\n        const bot = (\n            <li>\n                {_t(\n                    \"labs|bridge_state_manager\",\n                    {},\n                    {\n                        user: () => (\n                            <Pill\n                                type={PillType.UserMention}\n                                room={this.props.room}\n                                url={makeUserPermalink(content.bridgebot)}\n                                shouldShowPillAvatar={SettingsStore.getValue(\"Pill.shouldShowPillAvatar\")}\n                            />\n                        ),\n                    },\n                )}\n            </li>\n        );\n\n        let networkIcon;\n\n        if (protocol.avatar_url) {\n            const avatarUrl = mediaFromMxc(protocol.avatar_url).getSquareThumbnailHttp(64) ?? undefined;\n\n            networkIcon = (\n                <BaseAvatar\n                    className=\"mx_RoomSettingsDialog_protocolIcon\"\n                    size=\"48px\"\n                    name={protocolName}\n                    idName={protocolName}\n                    url={avatarUrl}\n                />\n            );\n        } else {\n            networkIcon = <div className=\"mx_RoomSettingsDialog_noProtocolIcon\" />;\n        }\n        let networkItem: ReactNode | undefined;\n        if (network) {\n            const networkName = network.displayname || network.id;\n            let networkLink = <span>{networkName}</span>;\n            if (typeof network.external_url === \"string\" && isUrlPermitted(network.external_url)) {\n                networkLink = (\n                    <a href={network.external_url} target=\"_blank\" rel=\"noreferrer noopener\">\n                        {networkName}\n                    </a>\n                );\n            }\n            networkItem = _t(\n                \"labs|bridge_state_workspace\",\n                {},\n                {\n                    networkLink: () => networkLink,\n                },\n            );\n        }\n\n        let channelLink = <span>{channelName}</span>;\n        if (typeof channel.external_url === \"string\" && isUrlPermitted(channel.external_url)) {\n            channelLink = (\n                <a href={channel.external_url} target=\"_blank\" rel=\"noreferrer noopener\">\n                    {channelName}\n                </a>\n            );\n        }\n\n        const id = this.props.ev.getId();\n        return (\n            <li key={id} className=\"mx_RoomSettingsDialog_BridgeList_listItem\">\n                <div className=\"mx_RoomSettingsDialog_column_icon\">{networkIcon}</div>\n                <div className=\"mx_RoomSettingsDialog_column_data\">\n                    <h3 className=\"mx_RoomSettingsDialog_column_data_protocolName\">{protocolName}</h3>\n                    <p className=\"mx_RoomSettingsDialog_column_data_details mx_RoomSettingsDialog_workspace_channel_details\">\n                        {networkItem}\n                        <span className=\"mx_RoomSettingsDialog_channel\">\n                            {_t(\n                                \"labs|bridge_state_channel\",\n                                {},\n                                {\n                                    channelLink: () => channelLink,\n                                },\n                            )}\n                        </span>\n                    </p>\n                    <ul className=\"mx_RoomSettingsDialog_column_data_metadata mx_RoomSettingsDialog_metadata\">\n                        {creator} {bot}\n                    </ul>\n                </div>\n            </li>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode } from \"react\";\nimport { type Room, type MatrixClient, type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../../../languageHandler\";\nimport BridgeTile from \"../../BridgeTile\";\nimport SettingsTab from \"../SettingsTab\";\nimport { SettingsSection } from \"../../shared/SettingsSection\";\nimport MatrixClientContext from \"../../../../../contexts/MatrixClientContext\";\n\nconst BRIDGE_EVENT_TYPES = [\n    \"uk.half-shot.bridge\",\n    // m.bridge\n];\n\nconst BRIDGES_LINK = \"https://matrix.org/bridges/\";\n\ninterface IProps {\n    room: Room;\n}\n\nexport default class BridgeSettingsTab extends React.Component<IProps> {\n    public static contextType = MatrixClientContext;\n    declare public context: React.ContextType<typeof MatrixClientContext>;\n\n    private renderBridgeCard(event: MatrixEvent, room: Room | null): ReactNode {\n        const content = event.getContent();\n        if (!room || !content?.channel || !content.protocol) return null;\n        return <BridgeTile key={event.getId()} room={room} ev={event} />;\n    }\n\n    public static getBridgeStateEvents(client: MatrixClient, roomId: string): MatrixEvent[] {\n        const roomState = client.getRoom(roomId)?.currentState;\n        if (!roomState) return [];\n\n        return BRIDGE_EVENT_TYPES.map((typeName) => roomState.getStateEvents(typeName)).flat(1);\n    }\n\n    public render(): React.ReactNode {\n        // This settings tab will only be invoked if the following function returns more\n        // than 0 events, so no validation is needed at this stage.\n        const bridgeEvents = BridgeSettingsTab.getBridgeStateEvents(this.context, this.props.room.roomId);\n        const room = this.props.room;\n\n        let content: JSX.Element;\n        if (bridgeEvents.length > 0) {\n            content = (\n                <div>\n                    <p>\n                        {_t(\n                            \"room_settings|bridges|description\",\n                            {},\n                            {\n                                // TODO: We don't have this link yet: this will prevent the translators\n                                // having to re-translate the string when we do.\n                                a: (sub) => (\n                                    <a href={BRIDGES_LINK} target=\"_blank\" rel=\"noreferrer noopener\">\n                                        {sub}\n                                    </a>\n                                ),\n                            },\n                        )}\n                    </p>\n                    <ul className=\"mx_RoomSettingsDialog_BridgeList\">\n                        {bridgeEvents.map((event) => this.renderBridgeCard(event, room))}\n                    </ul>\n                </div>\n            );\n        } else {\n            content = (\n                <p>\n                    {_t(\n                        \"room_settings|bridges|empty\",\n                        {},\n                        {\n                            // TODO: We don't have this link yet: this will prevent the translators\n                            // having to re-translate the string when we do.\n                            a: (sub) => (\n                                <a href={BRIDGES_LINK} target=\"_blank\" rel=\"noreferrer noopener\">\n                                    {sub}\n                                </a>\n                            ),\n                        },\n                    )}\n                </p>\n            );\n        }\n\n        return (\n            <SettingsTab>\n                <SettingsSection heading={_t(\"room_settings|bridges|title\")}>{content}</SettingsSection>\n            </SettingsTab>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEventHandler, useCallback, useMemo, useState } from \"react\";\nimport { JoinRule, EventType, type RoomState, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { type RoomPowerLevelsEventContent } from \"matrix-js-sdk/src/types\";\nimport { Form, SettingsToggleInput } from \"@vector-im/compound-web\";\n\nimport { _t } from \"../../../../../languageHandler\";\nimport { SettingsSubsection } from \"../../shared/SettingsSubsection\";\nimport SettingsTab from \"../SettingsTab\";\nimport { useRoomState } from \"../../../../../hooks/useRoomState\";\nimport SdkConfig, { DEFAULTS } from \"../../../../../SdkConfig\";\nimport { SettingsSection } from \"../../shared/SettingsSection\";\nimport { ElementCallEventType, ElementCallMemberEventType } from \"../../../../../call-types\";\n\ninterface ElementCallSwitchProps {\n    room: Room;\n}\n\nconst ElementCallSwitch: React.FC<ElementCallSwitchProps> = ({ room }) => {\n    const isPublic = useMemo(() => room.getJoinRule() === JoinRule.Public, [room]);\n    const [content, maySend] = useRoomState(\n        room,\n        useCallback(\n            (state: RoomState) => {\n                const content = state\n                    ?.getStateEvents(EventType.RoomPowerLevels, \"\")\n                    ?.getContent<RoomPowerLevelsEventContent>();\n                return [\n                    content ?? {},\n                    state?.maySendStateEvent(EventType.RoomPowerLevels, room.client.getSafeUserId()),\n                ] as const;\n            },\n            [room.client],\n        ),\n    );\n\n    const [elementCallEnabled, setElementCallEnabled] = useState<boolean>(() => {\n        return content.events?.[ElementCallMemberEventType.name] === 0;\n    });\n\n    const onChange = useCallback<ChangeEventHandler<HTMLInputElement>>(\n        (evt): void => {\n            const enabled = evt.target.checked;\n            setElementCallEnabled(enabled);\n\n            // Take a copy to avoid mutating the original\n            const newContent = { events: {}, ...content };\n\n            if (enabled) {\n                const userLevel = newContent.events[EventType.RoomMessage] ?? content.users_default ?? 0;\n                const moderatorLevel = content.kick ?? 50;\n\n                newContent.events[ElementCallEventType.name] = isPublic ? moderatorLevel : userLevel;\n                newContent.events[ElementCallMemberEventType.name] = userLevel;\n            } else {\n                const adminLevel = newContent.events[EventType.RoomPowerLevels] ?? content.state_default ?? 100;\n\n                newContent.events[ElementCallEventType.name] = adminLevel;\n                newContent.events[ElementCallMemberEventType.name] = adminLevel;\n            }\n\n            room.client.sendStateEvent(room.roomId, EventType.RoomPowerLevels, newContent);\n        },\n        [room.client, room.roomId, content, isPublic],\n    );\n\n    const brand = SdkConfig.get(\"element_call\").brand ?? DEFAULTS.element_call.brand;\n\n    return (\n        <SettingsToggleInput\n            name=\"element-call-switch\"\n            data-test-id=\"element-call-switch\"\n            label={_t(\"room_settings|voip|enable_element_call_label\", { brand })}\n            helpMessage={_t(\"room_settings|voip|enable_element_call_caption\", {\n                brand,\n            })}\n            checked={elementCallEnabled}\n            onChange={onChange}\n            disabled={!maySend}\n            disabledMessage={_t(\"room_settings|voip|enable_element_call_no_permissions_tooltip\")}\n        />\n    );\n};\n\ninterface Props {\n    room: Room;\n}\n\nexport const VoipRoomSettingsTab: React.FC<Props> = ({ room }) => {\n    return (\n        <SettingsTab>\n            <SettingsSection heading={_t(\"settings|voip|title\")}>\n                <Form.Root\n                    onSubmit={(evt) => {\n                        evt.preventDefault();\n                        evt.stopPropagation();\n                    }}\n                >\n                    <SettingsSubsection heading={_t(\"room_settings|voip|call_type_section\")}>\n                        <ElementCallSwitch room={room} />\n                    </SettingsSubsection>\n                </Form.Root>\n            </SettingsSection>\n        </SettingsTab>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useContext } from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport MatrixClientContext from \"../../../../../contexts/MatrixClientContext\";\nimport { PollHistory } from \"../../../polls/pollHistory/PollHistory\";\nimport { RoomPermalinkCreator } from \"../../../../../utils/permalinks/Permalinks\";\n\ninterface IProps {\n    room: Room;\n    onFinished: () => void;\n}\n\nexport const PollHistoryTab: React.FC<IProps> = ({ room, onFinished }) => {\n    const matrixClient = useContext(MatrixClientContext);\n    const permalinkCreator = new RoomPermalinkCreator(room, room.roomId);\n\n    return (\n        <div className=\"mx_SettingsTab\">\n            <PollHistory\n                room={room}\n                permalinkCreator={permalinkCreator}\n                matrixClient={matrixClient}\n                onFinished={onFinished}\n            />\n        </div>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 Nordeck IT + Consulting GmbH\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EventTimeline, type MatrixError, type Room, type RoomMember, RoomStateEvent } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport React, { useCallback, useState, type FC } from \"react\";\nimport { CloseIcon, CheckIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { formatRelativeTime } from \"../../../../../DateUtils\";\nimport { useTypedEventEmitterState } from \"../../../../../hooks/useEventEmitter\";\nimport { _t } from \"../../../../../languageHandler\";\nimport Modal, { type IHandle } from \"../../../../../Modal\";\nimport MemberAvatar from \"../../../avatars/MemberAvatar\";\nimport ErrorDialog from \"../../../dialogs/ErrorDialog\";\nimport AccessibleButton from \"../../../elements/AccessibleButton\";\nimport SettingsFieldset from \"../../SettingsFieldset\";\nimport { SettingsSection } from \"../../shared/SettingsSection\";\nimport SettingsTab from \"../SettingsTab\";\n\nconst Timestamp: FC<{ roomMember: RoomMember }> = ({ roomMember }) => {\n    const timestamp = roomMember.events.member?.event.origin_server_ts;\n    if (!timestamp) return null;\n    return <time className=\"mx_PeopleRoomSettingsTab_timestamp\">{formatRelativeTime(new Date(timestamp))}</time>;\n};\n\nconst SeeMoreOrLess: FC<{ roomMember: RoomMember }> = ({ roomMember }) => {\n    const [seeMore, setSeeMore] = useState(false);\n    const reason = roomMember.events.member?.getContent().reason;\n\n    if (!reason) return null;\n\n    const truncateAt = 120;\n    const shouldTruncate = reason.length > truncateAt;\n\n    return (\n        <>\n            <p className=\"mx_PeopleRoomSettingsTab_seeMoreOrLess\">\n                {seeMore || !shouldTruncate ? reason : `${reason.substring(0, truncateAt)}…`}\n            </p>\n            {shouldTruncate && (\n                <AccessibleButton kind=\"link\" onClick={() => setSeeMore(!seeMore)}>\n                    {seeMore ? _t(\"room_settings|people|see_less\") : _t(\"room_settings|people|see_more\")}\n                </AccessibleButton>\n            )}\n        </>\n    );\n};\n\nconst Knock: FC<{\n    canInvite: boolean;\n    canKick: boolean;\n    onApprove: (userId: string) => Promise<void>;\n    onDeny: (userId: string) => Promise<void>;\n    roomMember: RoomMember;\n}> = ({ canKick, canInvite, onApprove, onDeny, roomMember }) => {\n    const [disabled, setDisabled] = useState(false);\n\n    const handleApprove = (userId: string): void => {\n        setDisabled(true);\n        onApprove(userId).catch(onError);\n    };\n\n    const handleDeny = (userId: string): void => {\n        setDisabled(true);\n        onDeny(userId).catch(onError);\n    };\n\n    const onError = (): void => setDisabled(false);\n\n    return (\n        <div className=\"mx_PeopleRoomSettingsTab_knock\">\n            <MemberAvatar className=\"mx_PeopleRoomSettingsTab_avatar\" member={roomMember} size=\"42px\" />\n            <div className=\"mx_PeopleRoomSettingsTab_content\">\n                <span className=\"mx_PeopleRoomSettingsTab_name\">{roomMember.name}</span>\n                <Timestamp roomMember={roomMember} />\n                <span className=\"mx_PeopleRoomSettingsTab_userId\">{roomMember.userId}</span>\n                <SeeMoreOrLess roomMember={roomMember} />\n            </div>\n            <AccessibleButton\n                className=\"mx_PeopleRoomSettingsTab_action\"\n                disabled={!canKick || disabled}\n                kind=\"icon_primary_outline\"\n                onClick={() => handleDeny(roomMember.userId)}\n                title={_t(\"action|deny\")}\n            >\n                <CloseIcon width={18} height={18} />\n            </AccessibleButton>\n            <AccessibleButton\n                className=\"mx_PeopleRoomSettingsTab_action\"\n                disabled={!canInvite || disabled}\n                kind=\"icon_primary\"\n                onClick={() => handleApprove(roomMember.userId)}\n                title={_t(\"action|approve\")}\n            >\n                <CheckIcon width={18} height={18} />\n            </AccessibleButton>\n        </div>\n    );\n};\n\nexport const PeopleRoomSettingsTab: FC<{ room: Room }> = ({ room }) => {\n    const client = room.client;\n    const userId = client.getUserId() || \"\";\n    const canInvite = room.canInvite(userId);\n    const member = room.getMember(userId);\n    const state = room.getLiveTimeline().getState(EventTimeline.FORWARDS);\n    const canKick = member && state ? state.hasSufficientPowerLevelFor(\"kick\", member.powerLevel) : false;\n    const roomId = room.roomId;\n\n    const handleApprove = (userId: string): Promise<void> =>\n        new Promise((_, reject) =>\n            client.invite(roomId, userId).catch((error) => {\n                onError(error);\n                reject(error);\n            }),\n        );\n\n    const handleDeny = (userId: string): Promise<void> =>\n        new Promise((_, reject) =>\n            client.kick(roomId, userId).catch((error) => {\n                onError(error);\n                reject(error);\n            }),\n        );\n\n    const onError = (error: MatrixError): IHandle<typeof ErrorDialog> =>\n        Modal.createDialog(ErrorDialog, {\n            title: error.name,\n            description: error.message,\n        });\n\n    const knockMembers = useTypedEventEmitterState(\n        room,\n        RoomStateEvent.Update,\n        useCallback(() => room.getMembersWithMembership(KnownMembership.Knock), [room]),\n    );\n\n    return (\n        <SettingsTab>\n            <SettingsSection heading={_t(\"common|people\")}>\n                <SettingsFieldset legend={_t(\"room_settings|people|knock_section\")}>\n                    {knockMembers.length ? (\n                        knockMembers.map((knockMember) => (\n                            <Knock\n                                canInvite={canInvite}\n                                canKick={canKick}\n                                key={knockMember.userId}\n                                onApprove={handleApprove}\n                                onDeny={handleDeny}\n                                roomMember={knockMember}\n                            />\n                        ))\n                    ) : (\n                        <p className=\"mx_PeopleRoomSettingsTab_paragraph\">{_t(\"room_settings|people|knock_empty\")}</p>\n                    )}\n                </SettingsFieldset>\n            </SettingsSection>\n        </SettingsTab>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\nCopyright 2019 New Vector Ltd\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { RoomEvent, type Room, RoomStateEvent, type MatrixEvent, EventType } from \"matrix-js-sdk/src/matrix\";\nimport {\n    AdminIcon,\n    GroupIcon,\n    LockIcon,\n    PollsIcon,\n    SettingsIcon,\n    VoiceCallIcon,\n    NotificationsIcon,\n    AdvancedSettingsIcon,\n    TreeIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport TabbedView, { Tab } from \"../../structures/TabbedView\";\nimport { _t, _td } from \"../../../languageHandler\";\nimport AdvancedRoomSettingsTab from \"../settings/tabs/room/AdvancedRoomSettingsTab\";\nimport RolesRoomSettingsTab from \"../settings/tabs/room/RolesRoomSettingsTab\";\nimport GeneralRoomSettingsTab from \"../settings/tabs/room/GeneralRoomSettingsTab\";\nimport SecurityRoomSettingsTab from \"../settings/tabs/room/SecurityRoomSettingsTab\";\nimport NotificationSettingsTab from \"../settings/tabs/room/NotificationSettingsTab\";\nimport BridgeSettingsTab from \"../settings/tabs/room/BridgeSettingsTab\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { UIFeature } from \"../../../settings/UIFeature\";\nimport BaseDialog from \"./BaseDialog\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { VoipRoomSettingsTab } from \"../settings/tabs/room/VoipRoomSettingsTab\";\nimport { type ActionPayload } from \"../../../dispatcher/payloads\";\nimport { type NonEmptyArray } from \"../../../@types/common\";\nimport { PollHistoryTab } from \"../settings/tabs/room/PollHistoryTab\";\nimport ErrorBoundary from \"../elements/ErrorBoundary\";\nimport { PeopleRoomSettingsTab } from \"../settings/tabs/room/PeopleRoomSettingsTab\";\n\nexport const enum RoomSettingsTab {\n    General = \"ROOM_GENERAL_TAB\",\n    People = \"ROOM_PEOPLE_TAB\",\n    Voip = \"ROOM_VOIP_TAB\",\n    Security = \"ROOM_SECURITY_TAB\",\n    Roles = \"ROOM_ROLES_TAB\",\n    Notifications = \"ROOM_NOTIFICATIONS_TAB\",\n    Bridges = \"ROOM_BRIDGES_TAB\",\n    Advanced = \"ROOM_ADVANCED_TAB\",\n    PollHistory = \"ROOM_POLL_HISTORY_TAB\",\n}\n\ninterface IProps {\n    roomId: string;\n    onFinished: (success?: boolean) => void;\n    initialTabId?: RoomSettingsTab;\n}\n\ninterface IState {\n    room: Room;\n    activeTabId: RoomSettingsTab;\n}\n\nclass RoomSettingsDialog extends React.Component<IProps, IState> {\n    private dispatcherRef?: string;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        const room = this.getRoom();\n        this.state = { room, activeTabId: props.initialTabId || RoomSettingsTab.General };\n    }\n\n    public componentDidMount(): void {\n        this.dispatcherRef = dis.register(this.onAction);\n        MatrixClientPeg.safeGet().on(RoomEvent.Name, this.onRoomName);\n        MatrixClientPeg.safeGet().on(RoomStateEvent.Events, this.onStateEvent);\n        this.onRoomName();\n    }\n\n    public componentDidUpdate(): void {\n        if (this.props.roomId !== this.state.room.roomId) {\n            const room = this.getRoom();\n            this.setState({ room });\n        }\n    }\n\n    public componentWillUnmount(): void {\n        dis.unregister(this.dispatcherRef);\n\n        MatrixClientPeg.get()?.removeListener(RoomEvent.Name, this.onRoomName);\n        MatrixClientPeg.get()?.removeListener(RoomStateEvent.Events, this.onStateEvent);\n    }\n\n    /**\n     * Get room from client\n     * @returns Room\n     * @throws when room is not found\n     */\n    private getRoom(): Room {\n        const room = MatrixClientPeg.safeGet().getRoom(this.props.roomId)!;\n\n        // something is really wrong if we encounter this\n        if (!room) {\n            throw new Error(`Cannot find room ${this.props.roomId}`);\n        }\n        return room;\n    }\n\n    private onAction = (payload: ActionPayload): void => {\n        // When view changes below us, close the room settings\n        // whilst the modal is open this can only be triggered when someone hits Leave Room\n        if (payload.action === Action.ViewHomePage) {\n            this.props.onFinished(true);\n        }\n    };\n\n    private onRoomName = (): void => {\n        // rerender when the room name changes\n        this.forceUpdate();\n    };\n\n    private onStateEvent = (event: MatrixEvent): void => {\n        if (event.getType() === EventType.RoomJoinRules) this.forceUpdate();\n    };\n\n    private onTabChange = (tabId: RoomSettingsTab): void => {\n        this.setState({ activeTabId: tabId });\n    };\n\n    private getTabs(): NonEmptyArray<Tab<RoomSettingsTab>> {\n        const tabs: Tab<RoomSettingsTab>[] = [];\n\n        tabs.push(\n            new Tab(\n                RoomSettingsTab.General,\n                _td(\"common|general\"),\n                <SettingsIcon />,\n                <GeneralRoomSettingsTab room={this.state.room} />,\n                \"RoomSettingsGeneral\",\n            ),\n        );\n        if (SettingsStore.getValue(\"feature_ask_to_join\") && this.state.room.getJoinRule() === \"knock\") {\n            tabs.push(\n                new Tab(\n                    RoomSettingsTab.People,\n                    _td(\"common|people\"),\n                    <GroupIcon />,\n                    <PeopleRoomSettingsTab room={this.state.room} />,\n                ),\n            );\n        }\n        if (SettingsStore.getValue(\"feature_group_calls\")) {\n            tabs.push(\n                new Tab(\n                    RoomSettingsTab.Voip,\n                    _td(\"settings|voip|title\"),\n                    <VoiceCallIcon />,\n                    <VoipRoomSettingsTab room={this.state.room} />,\n                ),\n            );\n        }\n        tabs.push(\n            new Tab(\n                RoomSettingsTab.Security,\n                _td(\"room_settings|security|title\"),\n                <LockIcon />,\n                <SecurityRoomSettingsTab room={this.state.room} closeSettingsFn={() => this.props.onFinished(true)} />,\n                \"RoomSettingsSecurityPrivacy\",\n            ),\n        );\n        tabs.push(\n            new Tab(\n                RoomSettingsTab.Roles,\n                _td(\"room_settings|permissions|title\"),\n                <AdminIcon />,\n                <RolesRoomSettingsTab room={this.state.room} />,\n                \"RoomSettingsRolesPermissions\",\n            ),\n        );\n        tabs.push(\n            new Tab(\n                RoomSettingsTab.Notifications,\n                _td(\"notifications|enable_prompt_toast_title\"),\n                <NotificationsIcon />,\n                <NotificationSettingsTab\n                    roomId={this.state.room.roomId}\n                    closeSettingsFn={() => this.props.onFinished(true)}\n                />,\n                \"RoomSettingsNotifications\",\n            ),\n        );\n\n        if (SettingsStore.getValue(\"feature_bridge_state\")) {\n            tabs.push(\n                new Tab(\n                    RoomSettingsTab.Bridges,\n                    _td(\"room_settings|bridges|title\"),\n                    <TreeIcon />,\n                    <BridgeSettingsTab room={this.state.room} />,\n                    \"RoomSettingsBridges\",\n                ),\n            );\n        }\n\n        tabs.push(\n            new Tab(\n                RoomSettingsTab.PollHistory,\n                _td(\"right_panel|polls_button\"),\n                <PollsIcon />,\n                <PollHistoryTab room={this.state.room} onFinished={() => this.props.onFinished(true)} />,\n            ),\n        );\n\n        if (SettingsStore.getValue(UIFeature.AdvancedSettings)) {\n            tabs.push(\n                new Tab(\n                    RoomSettingsTab.Advanced,\n                    _td(\"common|advanced\"),\n                    <AdvancedSettingsIcon />,\n                    <AdvancedRoomSettingsTab\n                        room={this.state.room}\n                        closeSettingsFn={() => this.props.onFinished(true)}\n                    />,\n                    \"RoomSettingsAdvanced\",\n                ),\n            );\n        }\n\n        return tabs as NonEmptyArray<Tab<RoomSettingsTab>>;\n    }\n\n    public render(): React.ReactNode {\n        const roomName = this.state.room.name;\n        return (\n            <BaseDialog\n                className=\"mx_RoomSettingsDialog\"\n                hasCancel={true}\n                onFinished={this.props.onFinished}\n                title={_t(\"room_settings|title\", { roomName })}\n            >\n                <div className=\"mx_SettingsDialog_content\">\n                    <TabbedView\n                        tabs={this.getTabs()}\n                        activeTabId={this.state.activeTabId}\n                        screenName=\"RoomSettings\"\n                        onChange={this.onTabChange}\n                    />\n                </div>\n            </BaseDialog>\n        );\n    }\n}\n\nconst WrappedRoomSettingsDialog: React.FC<IProps> = (props) => (\n    <ErrorBoundary>\n        <RoomSettingsDialog {...props} />\n    </ErrorBoundary>\n);\n\nexport default WrappedRoomSettingsDialog;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport Modal from \"../../../Modal\";\nimport { _t } from \"../../../languageHandler\";\nimport { upgradeRoom } from \"../../../utils/RoomUpgrade\";\nimport BaseDialog from \"./BaseDialog\";\nimport ErrorDialog from \"./ErrorDialog\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport Spinner from \"../elements/Spinner\";\n\ninterface IProps {\n    room: Room;\n    onFinished(upgrade?: boolean): void;\n}\n\ninterface IState {\n    busy: boolean;\n}\n\nexport default class RoomUpgradeDialog extends React.Component<IProps, IState> {\n    private targetVersion?: string;\n\n    public state = {\n        busy: true,\n    };\n\n    public async componentDidMount(): Promise<void> {\n        const recommended = await this.props.room.getRecommendedVersion();\n        this.targetVersion = recommended.version;\n        this.setState({ busy: false });\n    }\n\n    private onCancelClick = (): void => {\n        this.props.onFinished(false);\n    };\n\n    private onUpgradeClick = (): void => {\n        this.setState({ busy: true });\n        upgradeRoom(this.props.room, this.targetVersion!, false, false)\n            .then(() => {\n                this.props.onFinished(true);\n            })\n            .catch((err) => {\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"room_settings|advanced|error_upgrade_title\"),\n                    description: err?.message ?? _t(\"room_settings|advanced|error_upgrade_description\"),\n                });\n            })\n            .finally(() => {\n                this.setState({ busy: false });\n            });\n    };\n\n    public render(): React.ReactNode {\n        let buttons: JSX.Element;\n        if (this.state.busy) {\n            buttons = <Spinner />;\n        } else {\n            buttons = (\n                <DialogButtons\n                    primaryButton={_t(\"room_settings|advanced|upgrade_button\", { version: this.targetVersion })}\n                    primaryButtonClass=\"danger\"\n                    hasCancel={true}\n                    onPrimaryButtonClick={this.onUpgradeClick}\n                    onCancel={this.onCancelClick}\n                />\n            );\n        }\n\n        return (\n            <BaseDialog\n                className=\"mx_RoomUpgradeDialog\"\n                onFinished={this.props.onFinished}\n                title={_t(\"room_settings|advanced|upgrade_dialog_title\")}\n                contentId=\"mx_Dialog_content\"\n                hasCancel={true}\n            >\n                <p>{_t(\"room_settings|advanced|upgrade_dialog_description\")}</p>\n                <ol>\n                    <li>{_t(\"room_settings|advanced|upgrade_dialog_description_1\")}</li>\n                    <li>{_t(\"room_settings|advanced|upgrade_dialog_description_2\")}</li>\n                    <li>{_t(\"room_settings|advanced|upgrade_dialog_description_3\")}</li>\n                    <li>{_t(\"room_settings|advanced|upgrade_dialog_description_4\")}</li>\n                </ol>\n                {buttons}\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEventHandler, type JSX, type ReactNode, type SyntheticEvent } from \"react\";\nimport { EventType, JoinRule } from \"matrix-js-sdk/src/matrix\";\nimport { Form, SettingsToggleInput } from \"@vector-im/compound-web\";\n\nimport { _t } from \"../../../languageHandler\";\nimport SdkConfig from \"../../../SdkConfig\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport Modal from \"../../../Modal\";\nimport BugReportDialog from \"./BugReportDialog\";\nimport BaseDialog from \"./BaseDialog\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport ProgressBar from \"../elements/ProgressBar\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\n\nexport interface IFinishedOpts {\n    continue: boolean;\n    invite: boolean;\n}\n\ninterface IProps {\n    roomId: string;\n    targetVersion: string;\n    description?: ReactNode;\n    doUpgrade?(opts: IFinishedOpts, fn: (progressText: string, progress: number, total: number) => void): Promise<void>;\n    onFinished(opts?: IFinishedOpts): void;\n}\n\ninterface Progress {\n    text: string;\n    progress: number;\n    total: number;\n}\n\ninterface IState {\n    inviteUsersToNewRoom: boolean;\n    progress?: Progress;\n}\n\nexport default class RoomUpgradeWarningDialog extends React.Component<IProps, IState> {\n    private readonly joinRule: JoinRule;\n    private readonly isInviteOrKnockRoom: boolean;\n    private readonly currentVersion?: string;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        const room = MatrixClientPeg.safeGet().getRoom(this.props.roomId);\n        const joinRules = room?.currentState.getStateEvents(EventType.RoomJoinRules, \"\");\n        this.joinRule = joinRules?.getContent()[\"join_rule\"] ?? JoinRule.Invite;\n        this.isInviteOrKnockRoom = [JoinRule.Invite, JoinRule.Knock].includes(this.joinRule);\n        this.currentVersion = room?.getVersion();\n\n        this.state = {\n            inviteUsersToNewRoom: true,\n        };\n    }\n\n    private onProgressCallback = (text: string, progress: number, total: number): void => {\n        this.setState({\n            progress: {\n                text,\n                progress,\n                total,\n            },\n        });\n    };\n\n    private onContinue = async (): Promise<void> => {\n        const opts = {\n            continue: true,\n            invite: this.isInviteOrKnockRoom && this.state.inviteUsersToNewRoom,\n        };\n\n        await this.props.doUpgrade?.(opts, this.onProgressCallback);\n        this.props.onFinished(opts);\n    };\n\n    private onCancel = (): void => {\n        this.props.onFinished({ continue: false, invite: false });\n    };\n\n    private onInviteUsersToggle: ChangeEventHandler<HTMLInputElement> = (evt): void => {\n        this.setState({ inviteUsersToNewRoom: evt.target.checked });\n    };\n\n    private openBugReportDialog = (e: SyntheticEvent): void => {\n        e.preventDefault();\n        e.stopPropagation();\n\n        Modal.createDialog(BugReportDialog, {});\n    };\n\n    public render(): React.ReactNode {\n        const brand = SdkConfig.get().brand;\n\n        let inviteToggle: JSX.Element | undefined;\n        if (this.isInviteOrKnockRoom) {\n            inviteToggle = (\n                <Form.Root\n                    onSubmit={(evt) => {\n                        evt.preventDefault();\n                        evt.stopPropagation();\n                    }}\n                >\n                    <SettingsToggleInput\n                        name=\"room-upgrade-warning\"\n                        checked={this.state.inviteUsersToNewRoom}\n                        onChange={this.onInviteUsersToggle}\n                        label={_t(\"room_settings|advanced|upgrade_warning_dialog_invite_label\")}\n                    />\n                </Form.Root>\n            );\n        }\n\n        let title: string;\n        switch (this.joinRule) {\n            case JoinRule.Invite:\n                title = _t(\"room_settings|advanced|upgrade_warning_dialog_title_private\");\n                break;\n            case JoinRule.Public:\n                title = _t(\"room_settings|advanced|upgrade_dwarning_ialog_title_public\");\n                break;\n            default:\n                title = _t(\"room_settings|advanced|upgrade_warning_dialog_title\");\n        }\n\n        let bugReports = <p>{_t(\"room_settings|advanced|upgrade_warning_dialog_report_bug_prompt\", { brand })}</p>;\n        if (SdkConfig.get().bug_report_endpoint_url) {\n            bugReports = (\n                <p>\n                    {_t(\n                        \"room_settings|advanced|upgrade_warning_dialog_report_bug_prompt_link\",\n                        {\n                            brand,\n                        },\n                        {\n                            a: (sub) => {\n                                return (\n                                    <AccessibleButton kind=\"link_inline\" onClick={this.openBugReportDialog}>\n                                        {sub}\n                                    </AccessibleButton>\n                                );\n                            },\n                        },\n                    )}\n                </p>\n            );\n        }\n\n        let footer: JSX.Element;\n        if (this.state.progress) {\n            footer = (\n                <span className=\"mx_RoomUpgradeWarningDialog_progress\">\n                    <ProgressBar value={this.state.progress.progress} max={this.state.progress.total} />\n                    <div className=\"mx_RoomUpgradeWarningDialog_progressText\">{this.state.progress.text}</div>\n                </span>\n            );\n        } else {\n            footer = (\n                <DialogButtons\n                    primaryButton={_t(\"action|upgrade\")}\n                    onPrimaryButtonClick={this.onContinue}\n                    cancelButton={_t(\"action|cancel\")}\n                    onCancel={this.onCancel}\n                />\n            );\n        }\n\n        return (\n            <BaseDialog\n                className=\"mx_RoomUpgradeWarningDialog\"\n                hasCancel={true}\n                fixedWidth={false}\n                onFinished={this.props.onFinished}\n                title={title}\n            >\n                <div>\n                    <p>{this.props.description || _t(\"room_settings|advanced|upgrade_warning_dialog_description\")}</p>\n                    <p>\n                        {_t(\n                            \"room_settings|advanced|upgrade_warning_dialog_explainer\",\n                            {},\n                            {\n                                b: (sub) => <strong>{sub}</strong>,\n                            },\n                        )}\n                    </p>\n                    {bugReports}\n                    <p>\n                        {_t(\n                            \"room_settings|advanced|upgrade_warning_dialog_footer\",\n                            {},\n                            {\n                                oldVersion: () => <code>{this.currentVersion}</code>,\n                                newVersion: () => <code>{this.props.targetVersion}</code>,\n                            },\n                        )}\n                    </p>\n                    {inviteToggle}\n                </div>\n                {footer}\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type FormEvent } from \"react\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport FocusLock from \"react-focus-lock\";\nimport { CloseIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { _t } from \"../../../languageHandler\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\n\nexport interface IScrollableBaseState {\n    canSubmit: boolean;\n    title: string;\n    actionLabel: string;\n    cancelLabel?: string;\n}\n\n/**\n * Scrollable dialog base from Compound (Web Components).\n */\nexport default abstract class ScrollableBaseModal<\n    TProps extends { onFinished?: (...args: any[]) => void },\n    TState extends IScrollableBaseState,\n> extends React.PureComponent<TProps, TState> {\n    protected constructor(props: TProps) {\n        super(props);\n    }\n\n    protected get matrixClient(): MatrixClient {\n        // XXX: The contract on MatrixClientContext says it is only available within a LoggedInView subtree,\n        // given that modals function outside the MatrixChat React tree this simulates that. We don't want to\n        // use safeGet as it throwing would mean we cannot use modals whilst the user isn't logged in.\n        // The longer term solution is to move our ModalManager into the React tree to inherit contexts properly.\n        return MatrixClientPeg.get()!;\n    }\n\n    private onKeyDown = (e: KeyboardEvent | React.KeyboardEvent): void => {\n        const action = getKeyBindingsManager().getAccessibilityAction(e);\n        switch (action) {\n            case KeyBindingAction.Escape:\n                e.stopPropagation();\n                e.preventDefault();\n                this.cancel();\n                break;\n        }\n    };\n\n    private onCancel = (): void => {\n        this.cancel();\n    };\n\n    private onSubmit = (e: MouseEvent | FormEvent): void => {\n        e.stopPropagation();\n        e.preventDefault();\n        if (!this.state.canSubmit) return; // pretend the submit button was disabled\n        this.submit();\n    };\n\n    protected abstract cancel(): void;\n    protected abstract submit(): void;\n    protected abstract renderContent(): React.ReactNode;\n\n    public render(): React.ReactNode {\n        return (\n            <MatrixClientContext.Provider value={this.matrixClient}>\n                <FocusLock\n                    returnFocus={true}\n                    lockProps={{\n                        onKeyDown: this.onKeyDown,\n                        role: \"dialog\",\n                        [\"aria-labelledby\"]: \"mx_CompoundDialog_title\",\n\n                        // Like BaseDialog, we'll just point this at the whole content\n                        [\"aria-describedby\"]: \"mx_CompoundDialog_content\",\n                    }}\n                    className=\"mx_CompoundDialog mx_ScrollableBaseDialog\"\n                >\n                    <div className=\"mx_CompoundDialog_header\">\n                        <h1>{this.state.title}</h1>\n                    </div>\n                    <AccessibleButton\n                        onClick={this.onCancel}\n                        className=\"mx_CompoundDialog_cancelButton\"\n                        aria-label={_t(\"dialog_close_label\")}\n                    >\n                        <CloseIcon />\n                    </AccessibleButton>\n                    <form onSubmit={this.onSubmit} className=\"mx_CompoundDialog_form\">\n                        <div className=\"mx_CompoundDialog_content\">{this.renderContent()}</div>\n                        <div className=\"mx_CompoundDialog_footer\">\n                            <AccessibleButton onClick={this.onCancel} kind=\"primary_outline\">\n                                {this.state.cancelLabel ?? _t(\"action|cancel\")}\n                            </AccessibleButton>\n                            <AccessibleButton\n                                onClick={this.onSubmit}\n                                kind=\"primary\"\n                                disabled={!this.state.canSubmit}\n                                type=\"submit\"\n                                element=\"button\"\n                                className=\"mx_Dialog_nonDialogButton\"\n                            >\n                                {this.state.actionLabel}\n                            </AccessibleButton>\n                        </div>\n                    </form>\n                </FocusLock>\n            </MatrixClientContext.Provider>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useMemo, useRef, useState } from \"react\";\nimport { Room, RoomMember, MatrixEvent, User } from \"matrix-js-sdk/src/matrix\";\nimport { Checkbox, Button } from \"@vector-im/compound-web\";\nimport LinkIcon from \"@vector-im/compound-design-tokens/assets/web/icons/link\";\nimport CheckIcon from \"@vector-im/compound-design-tokens/assets/web/icons/check\";\n\nimport { _t } from \"../../../languageHandler\";\nimport QRCode from \"../elements/QRCode\";\nimport { RoomPermalinkCreator, makeUserPermalink } from \"../../../utils/permalinks/Permalinks\";\nimport { copyPlaintext } from \"../../../utils/strings\";\nimport { UIFeature } from \"../../../settings/UIFeature\";\nimport BaseDialog from \"./BaseDialog\";\nimport { type XOR } from \"../../../@types/common\";\nimport { useSettingValue } from \"../../../hooks/useSettings.ts\";\n\n/* eslint-disable @typescript-eslint/no-require-imports */\nconst SOCIALS = [\n    {\n        name: \"Facebook\",\n        img: require(\"../../../../res/img/social/facebook.png\"),\n        url: (url: string) => `https://www.facebook.com/sharer/sharer.php?u=${url}`,\n    },\n    {\n        name: \"Twitter\",\n        img: require(\"../../../../res/img/social/twitter-2.png\"),\n        url: (url: string) => `https://twitter.com/home?status=${url}`,\n    },\n    {\n        name: \"LinkedIn\",\n        img: require(\"../../../../res/img/social/linkedin.png\"),\n        url: (url: string) => `https://www.linkedin.com/shareArticle?mini=true&url=${url}`,\n    },\n    {\n        name: \"Reddit\",\n        img: require(\"../../../../res/img/social/reddit.png\"),\n        url: (url: string) => `https://www.reddit.com/submit?url=${url}`,\n    },\n    {\n        name: \"email\",\n        img: require(\"../../../../res/img/social/email-1.png\"),\n        url: (url: string) => `mailto:?body=${url}`,\n    },\n];\n/* eslint-enable @typescript-eslint/no-require-imports */\n\ninterface BaseProps {\n    /**\n     * A function that is called when the dialog is dismissed\n     */\n    onFinished(): void;\n    /**\n     * An optional string to use as the dialog title.\n     * If not provided, an appropriate title for the target type will be used.\n     */\n    customTitle?: string;\n    /**\n     * An optional string to use as the dialog subtitle\n     */\n    subtitle?: string;\n}\n\ninterface Props extends BaseProps {\n    /**\n     * The target to link to.\n     * This can be a Room, User, RoomMember, or MatrixEvent or an already computed URL.\n     * A <u>matrix.to</u> link will be generated out of it if it's not already a url.\n     */\n    target: Room | User | RoomMember | URL;\n    /**\n     * Optional when the target is a Room, User, RoomMember or a URL.\n     * Mandatory when the target is a MatrixEvent.\n     */\n    permalinkCreator?: RoomPermalinkCreator;\n}\n\ninterface EventProps extends BaseProps {\n    /**\n     * The target to link to.\n     */\n    target: MatrixEvent;\n    /**\n     * Optional when the target is a Room, User, RoomMember or a URL.\n     * Mandatory when the target is a MatrixEvent.\n     */\n    permalinkCreator: RoomPermalinkCreator;\n}\n\ntype ShareDialogProps = XOR<Props, EventProps>;\n\n/**\n * A dialog to share a link to a room, user, room member or a matrix event.\n */\nexport function ShareDialog({ target, customTitle, onFinished, permalinkCreator }: ShareDialogProps): JSX.Element {\n    const showQrCode = useSettingValue(UIFeature.ShareQRCode);\n    const showSocials = useSettingValue(UIFeature.ShareSocial);\n\n    const timeoutIdRef = useRef<number>(undefined);\n    const [isCopied, setIsCopied] = useState(false);\n\n    const [linkToSpecificEvent, setLinkToSpecificEvent] = useState(target instanceof MatrixEvent);\n    const { title, url, checkboxLabel } = useTargetValues(target, linkToSpecificEvent, permalinkCreator);\n    const newTitle = customTitle ?? title;\n\n    return (\n        <BaseDialog\n            title={newTitle}\n            className=\"mx_ShareDialog\"\n            contentId=\"mx_Dialog_content\"\n            onFinished={onFinished}\n            fixedWidth={false}\n        >\n            <div className=\"mx_ShareDialog_content\">\n                <div className=\"mx_ShareDialog_top\">\n                    {showQrCode && <QRCode data={url} width={200} />}\n                    <span>{url}</span>\n                </div>\n                {checkboxLabel && (\n                    <label>\n                        <Checkbox\n                            defaultChecked={linkToSpecificEvent}\n                            onChange={(evt) => setLinkToSpecificEvent(evt.target.checked)}\n                        />\n                        {checkboxLabel}\n                    </label>\n                )}\n                <Button\n                    Icon={isCopied ? CheckIcon : LinkIcon}\n                    onClick={async () => {\n                        clearTimeout(timeoutIdRef.current);\n                        await copyPlaintext(url);\n                        setIsCopied(true);\n                        timeoutIdRef.current = setTimeout(() => setIsCopied(false), 2000);\n                    }}\n                >\n                    {isCopied ? _t(\"share|link_copied\") : _t(\"action|copy_link\")}\n                </Button>\n                {showSocials && <SocialLinks url={url} />}\n            </div>\n        </BaseDialog>\n    );\n}\n\n/**\n * Social links to share the link on different platforms.\n */\ninterface SocialLinksProps {\n    /**\n     * The URL to share.\n     */\n    url: string;\n}\n\n/**\n * The socials to share the link on.\n */\nfunction SocialLinks({ url }: SocialLinksProps): JSX.Element {\n    return (\n        <div className=\"mx_ShareDialog_social\">\n            {SOCIALS.map((social) => (\n                <a\n                    key={social.name}\n                    href={social.url(url)}\n                    target=\"_blank\"\n                    rel=\"noreferrer noopener\"\n                    title={social.name}\n                >\n                    <img src={social.img} alt={social.name} />\n                </a>\n            ))}\n        </div>\n    );\n}\n\n/**\n * Get the title, url and checkbox label for the dialog based on the target.\n * @param target\n * @param linkToSpecificEvent\n * @param permalinkCreator\n */\nfunction useTargetValues(\n    target: ShareDialogProps[\"target\"],\n    linkToSpecificEvent: boolean,\n    permalinkCreator?: RoomPermalinkCreator,\n): { title: string; url: string; checkboxLabel?: string } {\n    return useMemo(() => {\n        if (target instanceof URL) return { title: _t(\"share|title_link\"), url: target.toString() };\n        if (target instanceof User || target instanceof RoomMember)\n            return {\n                title: _t(\"share|title_user\"),\n                url: makeUserPermalink(target.userId),\n            };\n\n        if (target instanceof Room) {\n            const title = _t(\"share|title_room\");\n            const newPermalinkCreator = new RoomPermalinkCreator(target);\n            newPermalinkCreator.load();\n\n            const events = target.getLiveTimeline().getEvents();\n            return {\n                title,\n                url: linkToSpecificEvent\n                    ? newPermalinkCreator.forEvent(events[events.length - 1].getId()!)\n                    : newPermalinkCreator.forShareableRoom(),\n                ...(events.length > 0 && { checkboxLabel: _t(\"share|permalink_most_recent\") }),\n            };\n        }\n\n        // MatrixEvent is remaining and should have a permalinkCreator\n        const url = linkToSpecificEvent\n            ? permalinkCreator!.forEvent(target.getId()!)\n            : permalinkCreator!.forShareableRoom();\n        return {\n            title: _t(\"share|title_message\"),\n            url,\n            checkboxLabel: _t(\"share|permalink_message\"),\n        };\n    }, [target, linkToSpecificEvent, permalinkCreator]);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEvent, createRef } from \"react\";\n\nimport Field from \"../elements/Field\";\nimport { _t, _td } from \"../../../languageHandler\";\nimport { type IFieldState, type IValidationResult } from \"../elements/Validation\";\nimport BaseDialog from \"./BaseDialog\";\nimport DialogButtons from \"../elements/DialogButtons\";\n\ninterface IProps {\n    title: string;\n    description: React.ReactNode;\n    value: string;\n    placeholder?: string;\n    button?: string;\n    busyMessage: TranslationKey;\n    focus: boolean;\n    hasCancel: boolean;\n    validator?: (fieldState: IFieldState) => Promise<IValidationResult>; // result of withValidation\n    fixedWidth?: boolean;\n    onFinished(ok?: false, text?: void): void;\n    onFinished(ok: true, text: string): void;\n}\n\ninterface IState {\n    value: string;\n    busy: boolean;\n    valid: boolean;\n}\n\nexport default class TextInputDialog extends React.Component<IProps, IState> {\n    private field = createRef<Field>();\n\n    public static defaultProps: Partial<IProps> = {\n        title: \"\",\n        value: \"\",\n        description: \"\",\n        busyMessage: _td(\"common|loading\"),\n        focus: true,\n        hasCancel: true,\n    };\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            value: this.props.value,\n            busy: false,\n            valid: false,\n        };\n    }\n\n    public componentDidMount(): void {\n        if (this.props.focus) {\n            // Set the cursor at the end of the text input\n            // this._field.current.value = this.props.value;\n            this.field.current?.focus();\n        }\n    }\n\n    private onOk = async (ev: React.FormEvent): Promise<void> => {\n        ev.preventDefault();\n        if (!this.field.current) return;\n        if (this.props.validator) {\n            this.setState({ busy: true });\n            await this.field.current.validate({ allowEmpty: false });\n\n            if (!this.field.current.state.valid) {\n                this.field.current.focus();\n                this.field.current.validate({ allowEmpty: false, focused: true });\n                this.setState({ busy: false });\n                return;\n            }\n        }\n        this.props.onFinished(true, this.state.value);\n    };\n\n    private onCancel = (): void => {\n        this.props.onFinished(false);\n    };\n\n    private onChange = (ev: ChangeEvent<HTMLInputElement>): void => {\n        this.setState({\n            value: ev.target.value,\n        });\n    };\n\n    private onValidate = async (fieldState: IFieldState): Promise<IValidationResult> => {\n        const result = await this.props.validator!(fieldState);\n        this.setState({\n            valid: !!result.valid,\n        });\n        return result;\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <BaseDialog\n                className=\"mx_TextInputDialog\"\n                onFinished={this.props.onFinished}\n                title={this.props.title}\n                fixedWidth={this.props.fixedWidth}\n            >\n                <form onSubmit={this.onOk}>\n                    <div className=\"mx_Dialog_content\">\n                        <div className=\"mx_TextInputDialog_label\">\n                            <label htmlFor=\"textinput\"> {this.props.description} </label>\n                        </div>\n                        <div>\n                            <Field\n                                className=\"mx_TextInputDialog_input\"\n                                ref={this.field}\n                                type=\"text\"\n                                label={this.props.placeholder}\n                                value={this.state.value}\n                                onChange={this.onChange}\n                                onValidate={this.props.validator ? this.onValidate : undefined}\n                            />\n                        </div>\n                    </div>\n                </form>\n                <DialogButtons\n                    primaryButton={this.state.busy ? _t(this.props.busyMessage) : this.props.button}\n                    disabled={this.state.busy}\n                    onPrimaryButtonClick={this.onOk}\n                    onCancel={this.onCancel}\n                    hasCancel={this.props.hasCancel}\n                />\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { FilesIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport BaseDialog from \"./BaseDialog\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport { fileSize } from \"../../../utils/FileUtils\";\n\ninterface IProps {\n    file: File;\n    currentIndex: number;\n    totalFiles: number;\n    onFinished: (uploadConfirmed: boolean, uploadAll?: boolean) => void;\n}\n\ninterface IState {\n    objectUrl?: string;\n}\n\nexport default class UploadConfirmDialog extends React.Component<IProps, IState> {\n    public static defaultProps: Partial<IProps> = {\n        totalFiles: 1,\n        currentIndex: 0,\n    };\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {};\n    }\n\n    public componentDidMount(): void {\n        if (this.props.file.type.startsWith(\"image/\") || this.props.file.type.startsWith(\"video/\")) {\n            this.setState({\n                // We do not filter the mimetype using getBlobSafeMimeType here as if the user is uploading the file\n                // themselves they should be trusting it enough to open/load it, and it will be rendered into a hidden\n                // canvas for thumbnail generation anyway\n                objectUrl: URL.createObjectURL(this.props.file),\n            });\n        }\n    }\n\n    public componentWillUnmount(): void {\n        if (this.state.objectUrl) URL.revokeObjectURL(this.state.objectUrl);\n    }\n\n    private onCancelClick = (): void => {\n        this.props.onFinished(false);\n    };\n\n    private onUploadClick = (): void => {\n        this.props.onFinished(true);\n    };\n\n    private onUploadAllClick = (): void => {\n        this.props.onFinished(true, true);\n    };\n\n    public render(): React.ReactNode {\n        let title: string;\n        if (this.props.totalFiles > 1 && this.props.currentIndex !== undefined) {\n            title = _t(\"upload_file|title_progress\", {\n                current: this.props.currentIndex + 1,\n                total: this.props.totalFiles,\n            });\n        } else {\n            title = _t(\"upload_file|title\");\n        }\n\n        const fileId = `mx-uploadconfirmdialog-${this.props.file.name}`;\n        const mimeType = this.props.file.type;\n\n        let preview: JSX.Element | undefined;\n        let placeholder: JSX.Element | undefined;\n        if (mimeType.startsWith(\"image/\")) {\n            preview = (\n                <img\n                    className=\"mx_UploadConfirmDialog_imagePreview\"\n                    src={this.state.objectUrl}\n                    aria-labelledby={fileId}\n                />\n            );\n        } else if (mimeType.startsWith(\"video/\")) {\n            preview = (\n                <video\n                    className=\"mx_UploadConfirmDialog_imagePreview\"\n                    src={this.state.objectUrl}\n                    playsInline\n                    controls={false}\n                />\n            );\n        } else {\n            placeholder = <FilesIcon className=\"mx_UploadConfirmDialog_fileIcon\" height=\"18px\" width=\"18px\" />;\n        }\n\n        let uploadAllButton: JSX.Element | undefined;\n        if (this.props.currentIndex + 1 < this.props.totalFiles) {\n            uploadAllButton = <button onClick={this.onUploadAllClick}>{_t(\"upload_file|upload_all_button\")}</button>;\n        }\n\n        return (\n            <BaseDialog\n                className=\"mx_UploadConfirmDialog\"\n                fixedWidth={false}\n                onFinished={this.onCancelClick}\n                title={title}\n                contentId=\"mx_Dialog_content\"\n            >\n                <div id=\"mx_Dialog_content\">\n                    <div className=\"mx_UploadConfirmDialog_previewOuter\">\n                        <div className=\"mx_UploadConfirmDialog_previewInner\">\n                            {preview && <div>{preview}</div>}\n                            <div id={fileId}>\n                                {placeholder}\n                                {this.props.file.name} ({fileSize(this.props.file.size)})\n                            </div>\n                        </div>\n                    </div>\n                </div>\n\n                <DialogButtons\n                    primaryButton={_t(\"action|upload\")}\n                    hasCancel={false}\n                    onPrimaryButtonClick={this.onUploadClick}\n                    focus={true}\n                >\n                    {uploadAllButton}\n                </DialogButtons>\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport enum UserTab {\n    Account = \"USER_ACCOUNT_TAB\",\n    Appearance = \"USER_APPEARANCE_TAB\",\n    Notifications = \"USER_NOTIFICATIONS_TAB\",\n    Preferences = \"USER_PREFERENCES_TAB\",\n    Keyboard = \"USER_KEYBOARD_TAB\",\n    Sidebar = \"USER_SIDEBAR_TAB\",\n    Voice = \"USER_VOICE_TAB\",\n    Security = \"USER_SECURITY_TAB\",\n    Encryption = \"USER_ENCRYPTION_TAB\",\n    Labs = \"USER_LABS_TAB\",\n    Mjolnir = \"USER_MJOLNIR_TAB\",\n    Help = \"USER_HELP_TAB\",\n    SessionManager = \"USER_SESSION_MANAGER_TAB\",\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\nCopyright 2022 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createContext, type ReactNode, useState } from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport classNames from \"classnames\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport { type XOR } from \"../../../../@types/common\";\nimport { type Tool } from \"../DevtoolsDialog\";\n\nexport interface IDevtoolsProps {\n    onBack(): void;\n    setTool(label: TranslationKey, tool: Tool): void;\n}\n\ninterface IMinProps extends Pick<IDevtoolsProps, \"onBack\"> {\n    className?: string;\n    children?: ReactNode;\n    extraButton?: ReactNode;\n}\n\ninterface IProps extends IMinProps {\n    actionLabel: TranslationKey;\n    onAction(): Promise<string | void>;\n}\n\nconst BaseTool: React.FC<XOR<IMinProps, IProps>> = ({\n    className,\n    actionLabel,\n    onBack,\n    onAction,\n    children,\n    extraButton,\n}) => {\n    const [message, setMessage] = useState<string | null>(null);\n\n    const onBackClick = (): void => {\n        if (message) {\n            setMessage(null);\n        } else {\n            onBack();\n        }\n    };\n\n    let actionButton: ReactNode = null;\n    if (message) {\n        children = message;\n    } else if (onAction && actionLabel) {\n        const onActionClick = (): void => {\n            onAction().then((msg) => {\n                if (typeof msg === \"string\") {\n                    setMessage(msg);\n                }\n            });\n        };\n\n        actionButton = <button onClick={onActionClick}>{_t(actionLabel)}</button>;\n    }\n\n    return (\n        <>\n            <div className={classNames(\"mx_DevTools_content\", className)}>{children}</div>\n            <div className=\"mx_Dialog_buttons\">\n                {extraButton}\n                <button onClick={onBackClick}>{_t(\"action|back\")}</button>\n                {actionButton}\n            </div>\n        </>\n    );\n};\n\nexport default BaseTool;\n\ninterface IContext {\n    room: Room;\n    threadRootId?: string | null;\n}\n\nexport const DevtoolsContext = createContext<IContext>({} as IContext);\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\nCopyright 2022 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEvent, type ReactNode, useContext, useMemo, useRef, useState } from \"react\";\nimport { type IContent, type MatrixEvent, type TimelineEvents } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t, _td } from \"../../../../languageHandler\";\nimport Field from \"../../elements/Field\";\nimport BaseTool, { DevtoolsContext, type IDevtoolsProps } from \"./BaseTool\";\nimport MatrixClientContext from \"../../../../contexts/MatrixClientContext\";\nimport withValidation from \"../../elements/Validation\";\nimport SyntaxHighlight from \"../../elements/SyntaxHighlight\";\n\nexport const stringify = (object: object): string => {\n    return JSON.stringify(object, null, 2);\n};\n\ninterface IEventEditorProps extends Pick<IDevtoolsProps, \"onBack\"> {\n    fieldDefs: IFieldDef[]; // immutable\n    defaultContent?: string;\n    onSend(fields: string[], content: IContent): Promise<unknown>;\n}\n\ninterface IFieldDef {\n    id: string;\n    label: TranslationKey;\n    default?: string;\n}\n\nexport const eventTypeField = (defaultValue?: string): IFieldDef => ({\n    id: \"eventType\",\n    label: _td(\"devtools|event_type\"),\n    default: defaultValue,\n});\n\nexport const stateKeyField = (defaultValue?: string): IFieldDef => ({\n    id: \"stateKey\",\n    label: _td(\"devtools|state_key\"),\n    default: defaultValue,\n});\n\nconst validateEventContent = withValidation<any, Error | undefined>({\n    async deriveData({ value }) {\n        try {\n            JSON.parse(value!);\n        } catch (e) {\n            return e as Error;\n        }\n        return undefined;\n    },\n    rules: [\n        {\n            key: \"validJson\",\n            test: ({ value }, error) => {\n                if (!value) return true;\n                return !error;\n            },\n            invalid: (error) => _t(\"devtools|invalid_json\") + \" \" + error,\n        },\n    ],\n});\n\nexport const EventEditor: React.FC<IEventEditorProps> = ({ fieldDefs, defaultContent = \"{\\n\\n}\", onSend, onBack }) => {\n    const [fieldData, setFieldData] = useState<string[]>(fieldDefs.map((def) => def.default ?? \"\"));\n    const [content, setContent] = useState<string>(defaultContent);\n    const contentField = useRef<Field>(null);\n\n    const fields = fieldDefs.map((def, i) => (\n        <Field\n            key={def.id}\n            id={def.id}\n            label={_t(def.label)}\n            size={42}\n            autoFocus={defaultContent === undefined && i === 0}\n            type=\"text\"\n            autoComplete=\"on\"\n            value={fieldData[i]}\n            onChange={(ev: ChangeEvent<HTMLInputElement>) =>\n                setFieldData((data) => {\n                    data[i] = ev.target.value;\n                    return [...data];\n                })\n            }\n        />\n    ));\n\n    const onAction = async (): Promise<string | undefined> => {\n        const valid = contentField.current ? await contentField.current.validate({}) : false;\n\n        if (!valid) {\n            contentField.current?.focus();\n            contentField.current?.validate({ focused: true });\n            return;\n        }\n\n        try {\n            const json = JSON.parse(content);\n            await onSend(fieldData, json);\n        } catch (e) {\n            return _t(\"devtools|failed_to_send\") + (e instanceof Error ? ` (${e.message})` : \"\");\n        }\n        return _t(\"devtools|event_sent\");\n    };\n\n    return (\n        <BaseTool actionLabel={_td(\"forward|send_label\")} onAction={onAction} onBack={onBack}>\n            <div className=\"mx_DevTools_eventTypeStateKeyGroup\">{fields}</div>\n\n            <Field\n                id=\"evContent\"\n                label={_t(\"devtools|event_content\")}\n                type=\"text\"\n                className=\"mx_DevTools_textarea\"\n                autoComplete=\"off\"\n                value={content}\n                onChange={(ev) => setContent(ev.target.value)}\n                element=\"textarea\"\n                onValidate={validateEventContent}\n                ref={contentField}\n                autoFocus={!!defaultContent}\n            />\n        </BaseTool>\n    );\n};\n\nexport interface IEditorProps extends Pick<IDevtoolsProps, \"onBack\"> {\n    mxEvent?: MatrixEvent;\n}\n\ninterface IViewerProps extends Required<IEditorProps> {\n    Editor: React.FC<IEditorProps>;\n    extraButton?: ReactNode;\n}\n\nexport const EventViewer: React.FC<IViewerProps> = ({ mxEvent, onBack, Editor, extraButton }) => {\n    const [editing, setEditing] = useState(false);\n\n    if (editing) {\n        const onBack = (): void => {\n            setEditing(false);\n        };\n        return <Editor mxEvent={mxEvent} onBack={onBack} />;\n    }\n\n    const onAction = async (): Promise<void> => {\n        setEditing(true);\n    };\n\n    return (\n        <BaseTool onBack={onBack} actionLabel={_td(\"action|edit\")} onAction={onAction} extraButton={extraButton}>\n            <SyntaxHighlight language=\"json\">{stringify(mxEvent.event)}</SyntaxHighlight>\n        </BaseTool>\n    );\n};\n\n// returns the id of the initial message, not the id of the previous edit\nconst getBaseEventId = (baseEvent: MatrixEvent): string => {\n    // show the replacing event, not the original, if it is an edit\n    const mxEvent = baseEvent.replacingEvent() ?? baseEvent;\n    return mxEvent.getWireContent()[\"m.relates_to\"]?.event_id ?? baseEvent.getId()!;\n};\n\nexport const TimelineEventEditor: React.FC<IEditorProps> = ({ mxEvent, onBack }) => {\n    const context = useContext(DevtoolsContext);\n    const cli = useContext(MatrixClientContext);\n\n    const fields = useMemo(() => [eventTypeField(mxEvent?.getType())], [mxEvent]);\n\n    const onSend = ([eventType]: string[], content: TimelineEvents[keyof TimelineEvents]): Promise<unknown> => {\n        return cli.sendEvent(context.room.roomId, eventType as keyof TimelineEvents, content);\n    };\n\n    let defaultContent: string | undefined;\n\n    if (mxEvent) {\n        const originalContent = mxEvent.getContent();\n        // prefill an edit-message event, keep only the `body` and `msgtype` fields of originalContent\n        const bodyToStartFrom = originalContent[\"m.new_content\"]?.body ?? originalContent.body; // prefill the last edit body, to start editing from there\n        const newContent = {\n            \"body\": ` * ${bodyToStartFrom}`,\n            \"msgtype\": originalContent.msgtype,\n            \"m.new_content\": {\n                body: bodyToStartFrom,\n                msgtype: originalContent.msgtype,\n            },\n            \"m.relates_to\": {\n                rel_type: \"m.replace\",\n                event_id: getBaseEventId(mxEvent),\n            },\n        };\n\n        defaultContent = stringify(newContent);\n    } else if (context.threadRootId) {\n        defaultContent = stringify({\n            \"m.relates_to\": {\n                rel_type: \"m.thread\",\n                event_id: context.threadRootId,\n            },\n        });\n    }\n\n    return <EventEditor fieldDefs={fields} defaultContent={defaultContent} onSend={onSend} onBack={onBack} />;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\nCopyright 2022 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ChangeEvent, useEffect, useState } from \"react\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport Field from \"../../elements/Field\";\nimport TruncatedList from \"../../elements/TruncatedList\";\n\nconst INITIAL_LOAD_TILES = 20;\nconst LOAD_TILES_STEP_SIZE = 50;\n\ninterface IProps {\n    children: React.ReactElement[];\n    query: string;\n    onChange(value: string): void;\n}\n\nconst FilteredList: React.FC<IProps> = ({ children, query, onChange }) => {\n    const [truncateAt, setTruncateAt] = useState<number>(INITIAL_LOAD_TILES);\n    const [filteredChildren, setFilteredChildren] = useState<React.ReactElement[]>(children);\n\n    useEffect(() => {\n        let filteredChildren = children;\n        if (query) {\n            const lcQuery = query.toLowerCase();\n            filteredChildren = children.filter((child) => child.key?.toString().toLowerCase().includes(lcQuery));\n        }\n        setFilteredChildren(filteredChildren);\n        setTruncateAt(INITIAL_LOAD_TILES);\n    }, [children, query]);\n\n    const getChildren = (start: number, end: number): React.ReactElement[] => {\n        return filteredChildren.slice(start, end);\n    };\n\n    const getChildCount = (): number => {\n        return filteredChildren.length;\n    };\n\n    const createOverflowElement = (overflowCount: number, totalCount: number): JSX.Element => {\n        const showMore = (): void => {\n            setTruncateAt((num) => num + LOAD_TILES_STEP_SIZE);\n        };\n\n        return (\n            <button className=\"mx_DevTools_button\" onClick={showMore}>\n                {_t(\"common|and_n_others\", { count: overflowCount })}\n            </button>\n        );\n    };\n\n    return (\n        <>\n            <Field\n                label={_t(\"common|filter_results\")}\n                autoFocus={true}\n                size={64}\n                type=\"text\"\n                autoComplete=\"off\"\n                value={query}\n                onChange={(ev: ChangeEvent<HTMLInputElement>) => onChange(ev.target.value)}\n                className=\"mx_TextInputDialog_input mx_DevTools_RoomStateExplorer_query\"\n                // force re-render so that autoFocus is applied when this component is re-used\n                key={children?.[0]?.key ?? \"\"}\n            />\n\n            {filteredChildren.length < 1 ? (\n                _t(\"common|no_results_found\")\n            ) : (\n                <TruncatedList\n                    getChildren={getChildren}\n                    getChildCount={getChildCount}\n                    truncateAt={truncateAt}\n                    createOverflowElement={createOverflowElement}\n                />\n            )}\n        </>\n    );\n};\n\nexport default FilteredList;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\nCopyright 2022 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEventHandler, useCallback, useContext, useEffect, useMemo, useState } from \"react\";\nimport { type IContent, type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport classNames from \"classnames\";\nimport { Form, SettingsToggleInput } from \"@vector-im/compound-web\";\n\nimport { _t, _td } from \"../../../../languageHandler\";\nimport BaseTool, { DevtoolsContext, type IDevtoolsProps } from \"./BaseTool\";\nimport MatrixClientContext from \"../../../../contexts/MatrixClientContext\";\nimport { EventEditor, EventViewer, eventTypeField, stateKeyField, type IEditorProps, stringify } from \"./Event\";\nimport FilteredList from \"./FilteredList\";\nimport Spinner from \"../../elements/Spinner\";\nimport SyntaxHighlight from \"../../elements/SyntaxHighlight\";\nimport { useAsyncMemo } from \"../../../../hooks/useAsyncMemo\";\n\nexport const StateEventEditor: React.FC<IEditorProps> = ({ mxEvent, onBack }) => {\n    const context = useContext(DevtoolsContext);\n    const cli = useContext(MatrixClientContext);\n\n    const fields = useMemo(\n        () => [eventTypeField(mxEvent?.getType()), stateKeyField(mxEvent?.getStateKey())],\n        [mxEvent],\n    );\n\n    const onSend = async ([eventType, stateKey]: string[], content: IContent): Promise<void> => {\n        await cli.sendStateEvent(context.room.roomId, eventType as any, content, stateKey);\n    };\n\n    const defaultContent = mxEvent ? stringify(mxEvent.getContent()) : undefined;\n    return <EventEditor fieldDefs={fields} defaultContent={defaultContent} onSend={onSend} onBack={onBack} />;\n};\n\ninterface StateEventButtonProps {\n    label: string;\n    onClick(): void;\n}\n\nconst RoomStateHistory: React.FC<{\n    mxEvent: MatrixEvent;\n    onBack(): void;\n}> = ({ mxEvent, onBack }) => {\n    const cli = useContext(MatrixClientContext);\n    const events = useAsyncMemo(\n        async () => {\n            const events = [mxEvent.event];\n            while (!!events[0].unsigned?.replaces_state) {\n                try {\n                    events.unshift(await cli.fetchRoomEvent(mxEvent.getRoomId()!, events[0].unsigned.replaces_state));\n                } catch (e) {\n                    events.unshift({\n                        event_id: events[0].unsigned.replaces_state,\n                        unsigned: {\n                            error: e instanceof Error ? e.message : String(e),\n                        },\n                    });\n                }\n            }\n            return events;\n        },\n        [cli, mxEvent],\n        null,\n    );\n\n    let body = <Spinner />;\n    if (events !== null) {\n        body = (\n            <>\n                {events.map((ev) => (\n                    <SyntaxHighlight language=\"json\" key={ev.event_id}>\n                        {stringify(ev)}\n                    </SyntaxHighlight>\n                ))}\n            </>\n        );\n    }\n\n    return <BaseTool onBack={onBack}>{body}</BaseTool>;\n};\n\nconst StateEventButton: React.FC<StateEventButtonProps> = ({ label, onClick }) => {\n    const trimmed = label.trim();\n\n    let content = label;\n    if (!trimmed) {\n        content = label.length > 0 ? _t(\"devtools|spaces\", { count: label.length }) : _t(\"devtools|empty_string\");\n    }\n\n    return (\n        <button\n            className={classNames(\"mx_DevTools_button\", {\n                mx_DevTools_RoomStateExplorer_button_hasSpaces: trimmed.length !== label.length,\n                mx_DevTools_RoomStateExplorer_button_emptyString: !trimmed,\n            })}\n            onClick={onClick}\n        >\n            {content}\n        </button>\n    );\n};\n\ninterface IEventTypeProps extends Pick<IDevtoolsProps, \"onBack\"> {\n    eventType: string;\n}\n\nconst RoomStateExplorerEventType: React.FC<IEventTypeProps> = ({ eventType, onBack }) => {\n    const context = useContext(DevtoolsContext);\n    const [query, setQuery] = useState(\"\");\n    const [event, setEvent] = useState<MatrixEvent | null>(null);\n    const [history, setHistory] = useState(false);\n    const [showEmptyState, setShowEmptyState] = useState(true);\n    const onEmptyStateToggled = useCallback<ChangeEventHandler<HTMLInputElement>>(\n        (e) => setShowEmptyState(e.target.checked),\n        [setShowEmptyState],\n    );\n\n    const events = context.room.currentState.events.get(eventType)!;\n\n    useEffect(() => {\n        if (events.size === 1 && events.has(\"\")) {\n            setEvent(events.get(\"\")!);\n        } else {\n            setEvent(null);\n        }\n    }, [events]);\n\n    if (event && history) {\n        const _onBack = (): void => {\n            setHistory(false);\n        };\n        return <RoomStateHistory mxEvent={event} onBack={_onBack} />;\n    }\n    if (event) {\n        const _onBack = (): void => {\n            if (events?.size === 1 && events.has(\"\")) {\n                onBack();\n            } else {\n                setEvent(null);\n            }\n        };\n        const onHistoryClick = (): void => {\n            setHistory(true);\n        };\n        const extraButton = <button onClick={onHistoryClick}>{_t(\"devtools|see_history\")}</button>;\n        return <EventViewer mxEvent={event} onBack={_onBack} Editor={StateEventEditor} extraButton={extraButton} />;\n    }\n\n    return (\n        <BaseTool onBack={onBack}>\n            <FilteredList query={query} onChange={setQuery}>\n                {Array.from(events.entries())\n                    .filter(([_, ev]) => showEmptyState || Object.keys(ev.getContent()).length > 0)\n                    .map(([stateKey, ev]) => (\n                        <StateEventButton key={stateKey} label={stateKey} onClick={() => setEvent(ev)} />\n                    ))}\n            </FilteredList>\n            <Form.Root\n                onSubmit={(evt) => {\n                    evt.preventDefault();\n                    evt.stopPropagation();\n                }}\n            >\n                <SettingsToggleInput\n                    name=\"empty_state_toggle\"\n                    label={_t(\"devtools|show_empty_content_events\")}\n                    onChange={onEmptyStateToggled}\n                    checked={showEmptyState}\n                />\n            </Form.Root>\n        </BaseTool>\n    );\n};\n\nexport const RoomStateExplorer: React.FC<IDevtoolsProps> = ({ onBack, setTool }) => {\n    const context = useContext(DevtoolsContext);\n    const [query, setQuery] = useState(\"\");\n    const [eventType, setEventType] = useState<string | null>(null);\n\n    const events = context.room.currentState.events;\n\n    if (eventType !== null) {\n        const onBack = (): void => {\n            setEventType(null);\n        };\n        return <RoomStateExplorerEventType eventType={eventType} onBack={onBack} />;\n    }\n\n    const onAction = async (): Promise<void> => {\n        setTool(_td(\"devtools|send_custom_state_event\"), StateEventEditor);\n    };\n\n    return (\n        <BaseTool onBack={onBack} actionLabel={_td(\"devtools|send_custom_state_event\")} onAction={onAction}>\n            <FilteredList query={query} onChange={setQuery}>\n                {Array.from(events.keys()).map((eventType) => (\n                    <StateEventButton key={eventType} label={eventType} onClick={() => setEventType(eventType)} />\n                ))}\n            </FilteredList>\n        </BaseTool>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useContext } from \"react\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport BaseTool, { type IDevtoolsProps } from \"./BaseTool\";\nimport { _t } from \"../../../../languageHandler\";\nimport { useAsyncMemo } from \"../../../../hooks/useAsyncMemo\";\nimport MatrixClientContext from \"../../../../contexts/MatrixClientContext\";\nimport Spinner from \"../../elements/Spinner\";\nimport SyntaxHighlight from \"../../elements/SyntaxHighlight\";\nimport { MatrixClientPeg } from \"../../../../MatrixClientPeg\";\n\nconst FAILED_TO_LOAD = Symbol(\"failed-to-load\");\n\ninterface IServerWellKnown {\n    server: {\n        name: string;\n        version: string;\n    };\n}\n\nexport async function getServerVersionFromFederationApi(client: MatrixClient): Promise<IServerWellKnown> {\n    let baseUrl = client.getHomeserverUrl();\n\n    try {\n        const hsName = MatrixClientPeg.safeGet().getDomain();\n        // We don't use the js-sdk Autodiscovery module here as it only support client well-known, not server ones.\n        const response = await fetch(`https://${hsName}/.well-known/matrix/server`);\n        const json = await response.json();\n        if (json[\"m.server\"]) {\n            baseUrl = `https://${json[\"m.server\"]}`;\n        }\n    } catch (e) {\n        console.warn(e);\n    }\n\n    const response = await fetch(`${baseUrl}/_matrix/federation/v1/version`);\n    return response.json();\n}\n\nconst ServerInfo: React.FC<IDevtoolsProps> = ({ onBack }) => {\n    const cli = useContext(MatrixClientContext);\n    const capabilities = useAsyncMemo(() => cli.fetchCapabilities().catch(() => FAILED_TO_LOAD), [cli]);\n    const clientVersions = useAsyncMemo(() => cli.getVersions().catch(() => FAILED_TO_LOAD), [cli]);\n    const serverVersions = useAsyncMemo(async (): Promise<IServerWellKnown | symbol> => {\n        try {\n            return await getServerVersionFromFederationApi(cli);\n        } catch (e) {\n            console.warn(e);\n        }\n\n        return FAILED_TO_LOAD;\n    }, [cli]);\n\n    let body: JSX.Element;\n    if (!capabilities || !clientVersions || !serverVersions) {\n        body = <Spinner />;\n    } else {\n        body = (\n            <>\n                <h4>{_t(\"common|capabilities\")}</h4>\n                {capabilities !== FAILED_TO_LOAD ? (\n                    <SyntaxHighlight language=\"json\" children={JSON.stringify(capabilities, null, 4)} />\n                ) : (\n                    <div>{_t(\"devtools|failed_to_load\")}</div>\n                )}\n\n                <h4>{_t(\"devtools|client_versions\")}</h4>\n                {clientVersions !== FAILED_TO_LOAD ? (\n                    <SyntaxHighlight language=\"json\" children={JSON.stringify(clientVersions, null, 4)} />\n                ) : (\n                    <div>{_t(\"devtools|failed_to_load\")}</div>\n                )}\n\n                <h4>{_t(\"devtools|server_versions\")}</h4>\n                {serverVersions !== FAILED_TO_LOAD ? (\n                    <SyntaxHighlight language=\"json\" children={JSON.stringify(serverVersions, null, 4)} />\n                ) : (\n                    <div>{_t(\"devtools|failed_to_load\")}</div>\n                )}\n            </>\n        );\n    }\n\n    return <BaseTool onBack={onBack}>{body}</BaseTool>;\n};\n\nexport default ServerInfo;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2018, 2019 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEvent } from \"react\";\nimport { MatrixClient, MatrixError } from \"matrix-js-sdk/src/matrix\";\nimport { decodeRecoveryKey, type KeyBackupInfo, type KeyBackupRestoreResult } from \"matrix-js-sdk/src/crypto-api\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { MatrixClientPeg } from \"../../../../MatrixClientPeg\";\nimport { _t } from \"../../../../languageHandler\";\nimport { accessSecretStorage } from \"../../../../SecurityManager\";\nimport Spinner from \"../../elements/Spinner\";\nimport DialogButtons from \"../../elements/DialogButtons\";\nimport AccessibleButton from \"../../elements/AccessibleButton\";\nimport BaseDialog from \"../BaseDialog\";\n\nenum RestoreType {\n    Passphrase = \"passphrase\",\n    RecoveryKey = \"recovery_key\",\n    SecretStorage = \"secret_storage\",\n}\n\nenum ProgressState {\n    PreFetch = \"prefetch\",\n    Fetch = \"fetch\",\n    LoadKeys = \"load_keys\",\n}\n\ninterface IProps {\n    // if false, will close the dialog as soon as the restore completes successfully\n    // default: true\n    showSummary?: boolean;\n    onFinished(done?: boolean): void;\n}\n\ninterface IState {\n    backupInfo: KeyBackupInfo | null;\n    loading: boolean;\n    loadError: boolean | null;\n    restoreError: unknown | null;\n    recoveryKey: string;\n    recoverInfo: KeyBackupRestoreResult | null;\n    recoveryKeyValid: boolean;\n    forceRecoveryKey: boolean;\n    passPhrase: string;\n    restoreType: RestoreType | null;\n    progress: {\n        stage: ProgressState | string;\n        total?: number;\n        successes?: number;\n        failures?: number;\n    };\n}\n\n/*\n * Dialog for restoring e2e keys from a backup and the user's recovery key\n */\nexport default class RestoreKeyBackupDialog extends React.PureComponent<IProps, IState> {\n    public static defaultProps: Partial<IProps> = {\n        showSummary: true,\n    };\n\n    public constructor(props: IProps) {\n        super(props);\n        this.state = {\n            backupInfo: null,\n            loading: false,\n            loadError: null,\n            restoreError: null,\n            recoveryKey: \"\",\n            recoverInfo: null,\n            recoveryKeyValid: false,\n            forceRecoveryKey: false,\n            passPhrase: \"\",\n            restoreType: null,\n            progress: { stage: ProgressState.PreFetch },\n        };\n    }\n\n    public componentDidMount(): void {\n        this.loadBackupStatus();\n    }\n\n    private onCancel = (): void => {\n        this.props.onFinished(false);\n    };\n\n    private onDone = (): void => {\n        this.props.onFinished(true);\n    };\n\n    private onUseRecoveryKeyClick = (): void => {\n        this.setState({\n            forceRecoveryKey: true,\n        });\n    };\n\n    private progressCallback = (data: IState[\"progress\"]): void => {\n        this.setState({\n            progress: data,\n        });\n    };\n\n    private onResetRecoveryClick = (): void => {\n        this.props.onFinished(false);\n        accessSecretStorage(async (): Promise<void> => {}, { forceReset: true });\n    };\n\n    /**\n     * Check if the recovery key is valid\n     * @param recoveryKey\n     * @private\n     */\n    private isValidRecoveryKey(recoveryKey: string): boolean {\n        try {\n            decodeRecoveryKey(recoveryKey);\n            return true;\n        } catch {\n            return false;\n        }\n    }\n\n    private onRecoveryKeyChange = (e: ChangeEvent<HTMLInputElement>): void => {\n        this.setState({\n            recoveryKey: e.target.value,\n            recoveryKeyValid: this.isValidRecoveryKey(e.target.value),\n        });\n    };\n\n    private onPassPhraseNext = async (): Promise<void> => {\n        const crypto = MatrixClientPeg.safeGet().getCrypto();\n        if (!crypto) return;\n        this.setState({\n            loading: true,\n            restoreError: null,\n            restoreType: RestoreType.Passphrase,\n        });\n        try {\n            // We do still restore the key backup: we must ensure that the key backup key\n            // is the right one and restoring it is currently the only way we can do this.\n            const recoverInfo = await crypto.restoreKeyBackupWithPassphrase(this.state.passPhrase, {\n                progressCallback: this.progressCallback,\n            });\n\n            if (!this.props.showSummary) {\n                this.props.onFinished(true);\n                return;\n            }\n            this.setState({\n                loading: false,\n                recoverInfo,\n            });\n        } catch (e) {\n            logger.log(\"Error restoring backup\", e);\n            this.setState({\n                loading: false,\n                restoreError: e,\n            });\n        }\n    };\n\n    private onRecoveryKeyNext = async (): Promise<void> => {\n        const crypto = MatrixClientPeg.safeGet().getCrypto();\n        if (!this.state.recoveryKeyValid || !this.state.backupInfo?.version || !crypto) return;\n\n        this.setState({\n            loading: true,\n            restoreError: null,\n            restoreType: RestoreType.RecoveryKey,\n        });\n        try {\n            await crypto.storeSessionBackupPrivateKey(\n                decodeRecoveryKey(this.state.recoveryKey),\n                this.state.backupInfo.version,\n            );\n            const recoverInfo = await crypto.restoreKeyBackup({\n                progressCallback: this.progressCallback,\n            });\n\n            if (!this.props.showSummary) {\n                this.props.onFinished(true);\n                return;\n            }\n            this.setState({\n                loading: false,\n                recoverInfo,\n            });\n        } catch (e) {\n            logger.log(\"Error restoring backup\", e);\n            this.setState({\n                loading: false,\n                restoreError: e,\n            });\n        }\n    };\n\n    private onPassPhraseChange = (e: ChangeEvent<HTMLInputElement>): void => {\n        this.setState({\n            passPhrase: e.target.value,\n        });\n    };\n\n    private async restoreWithSecretStorage(): Promise<boolean> {\n        const crypto = MatrixClientPeg.safeGet().getCrypto();\n        if (!crypto) return false;\n\n        this.setState({\n            restoreError: null,\n            restoreType: RestoreType.SecretStorage,\n        });\n        try {\n            let recoverInfo: KeyBackupRestoreResult | null = null;\n            // `accessSecretStorage` may prompt for storage access as needed.\n            await accessSecretStorage(async (): Promise<void> => {\n                await crypto.loadSessionBackupPrivateKeyFromSecretStorage();\n                recoverInfo = await crypto.restoreKeyBackup({ progressCallback: this.progressCallback });\n            });\n            this.setState({\n                loading: false,\n                recoverInfo,\n            });\n            return true;\n        } catch (e) {\n            logger.log(\"restoreWithSecretStorage failed:\", e);\n            this.setState({\n                restoreError: e,\n                loading: false,\n            });\n            return false;\n        }\n    }\n\n    private async restoreWithCachedKey(backupInfo: KeyBackupInfo | null): Promise<boolean> {\n        const crypto = MatrixClientPeg.safeGet().getCrypto();\n        if (!crypto) return false;\n        try {\n            const recoverInfo = await crypto.restoreKeyBackup({ progressCallback: this.progressCallback });\n            this.setState({\n                recoverInfo,\n            });\n            return true;\n        } catch (e) {\n            logger.log(\"restoreWithCachedKey failed:\", e);\n            return false;\n        }\n    }\n\n    private async loadBackupStatus(): Promise<void> {\n        this.setState({\n            loading: true,\n            loadError: null,\n        });\n        try {\n            const cli = MatrixClientPeg.safeGet();\n            const backupInfo = (await cli.getCrypto()?.getKeyBackupInfo()) ?? null;\n            const has4S = await cli.secretStorage.hasKey();\n            const backupKeyStored = has4S ? await cli.isKeyBackupKeyStored() : null;\n            this.setState({\n                backupInfo,\n            });\n\n            const gotCache = await this.restoreWithCachedKey(backupInfo);\n            if (gotCache) {\n                logger.log(\"RestoreKeyBackupDialog: found cached backup key\");\n                this.setState({\n                    loading: false,\n                });\n                return;\n            }\n\n            const hasBackupFromSS = backupKeyStored && (await this.restoreWithSecretStorage());\n            if (hasBackupFromSS) {\n                logger.log(\"RestoreKeyBackupDialog: found backup key in secret storage\");\n                this.setState({\n                    loading: false,\n                });\n                return;\n            }\n\n            this.setState({\n                loadError: null,\n                loading: false,\n            });\n        } catch (e) {\n            logger.log(\"Error loading backup status\", e);\n            this.setState({\n                loadError: true,\n                loading: false,\n            });\n        }\n    }\n\n    public render(): React.ReactNode {\n        const backupHasPassphrase =\n            this.state.backupInfo &&\n            this.state.backupInfo.auth_data &&\n            this.state.backupInfo.auth_data.private_key_salt &&\n            this.state.backupInfo.auth_data.private_key_iterations;\n\n        let content;\n        let title;\n        if (this.state.loading) {\n            title = _t(\"encryption|access_secret_storage_dialog|restoring\");\n            let details;\n            if (this.state.progress.stage === ProgressState.Fetch) {\n                details = _t(\"restore_key_backup_dialog|key_fetch_in_progress\");\n            } else if (this.state.progress.stage === ProgressState.LoadKeys) {\n                const { total, successes, failures } = this.state.progress;\n                details = _t(\"restore_key_backup_dialog|load_keys_progress\", {\n                    total,\n                    completed: (successes ?? 0) + (failures ?? 0),\n                });\n            } else if (this.state.progress.stage === ProgressState.PreFetch) {\n                details = _t(\"restore_key_backup_dialog|key_fetch_in_progress\");\n            }\n            content = (\n                <div>\n                    <div>{details}</div>\n                    <Spinner />\n                </div>\n            );\n        } else if (this.state.loadError) {\n            title = _t(\"common|error\");\n            content = _t(\"restore_key_backup_dialog|load_error_content\");\n        } else if (this.state.restoreError) {\n            if (\n                this.state.restoreError instanceof MatrixError &&\n                this.state.restoreError.errcode === MatrixClient.RESTORE_BACKUP_ERROR_BAD_KEY\n            ) {\n                if (this.state.restoreType === RestoreType.RecoveryKey) {\n                    title = _t(\"restore_key_backup_dialog|recovery_key_mismatch_title\");\n                    content = (\n                        <div>\n                            <p>{_t(\"restore_key_backup_dialog|recovery_key_mismatch_description\")}</p>\n                        </div>\n                    );\n                } else {\n                    title = _t(\"restore_key_backup_dialog|incorrect_security_phrase_title\");\n                    content = (\n                        <div>\n                            <p>{_t(\"restore_key_backup_dialog|incorrect_security_phrase_dialog\")}</p>\n                        </div>\n                    );\n                }\n            } else {\n                title = _t(\"common|error\");\n                content = _t(\"restore_key_backup_dialog|restore_failed_error\");\n            }\n        } else if (this.state.backupInfo === null) {\n            title = _t(\"common|error\");\n            content = _t(\"restore_key_backup_dialog|no_backup_error\");\n        } else if (this.state.recoverInfo) {\n            title = _t(\"restore_key_backup_dialog|keys_restored_title\");\n            let failedToDecrypt;\n            if (this.state.recoverInfo.total > this.state.recoverInfo.imported) {\n                failedToDecrypt = (\n                    <p>\n                        {_t(\"restore_key_backup_dialog|count_of_decryption_failures\", {\n                            failedCount: this.state.recoverInfo.total - this.state.recoverInfo.imported,\n                        })}\n                    </p>\n                );\n            }\n            content = (\n                <div>\n                    <p>\n                        {_t(\"restore_key_backup_dialog|count_of_successfully_restored_keys\", {\n                            sessionCount: this.state.recoverInfo.imported,\n                        })}\n                    </p>\n                    {failedToDecrypt}\n                    <DialogButtons\n                        primaryButton={_t(\"action|ok\")}\n                        onPrimaryButtonClick={this.onDone}\n                        hasCancel={false}\n                        focus={true}\n                    />\n                </div>\n            );\n        } else if (backupHasPassphrase && !this.state.forceRecoveryKey) {\n            title = _t(\"restore_key_backup_dialog|enter_phrase_title\");\n            content = (\n                <div>\n                    <p>\n                        {_t(\"restore_key_backup_dialog|key_backup_warning\", {}, { b: (sub) => <strong>{sub}</strong> })}\n                    </p>\n                    <p>{_t(\"restore_key_backup_dialog|enter_phrase_description\")}</p>\n\n                    <form className=\"mx_RestoreKeyBackupDialog_primaryContainer\">\n                        <input\n                            data-testid=\"passphraseInput\"\n                            type=\"password\"\n                            className=\"mx_RestoreKeyBackupDialog_passPhraseInput\"\n                            onChange={this.onPassPhraseChange}\n                            value={this.state.passPhrase}\n                            autoFocus={true}\n                        />\n                        <DialogButtons\n                            primaryButton={_t(\"action|next\")}\n                            onPrimaryButtonClick={this.onPassPhraseNext}\n                            primaryIsSubmit={true}\n                            hasCancel={true}\n                            onCancel={this.onCancel}\n                            focus={false}\n                        />\n                    </form>\n                    {_t(\n                        \"restore_key_backup_dialog|phrase_forgotten_text\",\n                        {},\n                        {\n                            button1: (s) => (\n                                <AccessibleButton kind=\"link_inline\" onClick={this.onUseRecoveryKeyClick}>\n                                    {s}\n                                </AccessibleButton>\n                            ),\n                            button2: (s) => (\n                                <AccessibleButton kind=\"link_inline\" onClick={this.onResetRecoveryClick}>\n                                    {s}\n                                </AccessibleButton>\n                            ),\n                        },\n                    )}\n                </div>\n            );\n        } else {\n            title = _t(\"restore_key_backup_dialog|enter_key_title\");\n\n            let keyStatus;\n            if (this.state.recoveryKey.length === 0) {\n                keyStatus = <div className=\"mx_RestoreKeyBackupDialog_keyStatus\" />;\n            } else if (this.state.recoveryKeyValid) {\n                keyStatus = (\n                    <div className=\"mx_RestoreKeyBackupDialog_keyStatus\">\n                        {\"\\uD83D\\uDC4D \"}\n                        {_t(\"restore_key_backup_dialog|key_is_valid\")}\n                    </div>\n                );\n            } else {\n                keyStatus = (\n                    <div className=\"mx_RestoreKeyBackupDialog_keyStatus\">\n                        {\"\\uD83D\\uDC4E \"}\n                        {_t(\"restore_key_backup_dialog|key_is_invalid\")}\n                    </div>\n                );\n            }\n\n            content = (\n                <div>\n                    <p>\n                        {_t(\"restore_key_backup_dialog|key_backup_warning\", {}, { b: (sub) => <strong>{sub}</strong> })}\n                    </p>\n                    <p>{_t(\"restore_key_backup_dialog|enter_key_description\")}</p>\n\n                    <div className=\"mx_RestoreKeyBackupDialog_primaryContainer\">\n                        <input\n                            className=\"mx_RestoreKeyBackupDialog_recoveryKeyInput\"\n                            onChange={this.onRecoveryKeyChange}\n                            value={this.state.recoveryKey}\n                            autoFocus={true}\n                        />\n                        {keyStatus}\n                        <DialogButtons\n                            primaryButton={_t(\"action|next\")}\n                            onPrimaryButtonClick={this.onRecoveryKeyNext}\n                            hasCancel={true}\n                            onCancel={this.onCancel}\n                            focus={false}\n                            primaryDisabled={!this.state.recoveryKeyValid}\n                        />\n                    </div>\n                    {_t(\n                        \"restore_key_backup_dialog|key_forgotten_text\",\n                        {},\n                        {\n                            button: (s) => (\n                                <AccessibleButton kind=\"link_inline\" onClick={this.onResetRecoveryClick}>\n                                    {s}\n                                </AccessibleButton>\n                            ),\n                        },\n                    )}\n                </div>\n            );\n        }\n\n        return (\n            <BaseDialog className=\"mx_RestoreKeyBackupDialog\" onFinished={this.props.onFinished} title={title}>\n                <div className=\"mx_RestoreKeyBackupDialog_content\">{content}</div>\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport enum Filter {\n    People,\n    PublicRooms,\n    PublicSpaces,\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021, 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport React, { Fragment, type JSX, type ReactNode, useState } from \"react\";\nimport {\n    NotificationsOffSolidIcon,\n    OverflowHorizontalIcon,\n    NotificationsSolidIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { ContextMenuTooltipButton } from \"../../../../accessibility/context_menu/ContextMenuTooltipButton\";\nimport { useNotificationState } from \"../../../../hooks/useRoomNotificationState\";\nimport { _t } from \"../../../../languageHandler\";\nimport { RoomNotifState } from \"../../../../RoomNotifs\";\nimport { RoomGeneralContextMenu } from \"../../context_menus/RoomGeneralContextMenu\";\nimport { RoomNotificationContextMenu } from \"../../context_menus/RoomNotificationContextMenu\";\nimport SpaceContextMenu from \"../../context_menus/SpaceContextMenu\";\nimport { type ButtonEvent } from \"../../elements/AccessibleButton\";\nimport { contextMenuBelow } from \"../../rooms/RoomTile\";\nimport { shouldShowComponent } from \"../../../../customisations/helpers/UIComponents\";\nimport { UIComponent } from \"../../../../settings/UIFeature\";\n\ninterface Props {\n    room: Room;\n}\n\nexport function getNotificationIcon(state: RoomNotifState): ReactNode {\n    switch (state) {\n        case RoomNotifState.Mute:\n            return <NotificationsOffSolidIcon />;\n        default:\n            return <NotificationsSolidIcon />;\n    }\n}\n\nexport function RoomResultContextMenus({ room }: Props): JSX.Element {\n    const [notificationState] = useNotificationState(room);\n\n    const [generalMenuPosition, setGeneralMenuPosition] = useState<DOMRect | null>(null);\n    const [notificationMenuPosition, setNotificationMenuPosition] = useState<DOMRect | null>(null);\n\n    let generalMenu: JSX.Element | undefined;\n    if (generalMenuPosition !== null) {\n        if (room.isSpaceRoom()) {\n            generalMenu = (\n                <SpaceContextMenu\n                    {...contextMenuBelow(generalMenuPosition)}\n                    space={room}\n                    onFinished={() => setGeneralMenuPosition(null)}\n                />\n            );\n        } else {\n            generalMenu = (\n                <RoomGeneralContextMenu\n                    {...contextMenuBelow(generalMenuPosition)}\n                    room={room}\n                    onFinished={() => setGeneralMenuPosition(null)}\n                />\n            );\n        }\n    }\n\n    let notificationMenu: JSX.Element | undefined;\n    if (notificationMenuPosition !== null) {\n        notificationMenu = (\n            <RoomNotificationContextMenu\n                {...contextMenuBelow(notificationMenuPosition)}\n                room={room}\n                onFinished={() => setNotificationMenuPosition(null)}\n            />\n        );\n    }\n\n    return (\n        <Fragment>\n            {shouldShowComponent(UIComponent.RoomOptionsMenu) && (\n                <ContextMenuTooltipButton\n                    className=\"mx_SpotlightDialog_option--menu\"\n                    onClick={(ev: ButtonEvent) => {\n                        ev.preventDefault();\n                        ev.stopPropagation();\n\n                        const target = ev.target as HTMLElement;\n                        setGeneralMenuPosition(target.getBoundingClientRect());\n                    }}\n                    title={room.isSpaceRoom() ? _t(\"space|context_menu|options\") : _t(\"room|context_menu|title\")}\n                    isExpanded={generalMenuPosition !== null}\n                >\n                    <OverflowHorizontalIcon />\n                </ContextMenuTooltipButton>\n            )}\n            {!room.isSpaceRoom() && (\n                <ContextMenuTooltipButton\n                    className=\"mx_SpotlightDialog_option--notifications\"\n                    onClick={(ev: ButtonEvent) => {\n                        ev.preventDefault();\n                        ev.stopPropagation();\n\n                        const target = ev.target as HTMLElement;\n                        setNotificationMenuPosition(target.getBoundingClientRect());\n                    }}\n                    title={_t(\"room_list|notification_options\")}\n                    isExpanded={notificationMenuPosition !== null}\n                >\n                    {getNotificationIcon(notificationState!)}\n                </ContextMenuTooltipButton>\n            )}\n            {generalMenu}\n            {notificationMenu}\n        </Fragment>\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2016 Jani Mustonen\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n */\n\nimport React, {\n    type JSX,\n    type ComponentProps,\n    type ComponentPropsWithoutRef,\n    type ReactElement,\n    type KeyboardEvent,\n    type Ref,\n} from \"react\";\nimport classnames from \"classnames\";\nimport { Tooltip } from \"@vector-im/compound-web\";\n\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\n\nexport type ButtonEvent = React.MouseEvent<Element> | React.KeyboardEvent<Element> | React.FormEvent<Element>;\n\n/**\n * The kind of button, similar to how Bootstrap works.\n */\nexport type AccessibleButtonKind =\n    | \"primary\"\n    | \"primary_outline\"\n    | \"primary_sm\"\n    | \"secondary\"\n    | \"content_inline\"\n    | \"danger\"\n    | \"danger_outline\"\n    | \"danger_sm\"\n    | \"danger_inline\"\n    | \"link\"\n    | \"link_inline\"\n    | \"link_sm\"\n    | \"icon\"\n    | \"icon_primary\"\n    | \"icon_primary_outline\";\n\ntype ElementType = keyof HTMLElementTagNameMap;\nconst defaultElement = \"div\";\n\ntype TooltipProps = ComponentProps<typeof Tooltip>;\n\n/**\n * Type of props accepted by {@link AccessibleButton}.\n *\n * Extends props accepted by the underlying element specified using the `element` prop.\n */\ntype Props<T extends ElementType = \"div\"> = {\n    /**\n     * The base element type. \"div\" by default.\n     */\n    element?: T;\n    /**\n     * The kind of button, similar to how Bootstrap works.\n     */\n    kind?: AccessibleButtonKind;\n    /**\n     * Whether the button should be disabled.\n     */\n    disabled?: boolean;\n    /**\n     * Whether the button should trigger on mousedown event instead of on click event. Defaults to false (click event).\n     */\n    triggerOnMouseDown?: boolean;\n    /**\n     * Event handler for button activation. Should be implemented exactly like a normal `onClick` handler.\n     */\n    onClick: ((e: ButtonEvent) => void | Promise<void>) | null;\n    /**\n     * The tooltip to show on hover or focus.\n     */\n    title?: string;\n    /**\n     * The caption is a secondary text displayed under the `title` of the tooltip.\n     * Only valid when used in conjunction with `title`.\n     */\n    caption?: TooltipProps[\"caption\"];\n    /**\n     * The placement of the tooltip.\n     */\n    placement?: TooltipProps[\"placement\"];\n    /**\n     * Callback for when the tooltip is opened or closed.\n     */\n    onTooltipOpenChange?: TooltipProps[\"onOpenChange\"];\n\n    /**\n     * Whether the tooltip should be disabled.\n     */\n    disableTooltip?: TooltipProps[\"disabled\"];\n\n    ref?: Ref<HTMLElementTagNameMap[T]>;\n};\n\nexport type ButtonProps<T extends ElementType> = Props<T> & Omit<ComponentPropsWithoutRef<T>, keyof Props<T>>;\n\n/**\n * Type of the props passed to the element that is rendered by AccessibleButton.\n */\ntype RenderedElementProps<T extends ElementType> = React.InputHTMLAttributes<Element> & RefProp<T>;\n\n/**\n * AccessibleButton is a generic wrapper for any element that should be treated\n * as a button.  Identifies the element as a button, setting proper tab\n * indexing and keyboard activation behavior.\n *\n * If a ref is passed, it will be forwarded to the rendered element as specified using the `element` prop.\n *\n * @param {Object} props  react element properties\n * @returns {Object} rendered react\n */\nconst AccessibleButton = function AccessibleButton<T extends ElementType = typeof defaultElement>({\n    element,\n    onClick,\n    children,\n    kind,\n    disabled,\n    className,\n    onKeyDown,\n    onKeyUp,\n    triggerOnMouseDown,\n    title,\n    caption,\n    placement = \"right\",\n    onTooltipOpenChange,\n    disableTooltip,\n    role = \"button\",\n    tabIndex = 0,\n    ref,\n    ...restProps\n}: ButtonProps<T>): JSX.Element {\n    const newProps = {\n        ...restProps,\n        tabIndex,\n        role,\n        \"aria-label\": restProps[\"aria-label\"] ?? title,\n    } as RenderedElementProps<T>;\n\n    if (disabled) {\n        newProps[\"aria-disabled\"] = true;\n        newProps[\"disabled\"] = true;\n    } else {\n        if (triggerOnMouseDown) {\n            newProps.onMouseDown = onClick ?? undefined;\n        } else {\n            newProps.onClick = onClick ?? undefined;\n        }\n        // We need to consume enter onKeyDown and space onKeyUp\n        // otherwise we are risking also activating other keyboard focusable elements\n        // that might receive focus as a result of the AccessibleButtonClick action\n        // It's because we are using html buttons at a few places e.g. inside dialogs\n        // And divs which we report as role button to assistive technologies.\n        // Browsers handle space and enter key presses differently and we are only adjusting to the\n        // inconsistencies here\n        newProps.onKeyDown = (e: KeyboardEvent<never>) => {\n            const action = getKeyBindingsManager().getAccessibilityAction(e);\n\n            switch (action) {\n                case KeyBindingAction.Enter:\n                    e.stopPropagation();\n                    e.preventDefault();\n                    return onClick?.(e);\n                case KeyBindingAction.Space:\n                    e.stopPropagation();\n                    e.preventDefault();\n                    break;\n                default:\n                    onKeyDown?.(e);\n            }\n        };\n        newProps.onKeyUp = (e: KeyboardEvent<never>) => {\n            const action = getKeyBindingsManager().getAccessibilityAction(e);\n\n            switch (action) {\n                case KeyBindingAction.Enter:\n                    e.stopPropagation();\n                    e.preventDefault();\n                    break;\n                case KeyBindingAction.Space:\n                    e.stopPropagation();\n                    e.preventDefault();\n                    return onClick?.(e);\n                default:\n                    onKeyUp?.(e);\n                    break;\n            }\n        };\n    }\n\n    // Pass through the ref - used for keyboard shortcut access to some buttons\n    newProps.ref = ref;\n\n    newProps.className = classnames(\"mx_AccessibleButton\", className, {\n        mx_AccessibleButton_hasKind: kind,\n        [`mx_AccessibleButton_kind_${kind}`]: kind,\n        mx_AccessibleButton_disabled: disabled,\n    });\n\n    // React.createElement expects InputHTMLAttributes\n    const button = React.createElement(element ?? defaultElement, newProps, children);\n\n    if (title) {\n        return (\n            <Tooltip\n                description={title}\n                caption={caption}\n                isTriggerInteractive={true}\n                placement={placement}\n                onOpenChange={onTooltipOpenChange}\n                disabled={disableTooltip}\n            >\n                {button}\n            </Tooltip>\n        );\n    }\n    return button;\n};\n\ninterface RefProp<T extends ElementType> {\n    ref?: Ref<HTMLElementTagNameMap[T]>;\n}\n\ninterface ButtonComponent {\n    // With the explicit `element` prop\n    <C extends ElementType>(props: { element?: C } & ButtonProps<C> & RefProp<C>): ReactElement;\n    // Without the explicit `element` prop\n    (props: ButtonProps<\"div\"> & RefProp<\"div\">): ReactElement;\n}\n\nexport default AccessibleButton as ButtonComponent;\n","/*\nCopyright 2026 Element Creations Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useCallback } from \"react\";\nimport { Button } from \"@vector-im/compound-web\";\n\nimport SdkConfig from \"../../../SdkConfig\";\nimport { _t } from \"../../../languageHandler\";\nimport Modal from \"../../../Modal\";\nimport BugReportDialog, { type BugReportDialogProps } from \"../dialogs/BugReportDialog\";\nimport { BugReportEndpointURLLocal } from \"../../../IConfigOptions\";\n\n/**\n * Renders a button to open the BugReportDialog *if* the configuration\n * supports it.\n */\nexport function BugReportDialogButton({\n    label,\n    error,\n}: Pick<BugReportDialogProps, \"label\" | \"error\">): React.ReactElement | null {\n    const bugReportUrl = SdkConfig.get().bug_report_endpoint_url;\n    const onClick = useCallback(() => {\n        Modal.createDialog(BugReportDialog, {\n            label,\n            error,\n        });\n    }, [label, error]);\n\n    if (!bugReportUrl) {\n        return null;\n    }\n    return (\n        <Button kind=\"secondary\" size=\"sm\" onClick={onClick}>\n            {bugReportUrl === BugReportEndpointURLLocal\n                ? _t(\"bug_reporting|download_logs\")\n                : _t(\"bug_reporting|submit_debug_logs\")}\n        </Button>\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2019-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useState } from \"react\";\nimport classNames from \"classnames\";\nimport { CopyIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { copyPlaintext } from \"../../../utils/strings\";\nimport AccessibleButton, { type ButtonEvent } from \"./AccessibleButton\";\n\ninterface IProps extends React.HTMLAttributes<HTMLDivElement> {\n    children?: React.ReactNode;\n    getTextToCopy: () => string | null;\n    border?: boolean;\n    className?: string;\n}\n\nexport const CopyTextButton: React.FC<Pick<IProps, \"getTextToCopy\" | \"className\" | \"children\">> = ({\n    getTextToCopy,\n    className,\n    children,\n}) => {\n    const [tooltip, setTooltip] = useState<string | undefined>(undefined);\n\n    const onCopyClickInternal = async (e: ButtonEvent): Promise<void> => {\n        e.preventDefault();\n        const text = getTextToCopy();\n        const successful = !!text && (await copyPlaintext(text));\n        setTooltip(successful ? _t(\"common|copied\") : _t(\"error|failed_copy\"));\n    };\n\n    const onHideTooltip = (): void => {\n        if (tooltip) {\n            setTooltip(undefined);\n        }\n    };\n\n    return (\n        <AccessibleButton\n            title={tooltip ?? _t(\"action|copy\")}\n            onClick={onCopyClickInternal}\n            className={className}\n            onTooltipOpenChange={(open) => {\n                if (!open) onHideTooltip();\n            }}\n        >\n            {children}\n        </AccessibleButton>\n    );\n};\n\nconst CopyableText: React.FC<IProps> = ({ children, getTextToCopy, border = true, className, ...props }) => {\n    const combinedClassName = classNames(\"mx_CopyableText\", className, {\n        mx_CopyableText_border: border,\n    });\n\n    return (\n        <div className={combinedClassName} {...props}>\n            {children}\n            <CopyTextButton getTextToCopy={getTextToCopy} className=\"mx_CopyableText_copyButton\">\n                <CopyIcon />\n            </CopyTextButton>\n        </div>\n    );\n};\n\nexport default CopyableText;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { BackspaceSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport AccessibleButton, { type ButtonEvent } from \"./AccessibleButton\";\n\ninterface IProps {\n    // Callback for when the button is pressed\n    onBackspacePress: (ev: ButtonEvent) => void;\n}\n\nexport default class DialPadBackspaceButton extends React.PureComponent<IProps> {\n    public render(): React.ReactNode {\n        return (\n            <div className=\"mx_DialPadBackspaceButtonWrapper\">\n                <AccessibleButton\n                    className=\"mx_DialPadBackspaceButton\"\n                    onClick={this.props.onBackspacePress}\n                    aria-label={_t(\"keyboard|backspace\")}\n                >\n                    <BackspaceSolidIcon />\n                </AccessibleButton>\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd.\nCopyright 2017 Aidan Gauland\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode } from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\n\ninterface IProps {\n    // The primary button which is styled differently and has default focus.\n    primaryButton: React.ReactNode;\n\n    // A node to insert into the cancel button instead of default \"Cancel\"\n    cancelButton?: React.ReactNode;\n\n    // If true, make the primary button a form submit button (input type=\"submit\")\n    primaryIsSubmit?: boolean;\n\n    // onClick handler for the primary button. Note that the returned promise, if\n    // returning a promise, is not used.\n    onPrimaryButtonClick?: (ev: React.MouseEvent) => void | Promise<void>;\n\n    // should there be a cancel button? default: true\n    hasCancel?: boolean;\n\n    // The class of the cancel button, only used if a cancel button is\n    // enabled\n    cancelButtonClass?: string;\n\n    // onClick handler for the cancel button.\n    onCancel?: (...args: any[]) => void;\n\n    focus?: boolean;\n\n    // disables the primary and cancel buttons\n    disabled?: boolean;\n\n    // disables only the primary button\n    primaryDisabled?: boolean;\n\n    // something to stick next to the buttons, optionally\n    additive?: ReactNode;\n\n    primaryButtonClass?: string;\n    children?: ReactNode;\n}\n\n/**\n * Basic container for buttons in modal dialogs.\n */\nexport default class DialogButtons extends React.Component<IProps> {\n    public static defaultProps: Partial<IProps> = {\n        hasCancel: true,\n        disabled: false,\n    };\n\n    private onCancelClick = (event: React.MouseEvent): void => {\n        this.props.onCancel?.(event);\n    };\n\n    public render(): React.ReactNode {\n        let primaryButtonClassName = \"mx_Dialog_primary\";\n        if (this.props.primaryButtonClass) {\n            primaryButtonClassName += \" \" + this.props.primaryButtonClass;\n        }\n\n        let cancelButton: JSX.Element | undefined;\n        if (this.props.hasCancel) {\n            cancelButton = (\n                <button\n                    // important: the default type is 'submit' and this button comes before the\n                    // primary in the DOM so will get form submissions unless we make it not a submit.\n                    data-testid=\"dialog-cancel-button\"\n                    type=\"button\"\n                    onClick={this.onCancelClick}\n                    className={this.props.cancelButtonClass}\n                    disabled={this.props.disabled}\n                >\n                    {this.props.cancelButton || _t(\"action|cancel\")}\n                </button>\n            );\n        }\n\n        let additive: JSX.Element | undefined;\n        if (this.props.additive) {\n            additive = <div className=\"mx_Dialog_buttons_additive\">{this.props.additive}</div>;\n        }\n\n        return (\n            <div className=\"mx_Dialog_buttons\">\n                {additive}\n                <span className=\"mx_Dialog_buttons_row\">\n                    {cancelButton}\n                    {this.props.children}\n                    <button\n                        type={this.props.primaryIsSubmit ? \"submit\" : \"button\"}\n                        data-testid=\"dialog-primary-button\"\n                        className={primaryButtonClassName}\n                        onClick={this.props.onPrimaryButtonClick}\n                        autoFocus={this.props.focus}\n                        disabled={this.props.disabled || this.props.primaryDisabled}\n                    >\n                        {this.props.primaryButton}\n                    </button>\n                </span>\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017-2021 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, {\n    type JSX,\n    type ChangeEvent,\n    createRef,\n    type CSSProperties,\n    type ReactElement,\n    type ReactNode,\n    type Ref,\n} from \"react\";\nimport classnames from \"classnames\";\nimport { ChevronDownIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport AccessibleButton, { type ButtonEvent } from \"./AccessibleButton\";\nimport { _t } from \"../../../languageHandler\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { objectHasDiff } from \"../../../utils/objects\";\nimport { type NonEmptyArray } from \"../../../@types/common\";\n\ninterface IMenuOptionProps {\n    children: ReactElement;\n    highlighted?: boolean;\n    dropdownKey: string;\n    id?: string;\n    inputRef?: Ref<HTMLLIElement>;\n    onClick(dropdownKey: string): void;\n    onMouseEnter(dropdownKey: string): void;\n}\n\nclass MenuOption extends React.Component<IMenuOptionProps> {\n    public static defaultProps = {\n        disabled: false,\n    };\n\n    private onMouseEnter = (): void => {\n        this.props.onMouseEnter(this.props.dropdownKey);\n    };\n\n    private onClick = (e: React.MouseEvent): void => {\n        e.preventDefault();\n        e.stopPropagation();\n        this.props.onClick(this.props.dropdownKey);\n    };\n\n    public render(): React.ReactNode {\n        const optClasses = classnames({\n            mx_Dropdown_option: true,\n            mx_Dropdown_option_highlight: this.props.highlighted,\n        });\n\n        return (\n            <li\n                id={this.props.id}\n                className={optClasses}\n                onClick={this.onClick}\n                onMouseEnter={this.onMouseEnter}\n                role=\"option\"\n                aria-selected={this.props.highlighted}\n                ref={this.props.inputRef}\n                tabIndex={-1}\n            >\n                {this.props.children}\n            </li>\n        );\n    }\n}\n\nexport interface DropdownProps {\n    id: string;\n    // ARIA label\n    label: string;\n    value?: string;\n    className?: string;\n    autoComplete?: string;\n    children: NonEmptyArray<ReactElement & { key: string }>;\n    // negative for consistency with HTML\n    disabled?: boolean;\n    // The width that the dropdown should be. If specified,\n    // the dropped-down part of the menu will be set to this\n    // width.\n    menuWidth?: number;\n    searchEnabled?: boolean;\n    // Placeholder to show when no value is selected\n    placeholder?: string;\n    // Called when the selected option changes\n    onOptionChange(dropdownKey: string): void;\n    // Called when the value of the search field changes\n    onSearchChange?(query: string): void;\n    // Function that, given the key of an option, returns\n    // a node representing that option to be displayed in the\n    // box itself as the currently-selected option (ie. as\n    // opposed to in the actual dropped-down part). If\n    // unspecified, the appropriate child element is used as\n    // in the dropped-down menu.\n    getShortOption?(value: string): ReactNode;\n}\n\ninterface IState {\n    expanded: boolean;\n    highlightedOption: string;\n    searchQuery: string;\n}\n\n/*\n * Reusable dropdown select control, akin to react-select,\n * but somewhat simpler as react-select is 79KB of minified\n * javascript.\n */\nexport default class Dropdown extends React.Component<DropdownProps, IState> {\n    private readonly buttonRef = createRef<HTMLDivElement>();\n    private dropdownRootElement: HTMLDivElement | null = null;\n    private ignoreEvent: MouseEvent | null = null;\n    private childrenByKey: Record<string, ReactNode> = {};\n\n    public constructor(props: DropdownProps) {\n        super(props);\n\n        this.reindexChildren(this.props.children);\n\n        const firstChild = props.children[0];\n\n        this.state = {\n            // True if the menu is dropped-down\n            expanded: false,\n            // The key of the highlighted option\n            // (the option that would become selected if you pressed enter)\n            highlightedOption: firstChild.key,\n            // the current search query\n            searchQuery: \"\",\n        };\n    }\n\n    public componentDidMount(): void {\n        // Listen for all clicks on the document so we can close the\n        // menu when the user clicks somewhere else\n        document.addEventListener(\"click\", this.onDocumentClick, false);\n    }\n\n    public componentDidUpdate(prevProps: Readonly<DropdownProps>): void {\n        if (objectHasDiff(this.props, prevProps) && this.props.children?.length) {\n            this.reindexChildren(this.props.children);\n            const firstChild = this.props.children[0];\n            this.setState({\n                highlightedOption: firstChild.key,\n            });\n        }\n    }\n\n    public componentWillUnmount(): void {\n        document.removeEventListener(\"click\", this.onDocumentClick, false);\n    }\n\n    private reindexChildren(children: ReactElement[]): void {\n        this.childrenByKey = {};\n        React.Children.forEach(children, (child) => {\n            this.childrenByKey[(child as DropdownProps[\"children\"][number]).key] = child;\n        });\n    }\n\n    private onDocumentClick = (ev: MouseEvent): void => {\n        // Close the dropdown if the user clicks anywhere that isn't\n        // within our root element\n        if (ev !== this.ignoreEvent) {\n            this.setState({\n                expanded: false,\n            });\n        }\n    };\n\n    private onRootClick = (ev: MouseEvent): void => {\n        // This captures any clicks that happen within our elements,\n        // such that we can then ignore them when they're seen by the\n        // click listener on the document handler, ie. not close the\n        // dropdown immediately after opening it.\n        // NB. We can't just stopPropagation() because then the event\n        // doesn't reach the React onClick().\n        this.ignoreEvent = ev;\n    };\n\n    private onAccessibleButtonClick = (ev: ButtonEvent): void => {\n        if (this.props.disabled) return;\n\n        const action = getKeyBindingsManager().getAccessibilityAction(ev as React.KeyboardEvent);\n\n        if (!this.state.expanded) {\n            this.setState({ expanded: true });\n            ev.preventDefault();\n        } else if (action === KeyBindingAction.Enter) {\n            // the accessible button consumes enter onKeyDown for firing onClick, so handle it here\n            this.props.onOptionChange(this.state.highlightedOption);\n            this.close();\n        } else if (!(ev as React.KeyboardEvent).key) {\n            // collapse on other non-keyboard event activations\n            this.setState({ expanded: false });\n            ev.preventDefault();\n        }\n    };\n\n    private close(): void {\n        this.setState({\n            expanded: false,\n        });\n        // their focus was on the input, its getting unmounted, move it to the button\n        if (this.buttonRef.current) {\n            this.buttonRef.current.focus();\n        }\n    }\n\n    private onMenuOptionClick = (dropdownKey: string): void => {\n        this.close();\n        this.props.onOptionChange(dropdownKey);\n    };\n\n    private onKeyDown = (e: React.KeyboardEvent): void => {\n        let handled = true;\n\n        // These keys don't generate keypress events and so needs to be on keyup\n        const action = getKeyBindingsManager().getAccessibilityAction(e);\n        switch (action) {\n            case KeyBindingAction.Enter:\n                this.props.onOptionChange(this.state.highlightedOption);\n            // fallthrough\n            case KeyBindingAction.Escape:\n                this.close();\n                break;\n            case KeyBindingAction.ArrowDown:\n                if (this.state.expanded) {\n                    const nextKey = this.nextOption(this.state.highlightedOption);\n                    this.setState({\n                        highlightedOption: nextKey,\n                    });\n\n                    (\n                        this.dropdownRootElement?.querySelector(`#${this.props.id}__${nextKey}`) as HTMLLIElement\n                    )?.focus();\n                } else {\n                    this.setState({ expanded: true });\n                }\n                break;\n            case KeyBindingAction.ArrowUp:\n                if (this.state.expanded) {\n                    const prevKey = this.prevOption(this.state.highlightedOption);\n                    this.setState({\n                        highlightedOption: prevKey,\n                    });\n                    (\n                        this.dropdownRootElement?.querySelector(`#${this.props.id}__${prevKey}`) as HTMLLIElement\n                    )?.focus();\n                } else {\n                    this.setState({ expanded: true });\n                }\n                break;\n            default:\n                handled = false;\n        }\n\n        if (handled) {\n            e.preventDefault();\n            e.stopPropagation();\n        }\n    };\n\n    private onInputChange = (e: ChangeEvent<HTMLInputElement>): void => {\n        this.setState({\n            searchQuery: e.currentTarget.value,\n        });\n        if (this.props.onSearchChange) {\n            this.props.onSearchChange(e.currentTarget.value);\n        }\n    };\n\n    private collectRoot = (e: HTMLDivElement): void => {\n        if (this.dropdownRootElement) {\n            this.dropdownRootElement.removeEventListener(\"click\", this.onRootClick, false);\n        }\n        if (e) {\n            e.addEventListener(\"click\", this.onRootClick, false);\n        }\n        this.dropdownRootElement = e;\n    };\n\n    private setHighlightedOption = (optionKey: string): void => {\n        this.setState({\n            highlightedOption: optionKey,\n        });\n    };\n\n    private nextOption(optionKey: string): string {\n        const keys = Object.keys(this.childrenByKey);\n        const index = keys.indexOf(optionKey);\n        return keys[(index + 1) % keys.length];\n    }\n\n    private prevOption(optionKey: string): string {\n        const keys = Object.keys(this.childrenByKey);\n        const index = keys.indexOf(optionKey);\n        return keys[index <= 0 ? keys.length - 1 : (index - 1) % keys.length];\n    }\n\n    private scrollIntoView(node: Element | null): void {\n        node?.scrollIntoView({\n            block: \"nearest\",\n            behavior: \"auto\",\n        });\n    }\n\n    private getMenuOptions(): JSX.Element[] {\n        const options = React.Children.map(this.props.children, (child: ReactElement) => {\n            const highlighted = this.state.highlightedOption === child.key;\n            return (\n                <MenuOption\n                    id={`${this.props.id}__${child.key}`}\n                    key={child.key}\n                    dropdownKey={child.key as string}\n                    highlighted={highlighted}\n                    onMouseEnter={this.setHighlightedOption}\n                    onClick={this.onMenuOptionClick}\n                    inputRef={highlighted ? this.scrollIntoView : undefined}\n                >\n                    {child}\n                </MenuOption>\n            );\n        });\n        if (!options?.length) {\n            return [\n                <li key=\"0\" className=\"mx_Dropdown_option\" role=\"option\" aria-selected={false}>\n                    {_t(\"common|no_results\")}\n                </li>,\n            ];\n        }\n        return options;\n    }\n\n    public render(): React.ReactNode {\n        let currentValue: JSX.Element | undefined;\n\n        const menuStyle: CSSProperties = {};\n        if (this.props.menuWidth) menuStyle.width = this.props.menuWidth;\n\n        let menu: JSX.Element | undefined;\n        if (this.state.expanded) {\n            if (this.props.searchEnabled) {\n                currentValue = (\n                    <input\n                        id={`${this.props.id}_input`}\n                        type=\"text\"\n                        autoFocus={true}\n                        autoComplete={this.props.autoComplete}\n                        className=\"mx_Dropdown_option\"\n                        onChange={this.onInputChange}\n                        value={this.state.searchQuery}\n                        role=\"combobox\"\n                        aria-autocomplete=\"list\"\n                        aria-activedescendant={`${this.props.id}__${this.state.highlightedOption}`}\n                        aria-expanded={this.state.expanded}\n                        aria-controls={`${this.props.id}_listbox`}\n                        aria-disabled={this.props.disabled}\n                        aria-label={this.props.label}\n                        onKeyDown={this.onKeyDown}\n                    />\n                );\n            }\n            menu = (\n                <ul className=\"mx_Dropdown_menu\" style={menuStyle} role=\"listbox\" id={`${this.props.id}_listbox`}>\n                    {this.getMenuOptions()}\n                </ul>\n            );\n        }\n\n        if (!currentValue) {\n            let selectedChild: ReactNode | undefined;\n            if (this.props.value) {\n                selectedChild = this.props.getShortOption\n                    ? this.props.getShortOption(this.props.value)\n                    : this.childrenByKey[this.props.value];\n            }\n\n            currentValue = (\n                <div className=\"mx_Dropdown_option\" id={`${this.props.id}_value`}>\n                    {selectedChild || this.props.placeholder}\n                </div>\n            );\n        }\n\n        const dropdownClasses = classnames(\"mx_Dropdown\", this.props.className, {\n            mx_Dropdown_disabled: !!this.props.disabled,\n        });\n\n        // Note the menu sits inside the AccessibleButton div so it's anchored\n        // to the input, but overflows below it. The root contains both.\n        return (\n            <div className={dropdownClasses} ref={this.collectRoot}>\n                <AccessibleButton\n                    className=\"mx_Dropdown_input mx_no_textinput\"\n                    onClick={this.onAccessibleButtonClick}\n                    aria-haspopup=\"listbox\"\n                    aria-expanded={this.state.expanded}\n                    disabled={this.props.disabled}\n                    ref={this.buttonRef}\n                    aria-label={this.props.label}\n                    aria-describedby={`${this.props.id}_value`}\n                    aria-owns={`${this.props.id}_input`}\n                    onKeyDown={this.onKeyDown}\n                >\n                    {currentValue}\n                    <ChevronDownIcon className=\"mx_Dropdown_arrow\" />\n                    {menu}\n                </AccessibleButton>\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ErrorInfo, type ReactNode } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport PlatformPeg from \"../../../PlatformPeg\";\nimport SdkConfig from \"../../../SdkConfig\";\nimport AccessibleButton from \"./AccessibleButton\";\nimport { BugReportDialogButton } from \"./BugReportDialogButton\";\n\ninterface Props {\n    children: ReactNode;\n}\n\ninterface IState {\n    error?: Error;\n}\n\n/**\n * This error boundary component can be used to wrap large content areas and\n * catch exceptions during rendering in the component tree below them.\n */\nexport default class ErrorBoundary extends React.PureComponent<Props, IState> {\n    public constructor(props: Props) {\n        super(props);\n\n        this.state = {};\n    }\n\n    public static getDerivedStateFromError(error: Error): Partial<IState> {\n        // Side effects are not permitted here, so we only update the state so\n        // that the next render shows an error message.\n        return { error };\n    }\n\n    public componentDidCatch(error: Error, { componentStack }: ErrorInfo): void {\n        // Browser consoles are better at formatting output when native errors are passed\n        // in their own `console.error` invocation.\n        logger.error(error);\n        logger.error(\"The above error occurred while React was rendering the following components:\", componentStack);\n    }\n\n    private onClearCacheAndReload = (): void => {\n        if (!PlatformPeg.get()) return;\n\n        MatrixClientPeg.safeGet().stopClient();\n        MatrixClientPeg.safeGet()\n            .store.deleteAllData()\n            .then(() => {\n                PlatformPeg.get()?.reload();\n            });\n    };\n\n    public render(): ReactNode {\n        if (this.state.error) {\n            const newIssueUrl = SdkConfig.get().feedback.new_issue_url;\n\n            let bugReportSection;\n            if (SdkConfig.get().bug_report_endpoint_url) {\n                bugReportSection = (\n                    <React.Fragment>\n                        <p>\n                            {_t(\n                                \"bug_reporting|create_new_issue\",\n                                {},\n                                {\n                                    newIssueLink: (sub) => {\n                                        return (\n                                            <a target=\"_blank\" rel=\"noreferrer noopener\" href={newIssueUrl}>\n                                                {sub}\n                                            </a>\n                                        );\n                                    },\n                                },\n                            )}\n                        </p>\n                        <p>\n                            {_t(\"bug_reporting|introduction\")}\n                            &nbsp;\n                            {_t(\"bug_reporting|description\")}\n                        </p>\n                        <BugReportDialogButton error={this.state.error} label=\"react-soft-crash\" />\n                    </React.Fragment>\n                );\n            }\n\n            let clearCacheButton: JSX.Element | undefined;\n            // we only show this button if there is an initialised MatrixClient otherwise we can't clear the cache\n            if (MatrixClientPeg.get()) {\n                clearCacheButton = (\n                    <AccessibleButton onClick={this.onClearCacheAndReload} kind=\"danger\">\n                        {_t(\"setting|help_about|clear_cache_reload\")}\n                    </AccessibleButton>\n                );\n            }\n\n            return (\n                <div className=\"mx_ErrorBoundary\">\n                    <div className=\"mx_ErrorBoundary_body\">\n                        <h1>{_t(\"error|something_went_wrong\")}</h1>\n                        {bugReportSection}\n                        {clearCacheButton}\n                    </div>\n                </div>\n            );\n        }\n\n        return this.props.children;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type DetailedHTMLProps, type AnchorHTMLAttributes } from \"react\";\nimport classNames from \"classnames\";\nimport PopOutIcon from \"@vector-im/compound-design-tokens/assets/web/icons/pop-out\";\n\ninterface Props extends DetailedHTMLProps<AnchorHTMLAttributes<HTMLAnchorElement>, HTMLAnchorElement> {}\n\n/**\n * Simple link component that adds external link icon after link children\n */\nconst ExternalLink: React.FC<Props> = ({ children, className, ...rest }) => (\n    <a target=\"_blank\" rel=\"noreferrer noopener\" {...rest} className={classNames(\"mx_ExternalLink\", className)}>\n        {children}\n        <PopOutIcon className=\"mx_ExternalLink_icon\" />\n    </a>\n);\n\nexport default ExternalLink;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type FC, type HTMLAttributes, type ReactNode } from \"react\";\nimport { type RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { AvatarStack, Tooltip } from \"@vector-im/compound-web\";\nimport classNames from \"classnames\";\nimport { OverflowHorizontalIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport MemberAvatar from \"../avatars/MemberAvatar\";\nimport AccessibleButton, { type ButtonEvent } from \"./AccessibleButton\";\nimport { useToggled } from \"../rooms/RoomHeader/toggle/useToggled\";\nimport { RightPanelPhases } from \"../../../stores/right-panel/RightPanelStorePhases\";\n\ninterface IProps extends Omit<HTMLAttributes<HTMLDivElement>, \"onChange\"> {\n    members: RoomMember[];\n    size: string;\n    overflow: boolean;\n    tooltipLabel?: string;\n    tooltipShortcut?: string;\n    children?: ReactNode;\n    viewUserOnClick?: boolean;\n    onClick?: (e: ButtonEvent) => void | Promise<void>;\n}\n\n/**\n * A component which displays a list of avatars in a row, with a tooltip showing the names of the users.\n *\n * Any additional props, not named explicitly here, are passed to the underlying {@link AccessibleButton}.\n */\nconst FacePile: FC<IProps> = ({\n    members,\n    size,\n    overflow,\n    tooltipLabel,\n    tooltipShortcut,\n    children,\n    viewUserOnClick = true,\n    onClick,\n    ...props\n}) => {\n    const faces = members.map(\n        tooltipLabel\n            ? (m) => <MemberAvatar key={m.userId} member={m} size={size} hideTitle />\n            : (m) => (\n                  <Tooltip key={m.userId} label={m.name} caption={tooltipShortcut}>\n                      <MemberAvatar member={m} size={size} viewUserOnClick={!onClick && viewUserOnClick} hideTitle />\n                  </Tooltip>\n              ),\n    );\n\n    const pileContents = (\n        <>\n            {faces}\n            {overflow ? <OverflowHorizontalIcon className=\"mx_FacePile_more\" /> : null}\n        </>\n    );\n\n    const toggled = useToggled(RightPanelPhases.MemberList);\n    const classes = classNames({\n        mx_FacePile: true,\n        mx_FacePile_toggled: toggled,\n    });\n\n    const content = (\n        <AccessibleButton {...props} className={classes} onClick={onClick ?? null}>\n            <AvatarStack>{pileContents}</AvatarStack>\n            {children}\n        </AccessibleButton>\n    );\n\n    return tooltipLabel ? (\n        <Tooltip label={tooltipLabel} caption={tooltipShortcut}>\n            {content}\n        </Tooltip>\n    ) : (\n        content\n    );\n};\n\nexport default FacePile;\n","/*\nCopyright 2019-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, {\n    type JSX,\n    type InputHTMLAttributes,\n    type SelectHTMLAttributes,\n    type TextareaHTMLAttributes,\n    type RefObject,\n    createRef,\n    type ComponentProps,\n    type RefCallback,\n    type Ref,\n} from \"react\";\nimport classNames from \"classnames\";\nimport { debounce } from \"lodash\";\nimport { Tooltip } from \"@vector-im/compound-web\";\nimport { ChevronDownIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { type IFieldState, type IValidationResult } from \"./Validation\";\n\n// Invoke validation from user input (when typing, etc.) at most once every N ms.\nconst VALIDATION_THROTTLE_MS = 200;\n\nconst BASE_ID = \"mx_Field\";\nlet count = 1;\nfunction getId(): string {\n    return `${BASE_ID}_${count++}`;\n}\n\nexport interface IValidateOpts {\n    focused?: boolean;\n    allowEmpty?: boolean;\n}\n\ninterface IProps {\n    // The field's ID, which binds the input and label together. Immutable.\n    id?: string;\n    // The field's label string.\n    label?: string;\n    // The field's placeholder string. Defaults to the label.\n    placeholder?: string;\n    // When true (default false), the placeholder will be shown instead of the label when\n    // the component is unfocused & empty.\n    usePlaceholderAsHint?: boolean;\n    // Optional component to include inside the field before the input.\n    prefixComponent?: React.ReactNode;\n    // Optional component to include inside the field after the input.\n    postfixComponent?: React.ReactNode;\n    // The callback called whenever the contents of the field\n    // changes.  Returns an object with `valid` boolean field\n    // and a `feedback` react component field to provide feedback\n    // to the user.\n    onValidate?: (input: IFieldState) => Promise<IValidationResult>;\n    // If specified, overrides the value returned by onValidate.\n    forceValidity?: boolean;\n    // If specified, contents will appear as a tooltip on the element and\n    // validation feedback tooltips will be suppressed.\n    tooltipContent?: JSX.Element | string;\n    // If specified the tooltip will be shown regardless of feedback\n    forceTooltipVisible?: boolean;\n    // If specified, the tooltip with be aligned accorindly with the field, defaults to Right.\n    tooltipAlignment?: ComponentProps<typeof Tooltip>[\"placement\"];\n    // If specified alongside tooltipContent, the class name to apply to the\n    // tooltip itself.\n    tooltipClassName?: string;\n    // If specified, an additional class name to apply to the field container\n    className?: string;\n    // On what events should validation occur; by default on all\n    validateOnFocus?: boolean;\n    validateOnBlur?: boolean;\n    validateOnChange?: boolean;\n    // All other props pass through to the <input>.\n}\n\nexport interface IInputProps extends IProps, InputHTMLAttributes<HTMLInputElement> {\n    // The ref pass through to the input\n    inputRef?: Ref<HTMLInputElement>;\n    // The element to create. Defaults to \"input\".\n    element: \"input\";\n    // The input's value. This is a controlled component, so the value is required.\n    value: string;\n}\n\ninterface ISelectProps extends IProps, SelectHTMLAttributes<HTMLSelectElement> {\n    // The ref pass through to the select\n    inputRef?: Ref<HTMLSelectElement>;\n    // To define options for a select, use <Field><option ... /></Field>\n    element: \"select\";\n    // The select's value. This is a controlled component, so the value is required.\n    value: string;\n}\n\ninterface ITextareaProps extends IProps, TextareaHTMLAttributes<HTMLTextAreaElement> {\n    // The ref pass through to the textarea\n    inputRef?: Ref<HTMLTextAreaElement>;\n    element: \"textarea\";\n    // The textarea's value. This is a controlled component, so the value is required.\n    value: string;\n}\n\nexport interface INativeOnChangeInputProps extends IProps, InputHTMLAttributes<HTMLInputElement> {\n    // The ref pass through to the input\n    inputRef?: Ref<HTMLInputElement>;\n    element: \"input\";\n    // The input's value. This is a controlled component, so the value is required.\n    value: string;\n}\n\ntype PropShapes = IInputProps | ISelectProps | ITextareaProps | INativeOnChangeInputProps;\n\ninterface IState {\n    valid?: boolean;\n    feedback?: JSX.Element | string;\n    feedbackVisible: boolean;\n    focused: boolean;\n}\n\nexport default class Field extends React.PureComponent<PropShapes, IState> {\n    private readonly id: string;\n    private readonly _inputRef = createRef<HTMLInputElement | HTMLSelectElement | HTMLTextAreaElement>();\n\n    /**\n     * When props.inputRef is a callback ref, we will pass callbackRef to the DOM element.\n     * This is so that other methods here can still access the DOM element via this._inputRef.\n     */\n    private readonly callbackRef: RefCallback<HTMLInputElement | HTMLSelectElement | HTMLTextAreaElement> = (node) => {\n        this._inputRef.current = node;\n        (this.props.inputRef as RefCallback<unknown>)(node);\n    };\n\n    public static readonly defaultProps = {\n        element: \"input\",\n        type: \"text\",\n        validateOnFocus: true,\n        validateOnBlur: true,\n        validateOnChange: true,\n        tooltipAlignment: \"right\",\n    };\n\n    /*\n     * This was changed from throttle to debounce: this is more traditional for\n     * form validation since it means that the validation doesn't happen at all\n     * until the user stops typing for a bit (debounce defaults to not running on\n     * the leading edge). If we're doing an HTTP hit on each validation, we have more\n     * incentive to prevent validating input that's very unlikely to be valid.\n     * We may find that we actually want different behaviour for registration\n     * fields, in which case we can add some options to control it.\n     */\n    private validateOnChange = debounce(() => {\n        this.validate({\n            focused: true,\n        });\n    }, VALIDATION_THROTTLE_MS);\n\n    public constructor(props: PropShapes) {\n        super(props);\n        this.state = {\n            feedbackVisible: false,\n            focused: false,\n        };\n\n        this.id = this.props.id || getId();\n    }\n\n    public focus(): void {\n        this.inputRef.current?.focus();\n        // programmatic does not fire onFocus handler\n        this.setState({\n            focused: true,\n        });\n    }\n\n    private onFocus = (ev: React.FocusEvent<any>): void => {\n        this.setState({\n            focused: true,\n        });\n        if (this.props.validateOnFocus) {\n            this.validate({\n                focused: true,\n            });\n        }\n        // Parent component may have supplied its own `onFocus` as well\n        this.props.onFocus?.(ev);\n    };\n\n    private onChange = (ev: React.ChangeEvent<any>): void => {\n        if (this.props.validateOnChange) {\n            this.validateOnChange();\n        }\n        // Parent component may have supplied its own `onChange` as well\n        this.props.onChange?.(ev);\n    };\n\n    private onBlur = (ev: React.FocusEvent<any>): void => {\n        this.setState({\n            focused: false,\n        });\n        if (this.props.validateOnBlur) {\n            this.validate({\n                focused: false,\n            });\n        }\n        // Parent component may have supplied its own `onBlur` as well\n        this.props.onBlur?.(ev);\n    };\n\n    public async validate({ focused, allowEmpty = true }: IValidateOpts): Promise<boolean | undefined> {\n        if (!this.props.onValidate) {\n            return;\n        }\n        const value = this.inputRef.current?.value ?? null;\n        const { valid, feedback } = await this.props.onValidate({\n            value,\n            focused: !!focused,\n            allowEmpty,\n        });\n\n        // this method is async and so we may have been blurred since the method was called\n        // if we have then hide the feedback as withValidation does\n        if (this.state.focused && feedback) {\n            this.setState({\n                valid,\n                feedback,\n                feedbackVisible: true,\n            });\n        } else {\n            // When we receive null `feedback`, we want to hide the tooltip.\n            // We leave the previous `feedback` content in state without updating it,\n            // so that we can hide the tooltip containing the most recent feedback\n            // via CSS animation.\n            this.setState({\n                valid,\n                feedbackVisible: false,\n            });\n        }\n\n        return valid;\n    }\n\n    private get inputRef(): RefObject<HTMLInputElement | HTMLSelectElement | HTMLTextAreaElement | null> {\n        const inputRef = this.props.inputRef;\n        if (typeof inputRef === \"function\") {\n            // This is a callback ref, so return _inputRef which will point to the actual DOM element.\n            return this._inputRef;\n        }\n        return inputRef ?? this._inputRef;\n    }\n\n    private onTooltipOpenChange = (open: boolean): void => {\n        this.setState({\n            feedbackVisible: open,\n        });\n    };\n\n    public render(): React.ReactNode {\n        /* eslint @typescript-eslint/no-unused-vars: [\"error\", { \"ignoreRestSiblings\": true }] */\n        const {\n            element,\n            inputRef,\n            prefixComponent,\n            postfixComponent,\n            className,\n            onValidate,\n            children,\n            tooltipContent,\n            forceValidity,\n            tooltipClassName,\n            validateOnBlur,\n            validateOnChange,\n            validateOnFocus,\n            usePlaceholderAsHint,\n            forceTooltipVisible,\n            tooltipAlignment,\n            ...inputProps\n        } = this.props;\n\n        // Handle displaying feedback on validity\n        const tooltipProps: Pick<React.ComponentProps<typeof Tooltip>, \"aria-live\" | \"aria-atomic\"> = {};\n        let tooltipOpen = false;\n        if (tooltipContent || this.state.feedback) {\n            tooltipOpen = (this.state.focused && forceTooltipVisible) || this.state.feedbackVisible;\n\n            if (!tooltipContent) {\n                tooltipProps[\"aria-atomic\"] = \"true\";\n                tooltipProps[\"aria-live\"] = this.state.valid ? \"polite\" : \"assertive\";\n            }\n        }\n\n        inputProps.placeholder = inputProps.placeholder ?? inputProps.label;\n        inputProps.id = this.id; // this overwrites the id from props\n\n        inputProps.onFocus = this.onFocus;\n        inputProps.onChange = this.onChange;\n        inputProps.onBlur = this.onBlur;\n\n        // Appease typescript's inference\n        const inputProps_: React.HTMLAttributes<HTMLSelectElement | HTMLInputElement | HTMLTextAreaElement> &\n            React.ClassAttributes<HTMLSelectElement | HTMLInputElement | HTMLTextAreaElement> = {\n            ...inputProps,\n            ref: typeof this.props.inputRef === \"function\" ? this.callbackRef : this.inputRef,\n        };\n\n        const fieldInput = React.createElement(this.props.element, inputProps_, children);\n\n        let prefixContainer: JSX.Element | undefined;\n        if (prefixComponent) {\n            prefixContainer = <span className=\"mx_Field_prefix\">{prefixComponent}</span>;\n        }\n        let postfixContainer: JSX.Element | undefined;\n        if (postfixComponent) {\n            postfixContainer = <span className=\"mx_Field_postfix\">{postfixComponent}</span>;\n        }\n\n        const hasValidationFlag = forceValidity !== null && forceValidity !== undefined;\n        const fieldClasses = classNames(\"mx_Field\", `mx_Field_${this.props.element}`, className, {\n            // If we have a prefix element, leave the label always at the top left and\n            // don't animate it, as it looks a bit clunky and would add complexity to do\n            // properly.\n            mx_Field_labelAlwaysTopLeft: prefixComponent || usePlaceholderAsHint,\n            mx_Field_placeholderIsHint: usePlaceholderAsHint,\n            mx_Field_valid: hasValidationFlag ? forceValidity : onValidate && this.state.valid === true,\n            mx_Field_invalid: hasValidationFlag ? !forceValidity : onValidate && this.state.valid === false,\n        });\n\n        let inputDecoration: JSX.Element | undefined;\n        if (this.props.element === \"select\") {\n            inputDecoration = <ChevronDownIcon className=\"mx_Field_select_chevron\" />;\n        }\n\n        return (\n            <div className={fieldClasses}>\n                {prefixContainer}\n                <Tooltip\n                    {...tooltipProps}\n                    placement={tooltipAlignment}\n                    description=\"\"\n                    caption={tooltipContent || this.state.feedback}\n                    open={tooltipOpen}\n                    onOpenChange={this.onTooltipOpenChange}\n                >\n                    {fieldInput}\n                </Tooltip>\n                <label htmlFor={this.id}>{this.props.label}</label>\n                {inputDecoration}\n                {postfixContainer}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\n * Different browsers use different deltaModes. This causes different behaviour.\n * To avoid that we use this function to convert any event to pixels.\n * @param {WheelEvent} event to normalize\n * @returns {WheelEvent} normalized event event\n */\nexport function normalizeWheelEvent({ deltaMode, deltaX, deltaY, deltaZ, ...event }: WheelEvent): WheelEvent {\n    const LINE_HEIGHT = 18;\n\n    if (deltaMode === 1) {\n        // Units are lines\n        deltaX *= LINE_HEIGHT;\n        deltaY *= LINE_HEIGHT;\n        deltaZ *= LINE_HEIGHT;\n    }\n\n    return new WheelEvent(\"syntheticWheel\", {\n        deltaMode: 0,\n        deltaY,\n        deltaX,\n        deltaZ,\n        ...event,\n    });\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, createRef, type CSSProperties, useEffect } from \"react\";\nimport FocusLock from \"react-focus-lock\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport {\n    CloseIcon,\n    DownloadIcon,\n    OverflowHorizontalIcon,\n    RotateLeftIcon,\n    RotateRightIcon,\n    ZoomInIcon,\n    ZoomOutIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport MemberAvatar from \"../avatars/MemberAvatar\";\nimport { ContextMenuTooltipButton } from \"../../../accessibility/context_menu/ContextMenuTooltipButton\";\nimport MessageContextMenu from \"../context_menus/MessageContextMenu\";\nimport { aboveLeftOf } from \"../../structures/ContextMenu\";\nimport MessageTimestamp from \"../messages/MessageTimestamp\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { type RoomPermalinkCreator } from \"../../../utils/permalinks/Permalinks\";\nimport { normalizeWheelEvent } from \"../../../utils/Mouse\";\nimport UIStore from \"../../../stores/UIStore\";\nimport { type ViewRoomPayload } from \"../../../dispatcher/payloads/ViewRoomPayload\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { presentableTextForFile } from \"../../../utils/FileUtils\";\nimport AccessibleButton from \"./AccessibleButton\";\nimport { useDownloadMedia } from \"../../../hooks/useDownloadMedia.ts\";\n\n// Max scale to keep gaps around the image\nconst MAX_SCALE = 0.95;\n// This is used for the buttons\nconst ZOOM_STEP = 0.1;\n// This is used for mouse wheel events\nconst ZOOM_COEFFICIENT = 0.0025;\n// If we have moved only this much we can zoom\nconst ZOOM_DISTANCE = 10;\n\n// Height of mx_ImageView_panel\nconst getPanelHeight = (): number => {\n    const value = getComputedStyle(document.documentElement).getPropertyValue(\"--image-view-panel-height\");\n    // Return the value as a number without the unit\n    return parseInt(value.slice(0, value.length - 2));\n};\n\ninterface IProps {\n    src: string; // the source of the image being displayed\n    name?: string; // the main title ('name') for the image\n    link?: string; // the link (if any) applied to the name of the image\n    width?: number; // width of the image src in pixels\n    height?: number; // height of the image src in pixels\n    fileSize?: number; // size of the image src in bytes\n\n    // the event (if any) that the Image is displaying. Used for event-specific stuff like\n    // redactions, senders, timestamps etc.  Other descriptors are taken from the explicit\n    // properties above, which let us use lightboxes to display images which aren't associated\n    // with events.\n    mxEvent?: MatrixEvent;\n    permalinkCreator?: RoomPermalinkCreator;\n\n    thumbnailInfo?: {\n        positionX: number;\n        positionY: number;\n        width: number;\n        height: number;\n    };\n    onFinished(): void;\n}\n\ninterface IState {\n    zoom: number;\n    minZoom: number;\n    maxZoom: number;\n    rotation: number;\n    translationX: number;\n    translationY: number;\n    moving: boolean;\n    contextMenuDisplayed: boolean;\n}\n\nexport default class ImageView extends React.Component<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n\n        const { thumbnailInfo } = this.props;\n\n        let translationX = 0;\n        let translationY = 0;\n        if (thumbnailInfo) {\n            translationX = thumbnailInfo.positionX + thumbnailInfo.width / 2 - UIStore.instance.windowWidth / 2;\n            translationY =\n                thumbnailInfo.positionY +\n                thumbnailInfo.height / 2 -\n                UIStore.instance.windowHeight / 2 -\n                getPanelHeight() / 2;\n        }\n\n        this.state = {\n            zoom: 0, // We default to 0 and override this in imageLoaded once we have naturalSize\n            minZoom: MAX_SCALE,\n            maxZoom: MAX_SCALE,\n            rotation: 0,\n            translationX,\n            translationY,\n            moving: false,\n            contextMenuDisplayed: false,\n        };\n    }\n\n    // XXX: Refs to functional components\n    private contextMenuButton = createRef<any>();\n    private focusLock = createRef<any>();\n    private imageWrapper = createRef<HTMLDivElement>();\n    private image = createRef<HTMLImageElement>();\n\n    private downloadFunction?: () => Promise<void>;\n\n    private initX = 0;\n    private initY = 0;\n    private previousX = 0;\n    private previousY = 0;\n\n    private animatingLoading = false;\n    private imageIsLoaded = false;\n\n    public componentDidMount(): void {\n        // We have to use addEventListener() because the listener\n        // needs to be passive in order to work with Chromium\n        this.focusLock.current.addEventListener(\"wheel\", this.onWheel, { passive: false });\n        // We want to recalculate zoom whenever the window's size changes\n        window.addEventListener(\"resize\", this.recalculateZoom);\n        // After the image loads for the first time we want to calculate the zoom\n        this.image.current?.addEventListener(\"load\", this.imageLoaded);\n    }\n\n    public componentWillUnmount(): void {\n        this.focusLock.current.removeEventListener(\"wheel\", this.onWheel);\n        window.removeEventListener(\"resize\", this.recalculateZoom);\n        this.image.current?.removeEventListener(\"load\", this.imageLoaded);\n    }\n\n    private imageLoaded = (): void => {\n        if (!this.image.current) return;\n        // First, we calculate the zoom, so that the image has the same size as\n        // the thumbnail\n        const { thumbnailInfo } = this.props;\n        if (thumbnailInfo?.width) {\n            this.setState({ zoom: thumbnailInfo.width / this.image.current.naturalWidth });\n        }\n\n        // Once the zoom is set, we the image is considered loaded and we can\n        // start animating it into the center of the screen\n        this.imageIsLoaded = true;\n        this.animatingLoading = true;\n        this.setZoomAndRotation();\n        this.setState({\n            translationX: 0,\n            translationY: 0,\n        });\n\n        // Once the position is set, there is no need to animate anymore\n        this.animatingLoading = false;\n    };\n\n    private recalculateZoom = (): void => {\n        this.setZoomAndRotation();\n    };\n\n    private setZoomAndRotation = (inputRotation?: number): void => {\n        const image = this.image.current;\n        const imageWrapper = this.imageWrapper.current;\n        if (!image || !imageWrapper) return;\n\n        const rotation = inputRotation ?? this.state.rotation;\n\n        const imageIsNotFlipped = rotation % 180 === 0;\n\n        // If the image is rotated take it into account\n        const width = imageIsNotFlipped ? image.naturalWidth : image.naturalHeight;\n        const height = imageIsNotFlipped ? image.naturalHeight : image.naturalWidth;\n\n        const zoomX = imageWrapper.clientWidth / width;\n        const zoomY = imageWrapper.clientHeight / height;\n\n        // If the image is smaller in both dimensions set its the zoom to 1 to\n        // display it in its original size\n        if (zoomX >= 1 && zoomY >= 1) {\n            this.setState({\n                zoom: 1,\n                minZoom: 1,\n                maxZoom: 1,\n                rotation: rotation,\n            });\n            return;\n        }\n        // We set minZoom to the min of the zoomX and zoomY to avoid overflow in\n        // any direction. We also multiply by MAX_SCALE to get a gap around the\n        // image by default\n        const minZoom = Math.min(zoomX, zoomY) * MAX_SCALE;\n\n        // If zoom is smaller than minZoom don't go below that value\n        const zoom = this.state.zoom <= this.state.minZoom ? minZoom : this.state.zoom;\n\n        this.setState({\n            minZoom: minZoom,\n            maxZoom: 1,\n            rotation: rotation,\n            zoom: zoom,\n        });\n    };\n\n    private zoomDelta(delta: number, anchorX?: number, anchorY?: number): void {\n        this.zoom(this.state.zoom + delta, anchorX, anchorY);\n    }\n\n    private zoom(zoomLevel: number, anchorX?: number, anchorY?: number): void {\n        const oldZoom = this.state.zoom;\n        const maxZoom = this.state.maxZoom === this.state.minZoom ? 2 * this.state.maxZoom : this.state.maxZoom;\n        const newZoom = Math.min(zoomLevel, maxZoom);\n        if (newZoom <= this.state.minZoom) {\n            // Zoom out fully\n            this.setState({\n                zoom: this.state.minZoom,\n                translationX: 0,\n                translationY: 0,\n            });\n        } else if (typeof anchorX !== \"number\" || typeof anchorY !== \"number\") {\n            // Zoom relative to the center of the view\n            this.setState({\n                zoom: newZoom,\n                translationX: (this.state.translationX * newZoom) / oldZoom,\n                translationY: (this.state.translationY * newZoom) / oldZoom,\n            });\n        } else if (this.image.current) {\n            // Zoom relative to the given point on the image.\n            // First we need to figure out the offset of the anchor point\n            // relative to the center of the image, accounting for rotation.\n            let offsetX: number;\n            let offsetY: number;\n            // The modulo operator can return negative values for some\n            // rotations, so we have to do some extra work to normalize it\n            const rotation = (((this.state.rotation % 360) + 360) % 360) as 0 | 90 | 180 | 270;\n            switch (rotation) {\n                case 0:\n                    offsetX = this.image.current.clientWidth / 2 - anchorX;\n                    offsetY = this.image.current.clientHeight / 2 - anchorY;\n                    break;\n                case 90:\n                    offsetX = anchorY - this.image.current.clientHeight / 2;\n                    offsetY = this.image.current.clientWidth / 2 - anchorX;\n                    break;\n                case 180:\n                    offsetX = anchorX - this.image.current.clientWidth / 2;\n                    offsetY = anchorY - this.image.current.clientHeight / 2;\n                    break;\n                case 270:\n                    offsetX = this.image.current.clientHeight / 2 - anchorY;\n                    offsetY = anchorX - this.image.current.clientWidth / 2;\n            }\n\n            // Apply the zoom and offset\n            this.setState({\n                zoom: newZoom,\n                translationX: this.state.translationX + (newZoom - oldZoom) * offsetX,\n                translationY: this.state.translationY + (newZoom - oldZoom) * offsetY,\n            });\n        }\n    }\n\n    private onWheel = (ev: WheelEvent): void => {\n        if (ev.target === this.image.current) {\n            ev.stopPropagation();\n            ev.preventDefault();\n\n            const { deltaY } = normalizeWheelEvent(ev);\n            // Zoom in on the point on the image targeted by the cursor\n            this.zoomDelta(-deltaY * ZOOM_COEFFICIENT, ev.offsetX, ev.offsetY);\n        }\n    };\n\n    private onZoomInClick = (): void => {\n        this.zoomDelta(ZOOM_STEP);\n    };\n\n    private onZoomOutClick = (): void => {\n        this.zoomDelta(-ZOOM_STEP);\n    };\n\n    private onKeyDown = (ev: KeyboardEvent): void => {\n        const action = getKeyBindingsManager().getAccessibilityAction(ev);\n        switch (action) {\n            case KeyBindingAction.Escape:\n                ev.stopPropagation();\n                ev.preventDefault();\n                this.props.onFinished();\n                break;\n            case KeyBindingAction.Save:\n                ev.preventDefault();\n                ev.stopPropagation();\n                if (this.downloadFunction) {\n                    this.downloadFunction();\n                }\n                break;\n        }\n    };\n\n    private onRotateCounterClockwiseClick = (): void => {\n        const cur = this.state.rotation;\n        this.setZoomAndRotation(cur - 90);\n    };\n\n    private onRotateClockwiseClick = (): void => {\n        const cur = this.state.rotation;\n        this.setZoomAndRotation(cur + 90);\n    };\n\n    private onOpenContextMenu = (): void => {\n        this.setState({\n            contextMenuDisplayed: true,\n        });\n    };\n\n    private onCloseContextMenu = (): void => {\n        this.setState({\n            contextMenuDisplayed: false,\n        });\n    };\n\n    private onDownloadFunctionReady = (download: () => Promise<void>): void => {\n        this.downloadFunction = download;\n    };\n\n    private onPermalinkClicked = (ev: React.MouseEvent): void => {\n        // This allows the permalink to be opened in a new tab/window or copied as\n        // matrix.to, but also for it to enable routing within Element when clicked.\n        ev.preventDefault();\n        dis.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            event_id: this.props.mxEvent?.getId(),\n            highlighted: true,\n            room_id: this.props.mxEvent?.getRoomId(),\n            metricsTrigger: undefined, // room doesn't change\n        });\n        this.props.onFinished();\n    };\n\n    private onStartMoving = (ev: React.MouseEvent): void => {\n        ev.stopPropagation();\n        ev.preventDefault();\n\n        // Don't do anything if we pressed any\n        // other button than the left one\n        if (ev.button !== 0) return;\n\n        // Zoom in if we are completely zoomed out and increase the zoom factor for images\n        // smaller than the viewport size\n        if (this.state.zoom === this.state.minZoom) {\n            this.zoom(\n                this.state.maxZoom === this.state.minZoom ? 2 * this.state.maxZoom : this.state.maxZoom,\n                ev.nativeEvent.offsetX,\n                ev.nativeEvent.offsetY,\n            );\n            return;\n        }\n\n        this.setState({ moving: true });\n        this.previousX = this.state.translationX;\n        this.previousY = this.state.translationY;\n        this.initX = ev.pageX - this.state.translationX;\n        this.initY = ev.pageY - this.state.translationY;\n    };\n\n    private onMoving = (ev: React.MouseEvent): void => {\n        ev.stopPropagation();\n        ev.preventDefault();\n\n        if (!this.state.moving) return;\n\n        this.setState({\n            translationX: ev.pageX - this.initX,\n            translationY: ev.pageY - this.initY,\n        });\n    };\n\n    private onEndMoving = (): void => {\n        // Zoom out if we haven't moved much\n        if (\n            this.state.moving &&\n            Math.abs(this.state.translationX - this.previousX) < ZOOM_DISTANCE &&\n            Math.abs(this.state.translationY - this.previousY) < ZOOM_DISTANCE\n        ) {\n            this.zoom(this.state.minZoom);\n            this.initX = 0;\n            this.initY = 0;\n        }\n        this.setState({ moving: false });\n    };\n\n    private renderContextMenu(): JSX.Element {\n        let contextMenu: JSX.Element | undefined;\n        if (this.state.contextMenuDisplayed && this.props.mxEvent) {\n            contextMenu = (\n                <MessageContextMenu\n                    {...aboveLeftOf(this.contextMenuButton.current.getBoundingClientRect())}\n                    mxEvent={this.props.mxEvent}\n                    permalinkCreator={this.props.permalinkCreator}\n                    onFinished={this.onCloseContextMenu}\n                    onCloseDialog={this.props.onFinished}\n                />\n            );\n        }\n\n        return <React.Fragment>{contextMenu}</React.Fragment>;\n    }\n\n    public render(): React.ReactNode {\n        const showEventMeta = !!this.props.mxEvent;\n\n        let transitionClassName;\n        if (this.animatingLoading) transitionClassName = \"mx_ImageView_image_animatingLoading\";\n        else if (this.state.moving || !this.imageIsLoaded) transitionClassName = \"\";\n        else transitionClassName = \"mx_ImageView_image_animating\";\n\n        const rotationDegrees = this.state.rotation + \"deg\";\n        const zoom = this.state.zoom;\n        const translatePixelsX = this.state.translationX + \"px\";\n        const translatePixelsY = this.state.translationY + \"px\";\n        // The order of the values is important!\n        // First, we translate and only then we rotate, otherwise\n        // we would apply the translation to an already rotated\n        // image causing it translate in the wrong direction.\n        const style: CSSProperties = {\n            transform: `translateX(${translatePixelsX})\n                        translateY(${translatePixelsY})\n                        scale(${zoom})\n                        rotate(${rotationDegrees})`,\n        };\n\n        if (this.state.moving) style.cursor = \"grabbing\";\n        else if (this.state.zoom === this.state.minZoom) style.cursor = \"zoom-in\";\n        else style.cursor = \"zoom-out\";\n\n        let info: JSX.Element | undefined;\n        if (showEventMeta) {\n            const mxEvent = this.props.mxEvent!;\n            const showTwelveHour = SettingsStore.getValue(\"showTwelveHourTimestamps\");\n            let permalink = \"#\";\n            if (this.props.permalinkCreator) {\n                permalink = this.props.permalinkCreator.forEvent(mxEvent.getId()!);\n            }\n\n            const senderName = mxEvent.sender?.name ?? mxEvent.getSender();\n            const sender = <div className=\"mx_ImageView_info_sender\">{senderName}</div>;\n            const messageTimestamp = (\n                <MessageTimestamp\n                    href={permalink}\n                    onClick={this.onPermalinkClicked}\n                    showFullDate={true}\n                    showTwelveHour={showTwelveHour}\n                    ts={mxEvent.getTs()}\n                    showSeconds={false}\n                    inhibitTooltip\n                />\n            );\n            const avatar = (\n                <MemberAvatar\n                    member={mxEvent.sender}\n                    fallbackUserId={mxEvent.getSender()}\n                    size=\"32px\"\n                    viewUserOnClick={true}\n                    className=\"mx_Dialog_nonDialogButton\"\n                />\n            );\n\n            info = (\n                <div className=\"mx_ImageView_info_wrapper\">\n                    {avatar}\n                    <div className=\"mx_ImageView_info\">\n                        {sender}\n                        {messageTimestamp}\n                    </div>\n                </div>\n            );\n        } else {\n            // If there is no event - we're viewing an avatar, we set\n            // an empty div here, since the panel uses space-between\n            // and we want the same placement of elements\n            info = <div />;\n        }\n\n        let contextMenuButton: JSX.Element | undefined;\n        if (this.props.mxEvent) {\n            contextMenuButton = (\n                <ContextMenuTooltipButton\n                    className=\"mx_ImageView_button mx_ImageView_button_more\"\n                    title={_t(\"common|options\")}\n                    onClick={this.onOpenContextMenu}\n                    ref={this.contextMenuButton}\n                    isExpanded={this.state.contextMenuDisplayed}\n                >\n                    <OverflowHorizontalIcon />\n                </ContextMenuTooltipButton>\n            );\n        }\n\n        let title: JSX.Element | undefined;\n        if (this.props.mxEvent?.getContent()) {\n            title = (\n                <div className=\"mx_ImageView_title\">\n                    {presentableTextForFile(this.props.mxEvent?.getContent(), _t(\"common|image\"), true)}\n                </div>\n            );\n        }\n\n        return (\n            <FocusLock\n                returnFocus={true}\n                lockProps={{\n                    \"onKeyDown\": this.onKeyDown,\n                    \"role\": \"dialog\",\n                    \"aria-label\": _t(\"lightbox|title\"),\n                }}\n                className=\"mx_ImageView\"\n                ref={this.focusLock}\n            >\n                <div className=\"mx_ImageView_panel\">\n                    {info}\n                    {title}\n                    <div className=\"mx_ImageView_toolbar\">\n                        <AccessibleButton\n                            className=\"mx_ImageView_button\"\n                            title={_t(\"action|zoom_out\")}\n                            onClick={this.onZoomOutClick}\n                        >\n                            <ZoomOutIcon />\n                        </AccessibleButton>\n                        <AccessibleButton\n                            className=\"mx_ImageView_button\"\n                            title={_t(\"action|zoom_in\")}\n                            onClick={this.onZoomInClick}\n                        >\n                            <ZoomInIcon />\n                        </AccessibleButton>\n                        <AccessibleButton\n                            className=\"mx_ImageView_button\"\n                            title={_t(\"lightbox|rotate_left\")}\n                            onClick={this.onRotateCounterClockwiseClick}\n                        >\n                            <RotateLeftIcon />\n                        </AccessibleButton>\n                        <AccessibleButton\n                            className=\"mx_ImageView_button\"\n                            title={_t(\"lightbox|rotate_right\")}\n                            onClick={this.onRotateClockwiseClick}\n                        >\n                            <RotateRightIcon />\n                        </AccessibleButton>\n                        <DownloadButton\n                            url={this.props.src}\n                            fileName={this.props.name}\n                            mxEvent={this.props.mxEvent}\n                            onDownloadReady={this.onDownloadFunctionReady}\n                        />\n                        {contextMenuButton}\n                        <AccessibleButton\n                            className=\"mx_ImageView_button mx_ImageView_button_close\"\n                            title={_t(\"action|close\")}\n                            onClick={this.props.onFinished}\n                        >\n                            <CloseIcon />\n                        </AccessibleButton>\n                        {this.renderContextMenu()}\n                    </div>\n                </div>\n                <div\n                    className=\"mx_ImageView_image_wrapper\"\n                    ref={this.imageWrapper}\n                    onMouseDown={this.props.onFinished}\n                    onMouseMove={this.onMoving}\n                    onMouseUp={this.onEndMoving}\n                    onMouseLeave={this.onEndMoving}\n                >\n                    <img\n                        src={this.props.src}\n                        style={style}\n                        alt={this.props.name}\n                        ref={this.image}\n                        className={`mx_ImageView_image ${transitionClassName}`}\n                        draggable={true}\n                        onMouseDown={this.onStartMoving}\n                    />\n                </div>\n            </FocusLock>\n        );\n    }\n}\n\ninterface DownloadButtonProps {\n    url: string;\n    fileName?: string;\n    mxEvent?: MatrixEvent;\n    onDownloadReady?: (download: () => Promise<void>) => void;\n}\n\nexport const DownloadButton: React.FC<DownloadButtonProps> = ({ url, fileName, mxEvent, onDownloadReady }) => {\n    const { download, loading, canDownload } = useDownloadMedia(url, fileName, mxEvent);\n\n    useEffect(() => {\n        if (onDownloadReady) onDownloadReady(download);\n    }, [download, onDownloadReady]);\n\n    if (!canDownload) return null;\n\n    return (\n        <AccessibleButton\n            className=\"mx_ImageView_button\"\n            title={loading ? _t(\"timeline|download_action_downloading\") : _t(\"action|download\")}\n            onClick={download}\n            disabled={loading}\n        >\n            <DownloadIcon />\n        </AccessibleButton>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode } from \"react\";\nimport classNames from \"classnames\";\nimport { Tooltip } from \"@vector-im/compound-web\";\nimport { ErrorSolidIcon, InfoIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\n\nexport enum InfoTooltipKind {\n    Info = \"info\",\n    Warning = \"warning\",\n}\n\ninterface TooltipProps {\n    tooltip?: string;\n    className?: string;\n    kind?: InfoTooltipKind;\n    children?: ReactNode;\n    tabIndex?: number;\n}\n\nexport default class InfoTooltip extends React.PureComponent<TooltipProps> {\n    public render(): React.ReactNode {\n        const { tooltip, children, className, kind } = this.props;\n        const title = _t(\"info_tooltip_title\");\n\n        // Tooltip are forced on the right for a more natural feel to them on info icons\n        return (\n            <Tooltip description={tooltip || title} placement=\"right\">\n                <div className={classNames(\"mx_InfoTooltip\", className)} tabIndex={this.props.tabIndex ?? 0}>\n                    <span className=\"mx_InfoTooltip_icon\" aria-label={title}>\n                        {kind !== InfoTooltipKind.Warning ? <InfoIcon /> : <ErrorSolidIcon />}\n                    </span>\n                    {children}\n                </div>\n            </Tooltip>\n        );\n    }\n}\n","/*\nCopyright 2017-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { InlineSpinner as BaseInlineSpinner } from \"@vector-im/compound-web\";\n\nimport { _t } from \"../../../languageHandler\";\n\ninterface IProps {\n    size?: number;\n}\n\nexport default class InlineSpinner extends React.PureComponent<IProps> {\n    public static defaultProps = {\n        w: 16,\n        h: 16,\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <span className=\"mx_InlineSpinner\">\n                <BaseInlineSpinner\n                    size={this.props.size}\n                    aria-label={_t(\"common|loading\")}\n                    role=\"progressbar\"\n                    data-testid=\"spinner\"\n                />\n            </span>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactElement } from \"react\";\nimport { JoinRule } from \"matrix-js-sdk/src/matrix\";\nimport {\n    GroupIcon,\n    LockSolidIcon,\n    PublicIcon,\n    AskToJoinIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport Dropdown from \"./Dropdown\";\nimport { type NonEmptyArray } from \"../../../@types/common\";\n\ninterface IProps {\n    value: JoinRule;\n    label: string;\n    width?: number;\n    labelInvite: string;\n    labelKnock?: string;\n    labelPublic?: string;\n    labelRestricted?: string; // if omitted then this option will be hidden, e.g if unsupported\n    onChange(value: JoinRule): void;\n}\n\nconst JoinRuleDropdown: React.FC<IProps> = ({\n    label,\n    labelInvite,\n    labelKnock,\n    labelPublic,\n    labelRestricted,\n    value,\n    width = 448,\n    onChange,\n}) => {\n    const options = [\n        <div key={JoinRule.Invite} className=\"mx_JoinRuleDropdown_invite\">\n            <LockSolidIcon />\n            {labelInvite}\n        </div>,\n    ] as NonEmptyArray<ReactElement & { key: string }>;\n\n    if (labelPublic) {\n        options.push(\n            (\n                <div key={JoinRule.Public} className=\"mx_JoinRuleDropdown_public\">\n                    <PublicIcon />\n                    {labelPublic}\n                </div>\n            ) as ReactElement & { key: string },\n        );\n    }\n\n    if (labelKnock) {\n        options.unshift(\n            (\n                <div key={JoinRule.Knock} className=\"mx_JoinRuleDropdown_knock\">\n                    <AskToJoinIcon />\n                    {labelKnock}\n                </div>\n            ) as ReactElement & { key: string },\n        );\n    }\n\n    if (labelRestricted) {\n        options.unshift(\n            (\n                <div key={JoinRule.Restricted} className=\"mx_JoinRuleDropdown_restricted\">\n                    <GroupIcon />\n                    {labelRestricted}\n                </div>\n            ) as ReactElement & { key: string },\n        );\n    }\n\n    return (\n        <Dropdown\n            id=\"mx_JoinRuleDropdown\"\n            className=\"mx_JoinRuleDropdown\"\n            onOptionChange={onChange}\n            menuWidth={width}\n            value={value}\n            label={label}\n            disabled={options.length === 1}\n        >\n            {options}\n        </Dropdown>\n    );\n};\n\nexport default JoinRuleDropdown;\n","/*\nCopyright 2024,2025 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport classnames from \"classnames\";\n\nimport StyledCheckbox from \"./StyledCheckbox\";\n\ninterface IProps {\n    // The value for the checkbox\n    value: boolean;\n    // The translated label for the checkbox\n    label: string;\n    // Optional translated string to show below the checkbox\n    byline?: string;\n    // Whether or not to disable the checkbox\n    disabled?: boolean;\n    // The function to call when the value changes\n    onChange(checked: boolean): void;\n    // Optional additional CSS class to apply to the label\n    className?: string;\n    // The id for the checkbox\n    id?: string;\n}\n\nconst LabelledCheckbox: React.FC<IProps> = ({ value, label, byline, disabled, onChange, className, id }) => {\n    return (\n        <div id={id} className={classnames(\"mx_LabelledCheckbox\", className)}>\n            <StyledCheckbox\n                description={byline}\n                disabled={disabled}\n                checked={value}\n                onChange={(e) => onChange(e.target.checked)}\n            >\n                <span className=\"mx_LabelledCheckbox_label\">{label}</span>\n            </StyledCheckbox>\n        </div>\n    );\n};\n\nexport default LabelledCheckbox;\n","/*\nCopyright 2019-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\n\nclass ItemRange {\n    public constructor(\n        public topCount: number,\n        public renderCount: number,\n        public bottomCount: number,\n    ) {}\n\n    public contains(range: ItemRange): boolean {\n        // don't contain empty ranges\n        // as it will prevent clearing the list\n        // once it is scrolled far enough out of view\n        if (!range.renderCount && this.renderCount) {\n            return false;\n        }\n        return (\n            range.topCount >= this.topCount && range.topCount + range.renderCount <= this.topCount + this.renderCount\n        );\n    }\n\n    public expand(amount: number): ItemRange {\n        // don't expand ranges that won't render anything\n        if (this.renderCount === 0) {\n            return this;\n        }\n\n        const topGrow = Math.min(amount, this.topCount);\n        const bottomGrow = Math.min(amount, this.bottomCount);\n        return new ItemRange(\n            this.topCount - topGrow,\n            this.renderCount + topGrow + bottomGrow,\n            this.bottomCount - bottomGrow,\n        );\n    }\n\n    public totalSize(): number {\n        return this.topCount + this.renderCount + this.bottomCount;\n    }\n}\n\ninterface IProps<T> {\n    // height in pixels of the component returned by `renderItem`\n    itemHeight: number;\n    // function to turn an element of `items` into a react component\n    renderItem: (item: T) => JSX.Element;\n    // scrollTop of the viewport (minus the height of any content above this list like other `LazyRenderList`s)\n    scrollTop: number;\n    // the height of the viewport this content is scrolled in\n    height: number;\n    // all items for the list. These should not be react components, see `renderItem`.\n    items?: T[];\n    // the amount of items to scroll before causing a rerender,\n    // should typically be less than `overflowItems` unless applying\n    // margins in the parent component when using multiple LazyRenderList in one viewport.\n    // use 0 to only rerender when items will come into view.\n    overflowMargin: number;\n    // the amount of items to add at the top and bottom to render,\n    // so not every scroll of causes a rerender.\n    overflowItems: number;\n\n    element?: string;\n    className?: string;\n    role?: string;\n}\n\ninterface IState {\n    renderRange: ItemRange;\n}\n\nexport default class LazyRenderList<T = any> extends React.Component<IProps<T>, IState> {\n    public static defaultProps: Partial<IProps<unknown>> = {\n        overflowItems: 20,\n        overflowMargin: 5,\n    };\n\n    public constructor(props: IProps<T>) {\n        super(props);\n\n        this.state = LazyRenderList.getDerivedStateFromProps(props, {} as IState) as IState;\n    }\n\n    public static getDerivedStateFromProps<T>(props: IProps<T>, state: IState): Partial<IState> | null {\n        const range = LazyRenderList.getVisibleRangeFromProps(props);\n        const intersectRange = range.expand(props.overflowMargin);\n        const renderRange = range.expand(props.overflowItems);\n        const listHasChangedSize = !!state.renderRange && renderRange.totalSize() !== state.renderRange.totalSize();\n        // only update render Range if the list has shrunk/grown and we need to adjust padding OR\n        // if the new range + overflowMargin isn't contained by the old anymore\n        if (listHasChangedSize || !state.renderRange || !state.renderRange.contains(intersectRange)) {\n            return { renderRange };\n        }\n        return null;\n    }\n\n    private static getVisibleRangeFromProps<T>(props: IProps<T>): ItemRange {\n        const { items, itemHeight, scrollTop, height } = props;\n        const length = items ? items.length : 0;\n        const topCount = Math.min(Math.max(0, Math.floor(scrollTop / itemHeight)), length);\n        const itemsAfterTop = length - topCount;\n        const visibleItems = height !== 0 ? Math.ceil(height / itemHeight) : 0;\n        const renderCount = Math.min(visibleItems, itemsAfterTop);\n        const bottomCount = itemsAfterTop - renderCount;\n        return new ItemRange(topCount, renderCount, bottomCount);\n    }\n\n    public render(): React.ReactNode {\n        const { itemHeight, items, renderItem } = this.props;\n        const { renderRange } = this.state;\n        const { topCount, renderCount, bottomCount } = renderRange;\n\n        const paddingTop = topCount * itemHeight;\n        const paddingBottom = bottomCount * itemHeight;\n        const renderedItems = (items || []).slice(topCount, topCount + renderCount);\n\n        const element = this.props.element || \"div\";\n        const elementProps = {\n            style: { paddingTop: `${paddingTop}px`, paddingBottom: `${paddingBottom}px` },\n            className: this.props.className,\n            role: this.props.role,\n        };\n        return React.createElement(element, elementProps, renderedItems.map(renderItem));\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { useEffect, useState } from \"react\";\n\nimport { PillType } from \"../components/views/elements/Pill\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { type PermalinkParts } from \"../utils/permalinks/PermalinkConstructor\";\n\n/**\n * Tries to determine the initial room.\n * Initial here means it should be possible to load the room without sending API requests.\n * For an @room or a user mention it is the permalinkRoom.\n * If the parse result contains a room Id or alias try to find it with {@link findRoom}.\n * Otherwise returns null.\n *\n * @param type - Pill type\n * @param permalinkRoom - Room in which the permalink is displayed.\n * @param parseResult - Permalink parser result\n * @returns Initial room or null if it cannot be determined.\n */\nconst determineInitialRoom = (\n    type: PillType | null,\n    parseResult: PermalinkParts | null,\n    permalinkRoom: Room | undefined,\n): Room | null => {\n    if (type === PillType.AtRoomMention && permalinkRoom) return permalinkRoom;\n\n    if (type === PillType.UserMention && permalinkRoom) {\n        return permalinkRoom;\n    }\n\n    if (parseResult?.roomIdOrAlias) {\n        const room = findRoom(parseResult.roomIdOrAlias);\n        if (room) return room;\n    }\n\n    return null;\n};\n\n/**\n * Tries to find a room by room Id or searching all rooms for an alias.\n *\n * @param roomIdOrAlias - Id or alias of the room to find.\n * @returns Room if found, else null.\n */\nconst findRoom = (roomIdOrAlias: string): Room | null => {\n    const client = MatrixClientPeg.safeGet();\n\n    return roomIdOrAlias[0] === \"#\"\n        ? (client.getRooms().find((r) => {\n              return r.getCanonicalAlias() === roomIdOrAlias || r.getAltAliases().includes(roomIdOrAlias);\n          }) ?? null)\n        : client.getRoom(roomIdOrAlias);\n};\n\n/**\n * Hook to get the permalink target room:\n *\n * @param type - Permalink type\n * @param parseResult - Permalink parse result\n * @param permalinkRoom - Room in which the permalink is rendered\n * @returns Returns the target room:\n *          - The permalinkRoom for an @room or user mention\n *          - The room of the parse result for a room mention\n *          - The room of the event for an event permalink\n *          - Null in other cases or if the room cannot be found\n */\nexport const usePermalinkTargetRoom = (\n    type: PillType | null,\n    parseResult: PermalinkParts | null,\n    permalinkRoom: Room | undefined,\n): Room | null => {\n    // The listed permalink types require a room.\n    // If it cannot be initially determined, it will be looked up later by a memo hook.\n    const shouldLookUpRoom =\n        type && [PillType.RoomMention, PillType.EventInSameRoom, PillType.EventInOtherRoom, \"space\"].includes(type);\n    const initialRoom = determineInitialRoom(type, parseResult, permalinkRoom);\n    const [targetRoom, setTargetRoom] = useState<Room | null>(initialRoom);\n\n    useEffect(() => {\n        if (shouldLookUpRoom && !targetRoom && parseResult?.roomIdOrAlias) {\n            const newRoom = findRoom(parseResult.roomIdOrAlias);\n            setTargetRoom(newRoom);\n        }\n    }, [parseResult?.roomIdOrAlias, shouldLookUpRoom, targetRoom]);\n\n    return targetRoom;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type IMatrixProfile, type MatrixEvent, type Room, RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { useContext, useEffect, useState } from \"react\";\n\nimport { PillType } from \"../components/views/elements/Pill\";\nimport { SDKContext, type SdkContextClass } from \"../contexts/SDKContext\";\nimport { type PermalinkParts } from \"../utils/permalinks/PermalinkConstructor\";\n\nconst createMemberFromProfile = (userId: string, profile: IMatrixProfile): RoomMember => {\n    const member = new RoomMember(\"\", userId);\n    member.name = profile.displayname ?? userId;\n    member.rawDisplayName = member.name;\n    member.events.member = {\n        getContent: () => {\n            return { avatar_url: profile.avatar_url };\n        },\n        getDirectionalContent: function () {\n            // eslint-disable-next-line\n            return this.getContent();\n        },\n    } as MatrixEvent;\n    return member;\n};\n\n/**\n * Tries to determine the user Id of a permalink.\n * In case of a user permalink it is the user id.\n * In case of an event permalink it is the sender user Id of the event if that event is available.\n * Otherwise returns null.\n *\n * @param type - pill type\n * @param parseResult - permalink parse result\n * @param event - permalink event, if available\n * @returns permalink user Id. null if the Id cannot be determined.\n */\nconst determineUserId = (\n    type: PillType | null,\n    parseResult: PermalinkParts | null,\n    event: MatrixEvent | null,\n): string | null => {\n    if (type === null) return null;\n\n    if (parseResult?.userId) return parseResult.userId;\n\n    if (event && [PillType.EventInSameRoom, PillType.EventInOtherRoom].includes(type)) {\n        return event.getSender() ?? null;\n    }\n\n    return null;\n};\n\n/**\n * Tries to determine a RoomMember.\n *\n * @param userId - User Id to get the member for\n * @param targetRoom - permalink target room\n * @returns RoomMember of the target room if it exists.\n *          If sharing at least one room with the user, then the result will be the profile fetched via API.\n *          null in all other cases.\n */\nconst determineMember = (userId: string, targetRoom: Room, context: SdkContextClass): RoomMember | null => {\n    const targetRoomMember = targetRoom.getMember(userId);\n\n    if (targetRoomMember) return targetRoomMember;\n\n    const knownProfile = context.userProfilesStore.getOnlyKnownProfile(userId);\n\n    if (knownProfile) {\n        return createMemberFromProfile(userId, knownProfile);\n    }\n\n    return null;\n};\n\n/**\n * Hook to get the permalink member\n *\n * @param type - Permalink type\n * @param parseResult - Permalink parse result\n * @param targetRoom - Permalink target room {@link ./usePermalinkTargetRoom.ts}\n * @param event - Permalink event\n * @returns The permalink member:\n *          - The room member for a user mention\n *          - The sender for a permalink to an event in the same room\n *          - Null in other cases or the user cannot be loaded.\n */\nexport const usePermalinkMember = (\n    type: PillType | null,\n    parseResult: PermalinkParts | null,\n    targetRoom: Room | null,\n    event: MatrixEvent | null,\n): RoomMember | null => {\n    const context = useContext(SDKContext);\n    // User mentions and permalinks to events in the same room require to know the user.\n    // If it cannot be initially determined, it will be looked up later by a memo hook.\n    const shouldLookUpUser = type && [PillType.UserMention, PillType.EventInSameRoom].includes(type);\n    const userId = determineUserId(type, parseResult, event);\n    const userInRoom = shouldLookUpUser && userId && targetRoom ? determineMember(userId, targetRoom, context) : null;\n    const [member, setMember] = useState<RoomMember | null>(userInRoom);\n\n    useEffect(() => {\n        if (!shouldLookUpUser || !userId || member) {\n            // nothing to do here\n            return;\n        }\n\n        const doProfileLookup = async (): Promise<void> => {\n            const fetchedProfile = await context.userProfilesStore.fetchOnlyKnownProfile(userId);\n\n            if (fetchedProfile) {\n                const newMember = createMemberFromProfile(userId, fetchedProfile);\n                setMember(newMember);\n            }\n        };\n\n        doProfileLookup();\n    }, [context, member, shouldLookUpUser, targetRoom, userId]);\n\n    return member;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, type Room, type RoomMember } from \"matrix-js-sdk/src/matrix\";\n\nimport { type ButtonEvent } from \"../components/views/elements/AccessibleButton\";\nimport { PillType } from \"../components/views/elements/Pill\";\nimport { parsePermalink } from \"../utils/permalinks/Permalinks\";\nimport dis from \"../dispatcher/dispatcher\";\nimport { Action } from \"../dispatcher/actions\";\nimport { type PermalinkParts } from \"../utils/permalinks/PermalinkConstructor\";\nimport { _t } from \"../languageHandler\";\nimport { usePermalinkTargetRoom } from \"./usePermalinkTargetRoom\";\nimport { usePermalinkEvent } from \"./usePermalinkEvent\";\nimport { usePermalinkMember } from \"./usePermalinkMember\";\n\ninterface Args {\n    /** Room in which the permalink should be displayed. */\n    room?: Room;\n    /** When set forces the permalink type. */\n    type?: PillType;\n    /** Permalink URL. */\n    url?: string;\n}\n\ninterface HookResult {\n    /**\n     * Room member of a user mention permalink.\n     * null for other links, if the profile was not found or not yet loaded.\n     * This can change, for instance, from null to a RoomMember after the profile lookup completed.\n     */\n    member: RoomMember | null;\n    /**\n     * Displayable text of the permalink resource. Can for instance be a user or room name.\n     * null here means that there is nothing to display. Most likely if the URL was not a permalink.\n     */\n    text: string | null;\n    /**\n     * Should be used for click actions on the permalink.\n     * In case of a user permalink, a view profile action is dispatched.\n     */\n    onClick: (e: ButtonEvent) => void;\n    /**\n     * This can be for instance a user or room Id.\n     * null here means that the resource cannot be detected. Most likely if the URL was not a permalink.\n     */\n    resourceId: string | null;\n    /**\n     * Target room of the permalink:\n     * For an @room mention, this is the room where the permalink should be displayed.\n     * For a room permalink, it is the room from the permalink.\n     * null for other links or if the room cannot be found.\n     */\n    targetRoom: Room | null;\n    /**\n     * Type of the pill plus \"space\" for spaces.\n     * null here means that the type cannot be detected. Most likely if the URL was not a permalink.\n     */\n    type: PillType | \"space\" | null;\n    /**\n     * Target event of the permalink.\n     * Null if unable to load the event.\n     */\n    event: MatrixEvent | null;\n}\n\n/**\n * Tries to determine the pill type.\n *\n * If forcedType is present it will be returned.\n * If the parse result contains a room Id or alias and an event Id:\n * - Type is EventInSameRoom if the permalink room Id or alias equals the parsed room Id or alias\n * - Type is EventInOtherRoom if the permalink room Id or alias not equals the parsed room Id or alias\n * If the parse result contains a primary entity Id it will try to detect the type from it.\n * Otherwise returns null.\n *\n * @param forcedType - Forced pill type. Will be used if present and short-circuits all othe conditions.\n * @param parseResult - Permalink parser result\n * @param permalinkRoom - Room in which the permalink is displayed.\n * @returns Pill type or null if unable to determine.\n */\nconst determineType = (\n    forcedType: PillType | undefined,\n    parseResult: PermalinkParts | null,\n    permalinkRoom: Room | undefined,\n): PillType | null => {\n    if (forcedType) return forcedType;\n\n    if (parseResult?.roomIdOrAlias && parseResult?.eventId) {\n        if (parseResult.roomIdOrAlias === permalinkRoom?.roomId) {\n            return PillType.EventInSameRoom;\n        }\n\n        return PillType.EventInOtherRoom;\n    }\n\n    if (parseResult?.primaryEntityId) {\n        const prefix = parseResult.primaryEntityId[0] || \"\";\n        return (\n            {\n                \"@\": PillType.UserMention,\n                \"#\": PillType.RoomMention,\n                \"!\": PillType.RoomMention,\n            }[prefix] || null\n        );\n    }\n\n    return null;\n};\n\n/**\n * Can be used to retrieve all information needed to display a permalink.\n */\nexport const usePermalink: (args: Args) => HookResult = ({\n    room: permalinkRoom,\n    type: forcedType,\n    url,\n}): HookResult => {\n    let resourceId: string | null = null;\n    let parseResult: PermalinkParts | null = null;\n\n    if (url) {\n        parseResult = parsePermalink(url);\n\n        if (parseResult?.primaryEntityId) {\n            resourceId = parseResult.primaryEntityId;\n        }\n    }\n\n    const type = determineType(forcedType, parseResult, permalinkRoom);\n    const targetRoom = usePermalinkTargetRoom(type, parseResult, permalinkRoom);\n    const event = usePermalinkEvent(type, parseResult, targetRoom);\n    const member = usePermalinkMember(type, parseResult, targetRoom, event);\n\n    let onClick: (e: ButtonEvent) => void = () => {};\n    let text = resourceId;\n\n    if (type === PillType.AtRoomMention && permalinkRoom) {\n        text = \"@room\";\n    } else if (type === PillType.UserMention && member) {\n        text = member.name || resourceId;\n        onClick = (e: ButtonEvent): void => {\n            e.preventDefault();\n            e.stopPropagation();\n            dis.dispatch({\n                action: Action.ViewUser,\n                member: member,\n            });\n        };\n    } else if (type === PillType.RoomMention) {\n        if (targetRoom) {\n            text = targetRoom.name || resourceId;\n        }\n    } else if (type === PillType.EventInSameRoom) {\n        text = member?.name || _t(\"common|user\");\n    } else if (type === PillType.EventInOtherRoom) {\n        text = targetRoom?.name || _t(\"common|room\");\n    }\n\n    return {\n        event,\n        member,\n        onClick,\n        resourceId,\n        targetRoom,\n        text,\n        type,\n    };\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { MatrixEvent, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { useEffect, useState } from \"react\";\n\nimport { PillType } from \"../components/views/elements/Pill\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { type PermalinkParts } from \"../utils/permalinks/PermalinkConstructor\";\n\n/**\n * Tries to find the initial event.\n * If the event should not be looked up or there is no target room it returns null.\n * Otherwise it tries to get the event from the target room.\n *\n * @param shouldLookUpEvent - whether the parmalink event should be looked up\n * @param Room | null targetRoom - target room of the permalink\n * @param parseResult - permalink parse result\n * @returns The event if found or null if it should not be looked up or was not found.\n */\nconst determineInitialEvent = (\n    shouldLookUpEvent: boolean,\n    targetRoom: Room | null,\n    parseResult: PermalinkParts | null,\n): MatrixEvent | null => {\n    if (!shouldLookUpEvent || !targetRoom || !parseResult?.eventId) return null;\n\n    return targetRoom.findEventById(parseResult.eventId) || null;\n};\n\n/**\n * Hook to get a permalink target event\n *\n * @param type - Permalink type\n * @param parseResult - Permalink parse result\n * @param targetRoom - Target room of the permalink {@link ./usePermalinkTargetRoom.ts}\n * @returns The permalink event if it targets an event and it can be loaded.\n *          Else null.\n */\nexport const usePermalinkEvent = (\n    type: PillType | null,\n    parseResult: PermalinkParts | null,\n    targetRoom: Room | null,\n): MatrixEvent | null => {\n    // Event permalinks require to know the event.\n    // If it cannot be initially determined, it will be looked up later by a memo hook.\n    const shouldLookUpEvent =\n        !!type &&\n        !!parseResult?.roomIdOrAlias &&\n        !!parseResult?.eventId &&\n        [PillType.EventInSameRoom, PillType.EventInOtherRoom].includes(type);\n    const eventId = parseResult?.eventId;\n    const eventInRoom = determineInitialEvent(shouldLookUpEvent, targetRoom, parseResult);\n    const [event, setEvent] = useState<MatrixEvent | null>(eventInRoom);\n\n    useEffect(() => {\n        if (!shouldLookUpEvent || !eventId || event || !parseResult?.roomIdOrAlias || !parseResult.eventId) {\n            // nothing to do here\n            return;\n        }\n\n        const fetchRoomEvent = async (): Promise<void> => {\n            try {\n                const eventData = await MatrixClientPeg.safeGet().fetchRoomEvent(\n                    parseResult.roomIdOrAlias!,\n                    parseResult.eventId!,\n                );\n                setEvent(new MatrixEvent(eventData));\n            } catch {}\n        };\n\n        fetchRoomEvent();\n    }, [event, eventId, parseResult?.eventId, parseResult?.roomIdOrAlias, shouldLookUpEvent]);\n\n    return event;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017-2019 , 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactElement, useContext } from \"react\";\nimport classNames from \"classnames\";\nimport { type Room, type RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { Tooltip } from \"@vector-im/compound-web\";\nimport { LinkIcon, UserSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { usePermalink } from \"../../../hooks/usePermalink\";\nimport RoomAvatar from \"../avatars/RoomAvatar\";\nimport MemberAvatar from \"../avatars/MemberAvatar\";\nimport { _t } from \"../../../languageHandler\";\n\nexport enum PillType {\n    UserMention = \"TYPE_USER_MENTION\",\n    RoomMention = \"TYPE_ROOM_MENTION\",\n    AtRoomMention = \"TYPE_AT_ROOM_MENTION\", // '@room' mention\n    EventInSameRoom = \"TYPE_EVENT_IN_SAME_ROOM\",\n    EventInOtherRoom = \"TYPE_EVENT_IN_OTHER_ROOM\",\n    Keyword = \"TYPE_KEYWORD\", // Used to highlight keywords that triggered a notification rule\n}\n\nconst linkIcon = <LinkIcon className=\"mx_Pill_LinkIcon mx_BaseAvatar\" />;\n\nconst PillRoomAvatar: React.FC<{\n    shouldShowPillAvatar: boolean;\n    room: Room | null;\n}> = ({ shouldShowPillAvatar, room }) => {\n    if (!shouldShowPillAvatar) {\n        return null;\n    }\n\n    if (room) {\n        return <RoomAvatar room={room} size=\"16px\" aria-hidden=\"true\" />;\n    }\n    return linkIcon;\n};\n\nconst PillMemberAvatar: React.FC<{\n    shouldShowPillAvatar: boolean;\n    member: RoomMember | null;\n}> = ({ shouldShowPillAvatar, member }) => {\n    if (!shouldShowPillAvatar) {\n        return null;\n    }\n\n    if (member) {\n        return <MemberAvatar member={member} size=\"16px\" aria-hidden=\"true\" hideTitle />;\n    }\n    return <UserSolidIcon className=\"mx_Pill_UserIcon mx_BaseAvatar\" />;\n};\n\nexport interface PillProps {\n    // The Type of this Pill. If url is given, this is auto-detected.\n    type?: PillType;\n    // The URL to pillify (no validation is done)\n    url?: string;\n    /** Whether the pill is in a message. It will act as a link then. */\n    inMessage?: boolean;\n    // The room in which this pill is being rendered\n    room?: Room;\n    // Whether to include an avatar in the pill\n    shouldShowPillAvatar?: boolean;\n    // Explicitly-provided text to display in the pill\n    text?: string;\n}\n\nexport const Pill: React.FC<PillProps> = ({\n    type: propType,\n    url,\n    inMessage,\n    room,\n    shouldShowPillAvatar = true,\n    text: customPillText,\n}) => {\n    const cli = useContext(MatrixClientContext);\n    const {\n        event,\n        member,\n        onClick,\n        resourceId,\n        targetRoom,\n        text: linkText,\n        type,\n    } = usePermalink({\n        room,\n        type: propType,\n        url,\n    });\n    const text = customPillText ?? linkText;\n\n    if (!type || !text) {\n        return null;\n    }\n\n    const classes = classNames(\"mx_Pill\", {\n        mx_AtRoomPill: type === PillType.AtRoomMention,\n        mx_RoomPill: type === PillType.RoomMention,\n        mx_SpacePill: type === \"space\" || targetRoom?.isSpaceRoom(),\n        mx_UserPill: type === PillType.UserMention,\n        mx_UserPill_me: resourceId === cli.getUserId(),\n        mx_EventPill: type === PillType.EventInOtherRoom || type === PillType.EventInSameRoom,\n        mx_KeywordPill: type === PillType.Keyword,\n    });\n\n    let avatar: ReactElement | null = null;\n    let pillText: string | null = text;\n\n    switch (type) {\n        case PillType.EventInOtherRoom:\n            {\n                avatar = <PillRoomAvatar shouldShowPillAvatar={shouldShowPillAvatar} room={targetRoom} />;\n                pillText = _t(\"pill|permalink_other_room\", {\n                    room: text,\n                });\n            }\n            break;\n        case PillType.EventInSameRoom:\n            {\n                if (event) {\n                    avatar = <PillMemberAvatar shouldShowPillAvatar={shouldShowPillAvatar} member={member} />;\n                    pillText = _t(\"pill|permalink_this_room\", {\n                        user: text,\n                    });\n                } else {\n                    avatar = linkIcon;\n                    pillText = _t(\"common|message\");\n                }\n            }\n            break;\n        case PillType.AtRoomMention:\n        case PillType.RoomMention:\n        case \"space\":\n            avatar = <PillRoomAvatar shouldShowPillAvatar={shouldShowPillAvatar} room={targetRoom} />;\n            break;\n        case PillType.UserMention:\n            avatar = <PillMemberAvatar shouldShowPillAvatar={shouldShowPillAvatar} member={member} />;\n            break;\n        case PillType.Keyword:\n            break;\n        default:\n            return null;\n    }\n\n    const isAnchor = !!inMessage && !!url;\n    return (\n        <bdi>\n            <Tooltip\n                description={resourceId ?? \"\"}\n                open={resourceId ? undefined : false}\n                placement=\"right\"\n                isTriggerInteractive={isAnchor}\n            >\n                {isAnchor ? (\n                    <a className={classes} href={url} onClick={onClick}>\n                        {avatar}\n                        <span className=\"mx_Pill_text\">{pillText}</span>\n                    </a>\n                ) : (\n                    <span className={classes}>\n                        {avatar}\n                        <span className=\"mx_Pill_text\">{pillText}</span>\n                    </span>\n                )}\n            </Tooltip>\n        </bdi>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021, 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEvent, createRef } from \"react\";\nimport {\n    type Room,\n    type MatrixEvent,\n    type KnownPollKind,\n    M_POLL_KIND_DISCLOSED,\n    M_POLL_KIND_UNDISCLOSED,\n    M_POLL_START,\n    type IPartialEvent,\n    type TimelineEvents,\n} from \"matrix-js-sdk/src/matrix\";\nimport { PollStartEvent } from \"matrix-js-sdk/src/extensible_events_v1/PollStartEvent\";\nimport { CloseIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport ScrollableBaseModal, { type IScrollableBaseState } from \"../dialogs/ScrollableBaseModal\";\nimport QuestionDialog from \"../dialogs/QuestionDialog\";\nimport Modal from \"../../../Modal\";\nimport { _t } from \"../../../languageHandler\";\nimport { arrayFastClone, arraySeed } from \"../../../utils/arrays\";\nimport Field from \"./Field\";\nimport AccessibleButton from \"./AccessibleButton\";\nimport Spinner from \"./Spinner\";\nimport { doMaybeLocalRoomAction } from \"../../../utils/local-room\";\n\ninterface IProps {\n    room: Room;\n    threadId?: string;\n    editingMxEvent?: MatrixEvent; // Truthy if we are editing an existing poll\n    onFinished(pollCreated?: boolean): void;\n}\n\nenum FocusTarget {\n    Topic,\n    NewOption,\n}\ninterface IState extends IScrollableBaseState {\n    question: string;\n    options: string[];\n    busy: boolean;\n    kind: KnownPollKind;\n    autoFocusTarget: FocusTarget;\n}\n\nconst MIN_OPTIONS = 2;\nconst MAX_OPTIONS = 20;\nconst DEFAULT_NUM_OPTIONS = 2;\nconst MAX_QUESTION_LENGTH = 340;\nconst MAX_OPTION_LENGTH = 340;\n\nfunction creatingInitialState(): IState {\n    return {\n        title: _t(\"poll|create_poll_title\"),\n        actionLabel: _t(\"poll|create_poll_action\"),\n        canSubmit: false, // need to add a question and at least one option first\n        question: \"\",\n        options: arraySeed(\"\", DEFAULT_NUM_OPTIONS),\n        busy: false,\n        kind: M_POLL_KIND_DISCLOSED,\n        autoFocusTarget: FocusTarget.Topic,\n    };\n}\n\nfunction editingInitialState(editingMxEvent: MatrixEvent): IState {\n    const poll = editingMxEvent.unstableExtensibleEvent as PollStartEvent;\n    if (!poll?.isEquivalentTo(M_POLL_START)) return creatingInitialState();\n\n    return {\n        title: _t(\"poll|edit_poll_title\"),\n        actionLabel: _t(\"action|done\"),\n        canSubmit: true,\n        question: poll.question.text,\n        options: poll.answers.map((ans) => ans.text),\n        busy: false,\n        kind: poll.kind,\n        autoFocusTarget: FocusTarget.Topic,\n    };\n}\n\nexport default class PollCreateDialog extends ScrollableBaseModal<IProps, IState> {\n    private addOptionRef = createRef<HTMLDivElement>();\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = props.editingMxEvent ? editingInitialState(props.editingMxEvent) : creatingInitialState();\n    }\n\n    private checkCanSubmit(): void {\n        this.setState({\n            canSubmit:\n                !this.state.busy &&\n                this.state.question.trim().length > 0 &&\n                this.state.options.filter((op) => op.trim().length > 0).length >= MIN_OPTIONS,\n        });\n    }\n\n    private onQuestionChange = (e: ChangeEvent<HTMLInputElement>): void => {\n        this.setState({ question: e.target.value }, () => this.checkCanSubmit());\n    };\n\n    private onOptionChange = (i: number, e: ChangeEvent<HTMLInputElement>): void => {\n        const newOptions = arrayFastClone(this.state.options);\n        newOptions[i] = e.target.value;\n        this.setState({ options: newOptions }, () => this.checkCanSubmit());\n    };\n\n    private onOptionRemove = (i: number): void => {\n        const newOptions = arrayFastClone(this.state.options);\n        newOptions.splice(i, 1);\n        this.setState({ options: newOptions }, () => this.checkCanSubmit());\n    };\n\n    private onOptionAdd = (): void => {\n        const newOptions = arrayFastClone(this.state.options);\n        newOptions.push(\"\");\n        this.setState({ options: newOptions, autoFocusTarget: FocusTarget.NewOption }, () => {\n            // Scroll the button into view after the state update to ensure we don't experience\n            // a pop-in effect, and to avoid the button getting cut off due to a mid-scroll render.\n            this.addOptionRef.current?.scrollIntoView?.();\n        });\n    };\n\n    private createEvent(): IPartialEvent<object> {\n        const pollStart = PollStartEvent.from(\n            this.state.question.trim(),\n            this.state.options.map((a) => a.trim()).filter((a) => !!a),\n            this.state.kind.name,\n        ).serialize();\n\n        if (!this.props.editingMxEvent) {\n            return pollStart;\n        } else {\n            return {\n                content: {\n                    \"m.new_content\": pollStart.content,\n                    \"m.relates_to\": {\n                        rel_type: \"m.replace\",\n                        event_id: this.props.editingMxEvent.getId(),\n                    },\n                },\n                type: pollStart.type,\n            };\n        }\n    }\n\n    protected submit(): void {\n        this.setState({ busy: true, canSubmit: false });\n        const pollEvent = this.createEvent();\n        doMaybeLocalRoomAction(\n            this.props.room.roomId,\n            (actualRoomId: string) =>\n                this.matrixClient.sendEvent(\n                    actualRoomId,\n                    this.props.threadId ?? null,\n                    pollEvent.type as keyof TimelineEvents,\n                    pollEvent.content as TimelineEvents[keyof TimelineEvents],\n                ),\n            this.matrixClient,\n        )\n            .then(() => this.props.onFinished(true))\n            .catch((e) => {\n                console.error(\"Failed to post poll:\", e);\n                const { finished } = Modal.createDialog(QuestionDialog, {\n                    title: _t(\"poll|failed_send_poll_title\"),\n                    description: _t(\"poll|failed_send_poll_description\"),\n                    button: _t(\"action|try_again\"),\n                    cancelButton: _t(\"action|cancel\"),\n                });\n                finished.then(([tryAgain]) => {\n                    if (!tryAgain) {\n                        this.cancel();\n                    } else {\n                        this.setState({ busy: false, canSubmit: true });\n                    }\n                });\n            });\n    }\n\n    protected cancel(): void {\n        this.props.onFinished(false);\n    }\n\n    protected renderContent(): React.ReactNode {\n        return (\n            <div className=\"mx_PollCreateDialog\">\n                <h2>{_t(\"poll|type_heading\")}</h2>\n                <Field element=\"select\" value={this.state.kind.name} onChange={this.onPollTypeChange}>\n                    <option key={M_POLL_KIND_DISCLOSED.name} value={M_POLL_KIND_DISCLOSED.name}>\n                        {_t(\"poll|type_open\")}\n                    </option>\n                    <option key={M_POLL_KIND_UNDISCLOSED.name} value={M_POLL_KIND_UNDISCLOSED.name}>\n                        {_t(\"poll|type_closed\")}\n                    </option>\n                </Field>\n                <p>{pollTypeNotes(this.state.kind)}</p>\n                <h2>{_t(\"poll|topic_heading\")}</h2>\n                <Field\n                    id=\"poll-topic-input\"\n                    value={this.state.question}\n                    maxLength={MAX_QUESTION_LENGTH}\n                    label={_t(\"poll|topic_label\")}\n                    placeholder={_t(\"poll|topic_placeholder\")}\n                    onChange={this.onQuestionChange}\n                    usePlaceholderAsHint={true}\n                    disabled={this.state.busy}\n                    autoFocus={this.state.autoFocusTarget === FocusTarget.Topic}\n                />\n                <h2>{_t(\"poll|options_heading\")}</h2>\n                {this.state.options.map((op, i) => (\n                    <div key={`option_${i}`} className=\"mx_PollCreateDialog_option\">\n                        <Field\n                            id={`pollcreate_option_${i}`}\n                            value={op}\n                            maxLength={MAX_OPTION_LENGTH}\n                            label={_t(\"poll|options_label\", { number: i + 1 })}\n                            placeholder={_t(\"poll|options_placeholder\")}\n                            onChange={(e: ChangeEvent<HTMLInputElement>) => this.onOptionChange(i, e)}\n                            usePlaceholderAsHint={true}\n                            disabled={this.state.busy}\n                            autoFocus={\n                                this.state.autoFocusTarget === FocusTarget.NewOption &&\n                                i === this.state.options.length - 1\n                            }\n                        />\n                        <AccessibleButton\n                            onClick={() => this.onOptionRemove(i)}\n                            className=\"mx_PollCreateDialog_removeOption\"\n                            disabled={this.state.busy}\n                        >\n                            <CloseIcon />\n                        </AccessibleButton>\n                    </div>\n                ))}\n                <AccessibleButton\n                    onClick={this.onOptionAdd}\n                    disabled={this.state.busy || this.state.options.length >= MAX_OPTIONS}\n                    kind=\"secondary\"\n                    className=\"mx_PollCreateDialog_addOption\"\n                    ref={this.addOptionRef}\n                >\n                    {_t(\"poll|options_add_button\")}\n                </AccessibleButton>\n                {this.state.busy && (\n                    <div className=\"mx_PollCreateDialog_busy\">\n                        <Spinner />\n                    </div>\n                )}\n            </div>\n        );\n    }\n\n    public onPollTypeChange = (e: ChangeEvent<HTMLSelectElement>): void => {\n        this.setState({\n            kind: M_POLL_KIND_DISCLOSED.matches(e.target.value) ? M_POLL_KIND_DISCLOSED : M_POLL_KIND_UNDISCLOSED,\n        });\n    };\n}\n\nfunction pollTypeNotes(kind: KnownPollKind): string {\n    if (M_POLL_KIND_DISCLOSED.matches(kind.name)) {\n        return _t(\"poll|disclosed_notes\");\n    } else {\n        return _t(\"poll|notes\");\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport * as Roles from \"../../../Roles\";\nimport { _t } from \"../../../languageHandler\";\nimport Field from \"./Field\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { objectHasDiff } from \"../../../utils/objects\";\nimport { arrayHasDiff } from \"../../../utils/arrays.ts\";\n\nconst CUSTOM_VALUE = \"SELECT_VALUE_CUSTOM\";\n\ninterface Props<K extends undefined | string> {\n    value: number;\n    // The maximum value that can be set with the power selector\n    maxValue: number;\n\n    // Default user power level for the room\n    usersDefault: number;\n\n    // should the user be able to change the value? false by default.\n    disabled?: boolean;\n\n    // The name to annotate the selector with\n    label?: string;\n\n    onChange(value: number, powerLevelKey: K extends undefined ? void : K): void | Promise<void>;\n\n    // Optional key to pass as the second argument to `onChange`\n    powerLevelKey: K extends undefined ? void : K;\n}\n\ninterface IState {\n    // List of power levels to show in the drop-down\n    options: number[];\n\n    customValue: number;\n    selectValue: number | string;\n    custom?: boolean;\n}\n\nexport default class PowerSelector<K extends undefined | string> extends React.PureComponent<Props<K>, IState> {\n    public static defaultProps: Partial<Props<any>> = {\n        maxValue: Infinity,\n        usersDefault: 0,\n    };\n    private unmounted = false;\n\n    public constructor(props: Props<K>) {\n        super(props);\n\n        this.state = {\n            // List of power levels to show in the drop-down\n            options: [],\n\n            customValue: this.props.value,\n            selectValue: 0,\n        };\n    }\n\n    public componentDidMount(): void {\n        this.unmounted = false;\n        this.initStateFromProps();\n    }\n\n    public componentDidUpdate(prevProps: Readonly<Props<K>>): void {\n        if (objectHasDiff(this.props, prevProps)) {\n            this.initStateFromProps();\n        }\n    }\n\n    public componentWillUnmount(): void {\n        this.unmounted = true;\n    }\n\n    private initStateFromProps(): void {\n        // This needs to be done now because levelRoleMap has translated strings\n        const levelRoleMap = Roles.levelRoleMap(this.props.usersDefault);\n\n        const options = Object.keys(levelRoleMap)\n            .filter((level) => {\n                return (\n                    level === undefined || parseInt(level) <= this.props.maxValue || parseInt(level) == this.props.value\n                );\n            })\n            .map((level) => parseInt(level));\n\n        if (arrayHasDiff(options, this.state.options)) {\n            this.setState({ options });\n        }\n\n        const isCustom = levelRoleMap[this.props.value] === undefined;\n\n        this.setState({\n            custom: isCustom,\n            customValue: this.props.value,\n            selectValue: isCustom ? CUSTOM_VALUE : this.props.value,\n        });\n    }\n\n    private onSelectChange = async (event: React.ChangeEvent<HTMLSelectElement>): Promise<void> => {\n        const isCustom = event.target.value === CUSTOM_VALUE;\n        if (isCustom) {\n            this.setState({ custom: true });\n        } else {\n            const powerLevel = parseInt(event.target.value);\n            this.setState({ selectValue: powerLevel });\n            try {\n                await this.props.onChange(powerLevel, this.props.powerLevelKey);\n            } catch {\n                if (this.unmounted) return;\n                // If the request failed, roll back the state of the selector.\n                this.initStateFromProps();\n            }\n        }\n    };\n\n    private onCustomChange = (event: React.ChangeEvent<HTMLInputElement>): void => {\n        this.setState({ customValue: parseInt(event.target.value) });\n    };\n\n    private onCustomBlur = async (event: React.FocusEvent): Promise<void> => {\n        event.preventDefault();\n        event.stopPropagation();\n\n        if (Number.isFinite(this.state.customValue)) {\n            try {\n                await this.props.onChange(this.state.customValue, this.props.powerLevelKey);\n            } catch {\n                if (this.unmounted) return;\n                // If the request failed, roll back the state of the selector.\n                this.initStateFromProps();\n            }\n        } else {\n            this.initStateFromProps(); // reset, invalid input\n        }\n    };\n\n    private onCustomKeyDown = (event: React.KeyboardEvent<HTMLInputElement>): void => {\n        const action = getKeyBindingsManager().getAccessibilityAction(event);\n        switch (action) {\n            case KeyBindingAction.Enter:\n                event.preventDefault();\n                event.stopPropagation();\n\n                // Do not call the onChange handler directly here - it can cause an infinite loop.\n                // Long story short, a user hits Enter to submit the value which onChange handles as\n                // raising a dialog which causes a blur which causes a dialog which causes a blur and\n                // so on. By not causing the onChange to be called here, we avoid the loop because we\n                // handle the onBlur safely.\n                (event.target as HTMLInputElement).blur();\n                break;\n        }\n    };\n\n    public render(): React.ReactNode {\n        let picker;\n        const label = typeof this.props.label === \"undefined\" ? _t(\"power_level|label\") : this.props.label;\n        if (this.state.custom) {\n            picker = (\n                <Field\n                    type=\"number\"\n                    label={label}\n                    max={this.props.maxValue}\n                    onBlur={this.onCustomBlur}\n                    onKeyDown={this.onCustomKeyDown}\n                    onChange={this.onCustomChange}\n                    value={String(this.state.customValue)}\n                    disabled={this.props.disabled}\n                />\n            );\n        } else {\n            // Each level must have a definition in this.state.levelRoleMap\n            const options = this.state.options.map((level) => {\n                return {\n                    value: String(level),\n                    text: Roles.textualPowerLevel(level, this.props.usersDefault),\n                };\n            });\n            options.push({ value: CUSTOM_VALUE, text: _t(\"power_level|custom_level\") });\n            const optionsElements = options.map((op) => {\n                return (\n                    <option value={op.value} key={op.value} data-testid={`power-level-option-${op.value}`}>\n                        {op.text}\n                    </option>\n                );\n            });\n\n            picker = (\n                <Field\n                    element=\"select\"\n                    label={label}\n                    onChange={this.onSelectChange}\n                    value={String(this.state.selectValue)}\n                    disabled={this.props.disabled}\n                    data-testid=\"power-level-select-element\"\n                >\n                    {optionsElements}\n                </Field>\n            );\n        }\n\n        return <div className=\"mx_PowerSelector\">{picker}</div>;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { useCallback, useEffect, useRef } from \"react\";\n\nimport SettingsStore from \"../settings/SettingsStore\";\n\nconst debuglog = (...args: any[]): void => {\n    if (SettingsStore.getValue(\"debug_animation\")) {\n        logger.log.call(console, \"Animation debuglog:\", ...args);\n    }\n};\n\nexport function useAnimation(enabled: boolean, callback: (timestamp: DOMHighResTimeStamp) => boolean): void {\n    const handle = useRef<number | null>(null);\n\n    const handler = useCallback(\n        (timestamp: DOMHighResTimeStamp) => {\n            if (callback(timestamp)) {\n                handle.current = requestAnimationFrame(handler);\n            } else {\n                debuglog(\"Finished animation!\");\n            }\n        },\n        [callback],\n    );\n\n    useEffect(() => {\n        debuglog(\"Started animation!\");\n        if (enabled) {\n            handle.current = requestAnimationFrame(handler);\n        }\n        return () => {\n            if (handle.current) {\n                debuglog(\"Aborted animation!\");\n                cancelAnimationFrame(handle.current);\n                handle.current = null;\n            }\n        };\n    }, [enabled, handler]);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { useCallback, useEffect, useRef, useState } from \"react\";\n\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { useAnimation } from \"./useAnimation\";\n\nconst debuglog = (...args: any[]): void => {\n    if (SettingsStore.getValue(\"debug_animation\")) {\n        logger.log.call(console, \"Animation debuglog:\", ...args);\n    }\n};\n\n/**\n * Utility function to smoothly animate to a certain target value\n * @param initialValue Initial value to be used as initial starting point\n * @param targetValue Desired value to animate to (can be changed repeatedly to whatever is current at that time)\n * @param duration Duration that each animation should take, specify 0 to skip animating\n */\nexport function useSmoothAnimation(initialValue: number, targetValue: number, duration: number): number {\n    const state = useRef<{ timestamp: DOMHighResTimeStamp | null; value: number }>({\n        timestamp: null,\n        value: initialValue,\n    });\n    const [currentValue, setCurrentValue] = useState<number>(initialValue);\n    const [currentStepSize, setCurrentStepSize] = useState<number>(0);\n\n    useEffect(() => {\n        const totalDelta = targetValue - state.current.value;\n        setCurrentStepSize(totalDelta / duration);\n        state.current = { ...state.current, timestamp: null };\n    }, [duration, targetValue]);\n\n    const update = useCallback(\n        (timestamp: DOMHighResTimeStamp): boolean => {\n            if (!state.current.timestamp) {\n                state.current = { ...state.current, timestamp };\n                return true;\n            }\n\n            if (Math.abs(currentStepSize) < Number.EPSILON) {\n                return false;\n            }\n\n            const timeDelta = timestamp - state.current.timestamp;\n            const valueDelta = currentStepSize * timeDelta;\n            const maxValueDelta = targetValue - state.current.value;\n            const clampedValueDelta = Math.sign(valueDelta) * Math.min(Math.abs(maxValueDelta), Math.abs(valueDelta));\n            const value = state.current.value + clampedValueDelta;\n\n            debuglog(`Animating to ${targetValue} at ${value} timeDelta=${timeDelta}, valueDelta=${valueDelta}`);\n\n            setCurrentValue(value);\n            state.current = { value, timestamp };\n\n            return Math.abs(maxValueDelta) > Number.EPSILON;\n        },\n        [currentStepSize, targetValue],\n    );\n\n    useAnimation(duration > 0, update);\n\n    return duration > 0 ? currentValue : targetValue;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { useSmoothAnimation } from \"../../../hooks/useSmoothAnimation\";\n\ninterface IProps {\n    value: number;\n    max: number;\n    animated?: boolean;\n}\n\nconst PROGRESS_BAR_ANIMATION_DURATION = 300;\nconst ProgressBar: React.FC<IProps> = ({ value, max, animated = true }) => {\n    // Animating progress bars via CSS transition isn’t possible in all of our supported browsers yet.\n    // As workaround, we’re using animations through JS requestAnimationFrame\n    const currentValue = useSmoothAnimation(0, value, animated ? PROGRESS_BAR_ANIMATION_DURATION : 0);\n    return <progress className=\"mx_ProgressBar\" max={max} value={currentValue} />;\n};\n\nexport default ProgressBar;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { toDataURL, type QRCodeSegment, type QRCodeToDataURLOptions, type QRCodeRenderersOptions } from \"qrcode\";\nimport classNames from \"classnames\";\n\nimport { _t } from \"../../../languageHandler\";\nimport Spinner from \"./Spinner\";\n\ninterface IProps extends QRCodeRenderersOptions {\n    /** The data for the QR code. If `null`, a spinner is shown. */\n    data: null | string | QRCodeSegment[];\n    className?: string;\n}\n\nconst defaultOptions: QRCodeToDataURLOptions = {\n    errorCorrectionLevel: \"L\", // we want it as trivial-looking as possible\n};\n\nconst QRCode: React.FC<IProps> = ({ data, className, ...options }) => {\n    const [dataUri, setUri] = React.useState<string | null>(null);\n    React.useEffect(() => {\n        if (data === null) {\n            setUri(null);\n            return;\n        }\n        let cancelled = false;\n        toDataURL(data, { ...defaultOptions, ...options }).then((uri) => {\n            if (cancelled) return;\n            setUri(uri);\n        });\n        return () => {\n            cancelled = true;\n        };\n    }, [JSON.stringify(data), options]); // eslint-disable-line react-hooks/exhaustive-deps\n\n    return (\n        <div className={classNames(\"mx_QRCode\", className)}>\n            {dataUri ? <img src={dataUri} className=\"mx_VerificationQRCode\" alt={_t(\"common|qr_code\")} /> : <Spinner />}\n        </div>\n    );\n};\n\nexport default QRCode;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, createRef, type KeyboardEventHandler } from \"react\";\nimport { MatrixError } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../languageHandler\";\nimport withValidation, { type IFieldState, type IValidationResult } from \"./Validation\";\nimport Field, { type IValidateOpts } from \"./Field\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\n\ninterface IProps {\n    domain?: string;\n    value: string;\n    label?: string;\n    placeholder?: string;\n    disabled?: boolean;\n    // if roomId is passed then the entered alias is checked to point to this roomId, else must be unassigned\n    roomId?: string;\n    onKeyDown?: KeyboardEventHandler;\n    onChange?(value: string): void;\n}\n\ninterface IState {\n    isValid: boolean;\n}\n\n// Controlled form component wrapping Field for inputting a room alias scoped to a given domain\nexport default class RoomAliasField extends React.PureComponent<IProps, IState> {\n    public static contextType = MatrixClientContext;\n    declare public context: React.ContextType<typeof MatrixClientContext>;\n\n    private fieldRef = createRef<Field>();\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            isValid: true,\n        };\n    }\n\n    private asFullAlias(localpart: string): string {\n        const hashAlias = `#${localpart}`;\n        if (this.props.domain) {\n            return `${hashAlias}:${this.props.domain}`;\n        }\n        return hashAlias;\n    }\n\n    private get domainProps(): {\n        prefix: JSX.Element;\n        postfix: JSX.Element;\n        value: string;\n        maxlength: number;\n    } {\n        const { domain } = this.props;\n        const prefix = <span>#</span>;\n        const postfix = domain ? <span title={`:${domain}`}>{`:${domain}`}</span> : <span />;\n        const maxlength = domain ? 255 - domain.length - 2 : 255 - 1; // 2 for # and :\n        const value = domain\n            ? this.props.value.substring(1, this.props.value.length - domain.length - 1)\n            : this.props.value.substring(1);\n\n        return { prefix, postfix, value, maxlength };\n    }\n\n    public render(): React.ReactNode {\n        const { prefix, postfix, value, maxlength } = this.domainProps;\n        return (\n            <Field\n                label={this.props.label || _t(\"room_settings|general|alias_heading\")}\n                className=\"mx_RoomAliasField\"\n                prefixComponent={prefix}\n                postfixComponent={postfix}\n                ref={this.fieldRef}\n                onValidate={this.onValidate}\n                placeholder={this.props.placeholder || _t(\"room_settings|general|alias_field_placeholder_default\")}\n                onChange={this.onChange}\n                value={value}\n                maxLength={maxlength}\n                disabled={this.props.disabled}\n                autoComplete=\"off\"\n                onKeyDown={this.props.onKeyDown}\n            />\n        );\n    }\n\n    private onChange = (ev: React.ChangeEvent<HTMLInputElement>): void => {\n        this.props.onChange?.(this.asFullAlias(ev.target.value));\n    };\n\n    private onValidate = async (fieldState: IFieldState): Promise<IValidationResult> => {\n        const result = await this.validationRules(fieldState);\n        this.setState({ isValid: !!result.valid });\n        return result;\n    };\n\n    private validationRules = withValidation({\n        rules: [\n            {\n                key: \"hasDomain\",\n                test: async ({ value }): Promise<boolean> => {\n                    // Ignore if we have passed domain\n                    if (!value || this.props.domain) {\n                        return true;\n                    }\n\n                    if (value.split(\":\").length < 2) {\n                        return false;\n                    }\n                    return true;\n                },\n                invalid: () => _t(\"room_settings|general|alias_field_has_domain_invalid\"),\n            },\n            {\n                key: \"hasLocalpart\",\n                test: async ({ value }): Promise<boolean> => {\n                    if (!value || this.props.domain) {\n                        return true;\n                    }\n\n                    const split = value.split(\":\");\n                    if (split.length < 2) {\n                        return true; // hasDomain check will fail here instead\n                    }\n\n                    // Define the value invalid if there's no first part (roomname)\n                    if (split[0].length < 1) {\n                        return false;\n                    }\n                    return true;\n                },\n                invalid: () => _t(\"room_settings|general|alias_field_has_localpart_invalid\"),\n            },\n            {\n                key: \"safeLocalpart\",\n                test: async ({ value }): Promise<boolean> => {\n                    if (!value) {\n                        return true;\n                    }\n                    if (!this.props.domain) {\n                        return true;\n                    } else {\n                        const fullAlias = this.asFullAlias(value);\n                        const hasColon = this.props.domain ? !value.includes(\":\") : true;\n                        // XXX: FIXME https://github.com/matrix-org/matrix-doc/issues/668\n                        // NOTE: We could probably use linkifyjs to parse those aliases here?\n                        return (\n                            !value.includes(\"#\") &&\n                            hasColon &&\n                            !value.includes(\",\") &&\n                            encodeURI(fullAlias) === fullAlias\n                        );\n                    }\n                },\n                invalid: () => _t(\"room_settings|general|alias_field_safe_localpart_invalid\"),\n            },\n            {\n                key: \"required\",\n                test: async ({ value, allowEmpty }) => allowEmpty || !!value,\n                invalid: () => _t(\"room_settings|general|alias_field_required_invalid\"),\n            },\n            this.props.roomId\n                ? {\n                      key: \"matches\",\n                      final: true,\n                      test: async ({ value }): Promise<boolean> => {\n                          if (!value) {\n                              return true;\n                          }\n                          const client = this.context;\n                          try {\n                              const result = await client.getRoomIdForAlias(this.asFullAlias(value));\n                              return result.room_id === this.props.roomId;\n                          } catch (err) {\n                              console.log(err);\n                              return false;\n                          }\n                      },\n                      invalid: () => _t(\"room_settings|general|alias_field_matches_invalid\"),\n                  }\n                : {\n                      key: \"taken\",\n                      final: true,\n                      test: async ({ value }): Promise<boolean> => {\n                          if (!value) {\n                              return true;\n                          }\n                          const client = this.context;\n                          try {\n                              await client.getRoomIdForAlias(this.asFullAlias(value));\n                              // we got a room id, so the alias is taken\n                              return false;\n                          } catch (err) {\n                              console.log(err);\n                              // any server error code will do,\n                              // either it M_NOT_FOUND or the alias is invalid somehow,\n                              // in which case we don't want to show the invalid message\n                              return err instanceof MatrixError;\n                          }\n                      },\n                      valid: () => _t(\"room_settings|general|alias_field_taken_valid\"),\n                      invalid: () =>\n                          this.props.domain\n                              ? _t(\"room_settings|general|alias_field_taken_invalid_domain\")\n                              : _t(\"room_settings|general|alias_field_taken_invalid\"),\n                  },\n        ],\n    });\n\n    public get isValid(): boolean {\n        return this.state.isValid;\n    }\n\n    public async validate(options: IValidateOpts): Promise<boolean> {\n        const val = await this.fieldRef.current?.validate(options);\n        return val ?? false;\n    }\n\n    public focus(): void {\n        this.fieldRef.current?.focus();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEvent } from \"react\";\nimport { secureRandomString } from \"matrix-js-sdk/src/randomstring\";\nimport { SettingsToggleInput } from \"@vector-im/compound-web\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { _t } from \"../../../languageHandler\";\nimport { type SettingLevel } from \"../../../settings/SettingLevel\";\nimport { type BooleanSettingKey, defaultWatchManager } from \"../../../settings/Settings\";\n\ninterface IProps {\n    // The setting must be a boolean\n    name: BooleanSettingKey;\n    level: SettingLevel;\n    roomId?: string; // for per-room settings\n    label?: string;\n    isExplicit?: boolean;\n    hideIfCannotSet?: boolean;\n    onChange?(checked: boolean): void;\n}\n\ninterface IState {\n    value: boolean;\n}\n\nexport default class SettingsFlag extends React.Component<IProps, IState> {\n    private readonly id = `mx_SettingsFlag_${secureRandomString(12)}`;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            value: this.getSettingValue(),\n        };\n    }\n\n    public componentDidMount(): void {\n        defaultWatchManager.watchSetting(this.props.name, this.props.roomId ?? null, this.onSettingChange);\n    }\n\n    public componentWillUnmount(): void {\n        defaultWatchManager.unwatchSetting(this.onSettingChange);\n    }\n\n    private getSettingValue(): boolean {\n        // If a level defined in props is overridden by a level at a high presedence, it gets disabled\n        // and we should show the overridding value.\n        if (\n            SettingsStore.settingIsOveriddenAtConfigLevel(this.props.name, this.props.roomId ?? null, this.props.level)\n        ) {\n            return !!SettingsStore.getValue(this.props.name);\n        }\n        return !!SettingsStore.getValueAt(\n            this.props.level,\n            this.props.name,\n            this.props.roomId ?? null,\n            this.props.isExplicit,\n        );\n    }\n    private onSettingChange = (): void => {\n        this.setState({\n            value: this.getSettingValue(),\n        });\n    };\n\n    private onChange = async (evt: ChangeEvent<HTMLInputElement>): Promise<void> => {\n        const newValue = evt.target.checked;\n        try {\n            await this.save(newValue);\n        } catch (ex) {\n            logger.info(`Failed to save setting ${this.props.name}`, ex);\n            return;\n        }\n        this.setState({ value: newValue });\n        this.props.onChange?.(newValue);\n    };\n\n    private save = async (val?: boolean): Promise<void> => {\n        await SettingsStore.setValue(\n            this.props.name,\n            this.props.roomId ?? null,\n            this.props.level,\n            val !== undefined ? val : this.state.value,\n        );\n    };\n\n    public render(): React.ReactNode {\n        const disabled = !SettingsStore.canSetValue(this.props.name, this.props.roomId ?? null, this.props.level);\n\n        if (disabled && this.props.hideIfCannotSet) return null;\n\n        const label = this.props.label ?? SettingsStore.getDisplayName(this.props.name, this.props.level);\n        const description = SettingsStore.getDescription(this.props.name);\n        const shouldWarn = SettingsStore.shouldHaveWarning(this.props.name);\n        const helpMessage = shouldWarn\n            ? _t(\n                  \"settings|warning\",\n                  {},\n                  {\n                      w: (sub) => <span className=\"mx_SettingsTab_microcopy_warning\">{sub}</span>,\n                      description,\n                  },\n              )\n            : description;\n        const disabledMessage = SettingsStore.disabledMessage(this.props.name);\n        return (\n            <SettingsToggleInput\n                id={this.id}\n                checked={this.state.value}\n                onChange={disabledMessage ? undefined : this.onChange}\n                name={this.props.name}\n                disabled={disabled}\n                label={label ?? this.props.name}\n                helpMessage={helpMessage as string}\n                disabledMessage={disabledMessage}\n            />\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { InlineSpinner } from \"@vector-im/compound-web\";\n\nimport { _t } from \"../../../languageHandler\";\n\ninterface IProps {\n    size?: number;\n    message?: string;\n    onFinished: any; // XXX: Spinner pretends to be a dialog so it must accept an onFinished, but it never calls it\n}\n\nexport default class Spinner extends React.PureComponent<IProps> {\n    public static defaultProps: Partial<IProps> = {\n        size: 32,\n    };\n\n    public render(): React.ReactNode {\n        const { size, message } = this.props;\n        return (\n            <div className=\"mx_Spinner\">\n                {message && (\n                    <React.Fragment>\n                        <div className=\"mx_Spinner_Msg\">{message}</div>&nbsp;\n                    </React.Fragment>\n                )}\n                <InlineSpinner size={size} aria-label={_t(\"common|loading\")} role=\"progressbar\" data-testid=\"spinner\" />\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024,2025 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useId, type ReactNode, type Ref } from \"react\";\nimport { secureRandomString } from \"matrix-js-sdk/src/randomstring\";\nimport { CheckboxInput, Form, HelpMessage, InlineField, Label } from \"@vector-im/compound-web\";\n\ninterface IProps extends React.InputHTMLAttributes<HTMLInputElement> {\n    inputRef?: Ref<HTMLInputElement>;\n    id?: string;\n    description?: ReactNode;\n}\n\nconst StyledCheckbox: React.FC<IProps> = ({\n    id: initialId,\n    children: label,\n    className,\n    inputRef,\n    description,\n    ...otherProps\n}) => {\n    const id = initialId || \"checkbox_\" + secureRandomString(10);\n    const name = useId();\n    const descriptionId = useId();\n    return (\n        <Form.Root>\n            <InlineField\n                className={className}\n                name={name}\n                control={\n                    <CheckboxInput\n                        ref={inputRef}\n                        aria-describedby={description ? descriptionId : undefined}\n                        id={id}\n                        {...otherProps}\n                    />\n                }\n            >\n                {label && <Label htmlFor={id}>{label}</Label>}\n                {description && <HelpMessage id={descriptionId}>{description}</HelpMessage>}\n            </InlineField>\n        </Form.Root>\n    );\n};\n\nexport default StyledCheckbox;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type Ref } from \"react\";\nimport classnames from \"classnames\";\n\ninterface IProps extends React.InputHTMLAttributes<HTMLInputElement> {\n    inputRef?: Ref<HTMLInputElement>;\n    outlined?: boolean;\n    // If true (default), the children will be contained within a <label> element\n    // If false, they'll be in a div. Putting interactive components that have labels\n    // themselves in labels can cause strange bugs like https://github.com/vector-im/element-web/issues/18031\n    childrenInLabel?: boolean;\n\n    /**\n     * If provided will override the default dot icon drawn for checked state\n     */\n    icon?: JSX.Element;\n}\n\nexport default class StyledRadioButton extends React.PureComponent<IProps> {\n    public static readonly defaultProps = {\n        className: \"\",\n        childrenInLabel: true,\n    };\n\n    public render(): React.ReactNode {\n        const { children, className, disabled, outlined, childrenInLabel, inputRef, icon, ...otherProps } = this.props;\n        const _className = classnames(\"mx_StyledRadioButton\", className, {\n            mx_StyledRadioButton_disabled: disabled,\n            mx_StyledRadioButton_enabled: !disabled,\n            mx_StyledRadioButton_checked: this.props.checked,\n            mx_StyledRadioButton_outlined: outlined,\n        });\n\n        const radioButton = (\n            <React.Fragment>\n                <input\n                    // Pass through the ref - used for keyboard shortcut access to some buttons\n                    ref={inputRef}\n                    type=\"radio\"\n                    disabled={disabled}\n                    {...otherProps}\n                />\n                <div>\n                    {/* Empty div is used to render the radio button circle */}\n                    <div>{icon}</div>\n                </div>\n            </React.Fragment>\n        );\n\n        if (childrenInLabel) {\n            return (\n                <label className={_className}>\n                    {radioButton}\n                    <div className=\"mx_StyledRadioButton_content\">{children}</div>\n                    <div className=\"mx_StyledRadioButton_spacer\" />\n                </label>\n            );\n        } else {\n            return (\n                <div className={_className}>\n                    <label className=\"mx_StyledRadioButton_innerLabel\">{radioButton}</label>\n                    <div className=\"mx_StyledRadioButton_content\">{children}</div>\n                    <div className=\"mx_StyledRadioButton_spacer\" />\n                </div>\n            );\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ChangeEvent, type ReactNode } from \"react\";\nimport classNames from \"classnames\";\n\nimport StyledRadioButton from \"./StyledRadioButton\";\n\nexport interface IDefinition<T extends string> {\n    value: T;\n    className?: string;\n    disabled?: boolean;\n    label: ReactNode;\n    description?: ReactNode;\n    checked?: boolean; // If provided it will override the value comparison done in the group\n}\n\ninterface IProps<T extends string> {\n    name: string;\n    className?: string;\n    definitions: IDefinition<T>[];\n    value?: T; // if not provided no options will be selected\n    outlined?: boolean;\n    disabled?: boolean;\n    onChange(newValue: T): void;\n}\n\nfunction StyledRadioGroup<T extends string>({\n    name,\n    definitions,\n    value,\n    className,\n    outlined,\n    disabled,\n    onChange,\n}: IProps<T>): JSX.Element {\n    const _onChange = (e: ChangeEvent<HTMLInputElement>): void => {\n        onChange(e.target.value as T);\n    };\n\n    return (\n        <React.Fragment>\n            {definitions.map((d) => {\n                const id = `${name}-${d.value}`;\n                return (\n                    <React.Fragment key={d.value}>\n                        <StyledRadioButton\n                            id={id}\n                            className={classNames(className, d.className)}\n                            onChange={_onChange}\n                            checked={d.checked !== undefined ? d.checked : d.value === value}\n                            name={name}\n                            value={d.value}\n                            disabled={d.disabled ?? disabled}\n                            outlined={outlined}\n                            aria-describedby={d.description ? `${id}-description` : undefined}\n                        >\n                            {d.label}\n                        </StyledRadioButton>\n                        {d.description ? <span id={`${id}-description`}>{d.description}</span> : null}\n                    </React.Fragment>\n                );\n            })}\n        </React.Fragment>\n    );\n}\n\nexport default StyledRadioGroup;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\nCopyright 2017 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\n\nimport { useAsyncMemo } from \"../../../hooks/useAsyncMemo\";\n\ninterface Props {\n    language?: string;\n    children: string;\n}\n\nexport default function SyntaxHighlight({ children, language }: Props): JSX.Element {\n    const highlighted = useAsyncMemo(async () => {\n        const { default: highlight } = await import(\"highlight.js\");\n        return language ? highlight.highlight(children, { language }) : highlight.highlightAuto(children);\n    }, [language, children]);\n\n    return (\n        <pre className={`mx_SyntaxHighlight hljs language-${highlighted?.language}`}>\n            {highlighted ? <code dangerouslySetInnerHTML={{ __html: highlighted.value }} /> : children}\n        </pre>\n    );\n}\n","/*\nCopyright 2019-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n */\n\nimport React, { type HTMLAttributes } from \"react\";\nimport { Tooltip } from \"@vector-im/compound-web\";\n\ninterface IProps extends HTMLAttributes<HTMLSpanElement> {\n    tooltip: string;\n    tooltipProps?: {\n        tabIndex?: number;\n    };\n}\n\nexport default class TextWithTooltip extends React.Component<IProps> {\n    public render(): React.ReactNode {\n        const { className, children, tooltip, tooltipProps } = this.props;\n\n        return (\n            <Tooltip label={tooltip} placement=\"right\">\n                <span className={className} tabIndex={tooltipProps?.tabIndex ?? 0}>\n                    {children}\n                </span>\n            </Tooltip>\n        );\n    }\n}\n","/*\nCopyright 2017-2024 New Vector Ltd.\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode } from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\n\ninterface IProps {\n    // The number of elements to show before truncating. If negative, no truncation is done.\n    truncateAt: number;\n    // The className to apply to the wrapping div\n    className?: string;\n    // A function that returns the children to be rendered into the element.\n    // The start element is included, the end is not (as in `slice`).\n    // If omitted, the React child elements will be used. This parameter can be used\n    // to avoid creating unnecessary React elements.\n    getChildren?: (start: number, end: number) => Array<React.ReactNode>;\n    // A function that should return the total number of child element available.\n    // Required if getChildren is supplied.\n    getChildCount?: () => number;\n    // A function which will be invoked when an overflow element is required.\n    // This will be inserted after the children.\n    createOverflowElement: (overflowCount: number, totalCount: number) => React.ReactNode;\n    children?: ReactNode;\n    id?: string;\n}\n\nexport default class TruncatedList extends React.Component<IProps> {\n    public static defaultProps = {\n        truncateAt: 2,\n        createOverflowElement(overflowCount: number, totalCount: number) {\n            return <div>{_t(\"truncated_list_n_more\", { count: overflowCount })}</div>;\n        },\n    };\n\n    private getChildren(start: number, end: number): Array<React.ReactNode> {\n        if (this.props.getChildren && this.props.getChildCount) {\n            return this.props.getChildren(start, end);\n        } else {\n            // XXX: I'm not sure why anything would pass null into this, it seems\n            // like a bizarre case to handle, but I'm preserving the behaviour.\n            // (see commit 38d5c7d5c5d5a34dc16ef5d46278315f5c57f542)\n            return React.Children.toArray(this.props.children)\n                .filter((c) => {\n                    return c != null;\n                })\n                .slice(start, end);\n        }\n    }\n\n    private getChildCount(): number {\n        if (this.props.getChildren && this.props.getChildCount) {\n            return this.props.getChildCount();\n        } else {\n            return React.Children.toArray(this.props.children).filter((c) => {\n                return c != null;\n            }).length;\n        }\n    }\n\n    public render(): ReactNode {\n        let overflowNode: ReactNode | undefined;\n\n        const totalChildren = this.getChildCount();\n        let upperBound = totalChildren;\n        if (this.props.truncateAt >= 0) {\n            const overflowCount = totalChildren - this.props.truncateAt;\n            if (overflowCount > 1) {\n                overflowNode = this.props.createOverflowElement(overflowCount, totalChildren);\n                upperBound = this.props.truncateAt;\n            }\n        }\n        const childNodes = this.getChildren(0, upperBound);\n\n        return (\n            <div className={this.props.className} role=\"list\" id={this.props.id}>\n                {childNodes}\n                {overflowNode}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode } from \"react\";\nimport classNames from \"classnames\";\nimport memoizeOne from \"memoize-one\";\nimport { CheckIcon, CloseIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\ntype Data = Pick<IFieldState, \"value\" | \"allowEmpty\">;\n\ninterface IResult {\n    key: string;\n    valid: boolean;\n    text: string;\n}\n\ninterface IRule<T, D = undefined> {\n    key: string;\n    final?: boolean;\n    skip?(this: T, data: Data, derivedData: D): boolean;\n    test(this: T, data: Data, derivedData: D): boolean | Promise<boolean>;\n    valid?(this: T, derivedData: D): string | null;\n    invalid?(this: T, derivedData: D): string | null;\n}\n\ninterface IArgs<T, D = void> {\n    rules: IRule<T, D>[];\n    description?(this: T, derivedData: D, results: IResult[]): ReactNode;\n    hideDescriptionIfValid?: boolean;\n    deriveData?(data: Data): Promise<D>;\n    memoize?: boolean;\n}\n\nexport interface IFieldState {\n    value: string | null;\n    focused: boolean;\n    allowEmpty?: boolean;\n}\n\nexport interface IValidationResult {\n    valid?: boolean;\n    feedback?: JSX.Element | string;\n}\n\n/**\n * Creates a validation function from a set of rules describing what to validate.\n * Generic T is the \"this\" type passed to the rule methods\n *\n * @param {Function} description\n *     Function that returns a string summary of the kind of value that will\n *     meet the validation rules. Shown at the top of the validation feedback.\n * @param {boolean} hideDescriptionIfValid\n *     If true, don't show the description if the validation passes validation.\n * @param {Function} deriveData\n *     Optional function that returns a Promise to an object of generic type D.\n *     The result of this Promise is passed to rule methods `skip`, `test`, `valid`, and `invalid`.\n *     Useful for doing calculations per-value update once rather than in each of the above rule methods.\n * @param {Object} rules\n *     An array of rules describing how to check to input value. Each rule in an object\n *     and may have the following properties:\n *     - `key`: A unique ID for the rule. Required.\n *     - `skip`: A function used to determine whether the rule should even be evaluated.\n *     - `test`: A function used to determine the rule's current validity. Required.\n *     - `valid`: Function returning text to show when the rule is valid. Only shown if set.\n *     - `invalid`: Function returning text to show when the rule is invalid. Only shown if set.\n *     - `final`: A Boolean if true states that this rule will only be considered if all rules before it returned valid.\n * @param {boolean?} memoize\n *     If true, will use memoization to avoid calling deriveData & rules unless the value or allowEmpty change.\n *     Be careful to not use this if your validation is not pure and depends on other fields, such as \"repeat password\".\n * @returns {Function}\n *     A validation function that takes in the current input value and returns\n *     the overall validity and a feedback UI that can be rendered for more detail.\n */\nexport default function withValidation<T = void, D = void>({\n    description,\n    hideDescriptionIfValid,\n    deriveData,\n    rules,\n    memoize,\n}: IArgs<T, D>): (fieldState: IFieldState) => Promise<IValidationResult> {\n    let checkRules = async function (\n        this: T,\n        data: Data,\n        derivedData: D,\n    ): Promise<[valid: boolean, results: IResult[]]> {\n        const results: IResult[] = [];\n        let valid = true;\n        for (const rule of rules) {\n            if (!rule.key || !rule.test) {\n                continue;\n            }\n\n            if (!valid && rule.final) {\n                continue;\n            }\n\n            if (rule.skip?.call(this, data, derivedData)) {\n                continue;\n            }\n\n            // We're setting `this` to whichever component holds the validation\n            // function. That allows rules to access the state of the component.\n            const ruleValid: boolean = await rule.test.call(this, data, derivedData);\n            valid = valid && ruleValid;\n            if (ruleValid && rule.valid) {\n                // If the rule's result is valid and has text to show for\n                // the valid state, show it.\n                const text = rule.valid.call(this, derivedData);\n                if (!text) {\n                    continue;\n                }\n                results.push({\n                    key: rule.key,\n                    valid: true,\n                    text,\n                });\n            } else if (!ruleValid && rule.invalid) {\n                // If the rule's result is invalid and has text to show for\n                // the invalid state, show it.\n                const text = rule.invalid.call(this, derivedData);\n                if (!text) {\n                    continue;\n                }\n                results.push({\n                    key: rule.key,\n                    valid: false,\n                    text,\n                });\n            }\n        }\n\n        return [valid, results];\n    };\n\n    // We have to memoize it in chunks as `focused` can change frequently, but it isn't passed to these methods\n    if (memoize) {\n        if (deriveData) deriveData = memoizeOne(deriveData, isDataEqual);\n        checkRules = memoizeOne(checkRules, isDerivedDataEqual);\n    }\n\n    return async function onValidate(\n        this: T,\n        { value, focused, allowEmpty = true }: IFieldState,\n    ): Promise<IValidationResult> {\n        if (!value && allowEmpty) {\n            return {};\n        }\n\n        const data = { value, allowEmpty };\n        // We know that if deriveData is set then D will not be undefined\n        const derivedData = (await deriveData?.call(this, data)) as D;\n        const [valid, results] = await checkRules.call(this, data, derivedData);\n\n        // Hide feedback when not focused\n        if (!focused) {\n            return { valid };\n        }\n\n        let details: ReactNode | undefined;\n        if (results && results.length) {\n            details = (\n                <ul className=\"mx_Validation_details\">\n                    {results.map((result) => {\n                        const classes = classNames({\n                            mx_Validation_detail: true,\n                            mx_Validation_valid: result.valid,\n                            mx_Validation_invalid: !result.valid,\n                        });\n                        return (\n                            <li key={result.key} className={classes}>\n                                {result.valid ? <CheckIcon /> : <CloseIcon />}\n                                {result.text}\n                            </li>\n                        );\n                    })}\n                </ul>\n            );\n        }\n\n        let summary: ReactNode | undefined;\n        if (description && (details || !hideDescriptionIfValid)) {\n            // We're setting `this` to whichever component holds the validation\n            // function. That allows rules to access the state of the component.\n            const content = description.call(this, derivedData, results);\n            summary = content ? <div className=\"mx_Validation_description\">{content}</div> : undefined;\n        }\n\n        let feedback: JSX.Element | undefined;\n        if (summary || details) {\n            feedback = (\n                <div className=\"mx_Validation\">\n                    {summary}\n                    {details}\n                </div>\n            );\n        }\n\n        return {\n            valid,\n            feedback,\n        };\n    };\n}\n\nfunction isDataEqual([a]: [Data], [b]: [Data]): boolean {\n    return a.value === b.value && a.allowEmpty === b.allowEmpty;\n}\n\nfunction isDerivedDataEqual([a1, a2]: [Data, any], [b1, b2]: [Data, any]): boolean {\n    return a2 === b2 && isDataEqual([a1], [b1]);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Tulir Asokan <tulir@maunium.net>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport classNames from \"classnames\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { type CategoryKey, type ICategory } from \"./Category\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\n\ninterface IProps {\n    categories: ICategory[];\n    onAnchorClick(id: CategoryKey): void;\n}\n\nclass Header extends React.PureComponent<IProps> {\n    private findNearestEnabled(index: number, delta: number): number | undefined {\n        index += this.props.categories.length;\n        const cats = [...this.props.categories, ...this.props.categories, ...this.props.categories];\n\n        while (index < cats.length && index >= 0) {\n            if (cats[index].enabled) return index % this.props.categories.length;\n            index += delta > 0 ? 1 : -1;\n        }\n    }\n\n    private changeCategoryRelative(delta: number): void {\n        // Move to the next/previous category using the first visible as the current.\n        const current = this.props.categories.findIndex((c) => c.visible);\n        this.changeCategoryAbsolute(current + delta, delta);\n    }\n\n    private changeCategoryAbsolute(index: number, delta = 1): void {\n        const category = this.props.categories[this.findNearestEnabled(index, delta)!];\n        if (category) {\n            this.props.onAnchorClick(category.id);\n            category.ref.current?.focus();\n        }\n    }\n\n    // Implements ARIA Tabs with Automatic Activation pattern\n    // https://www.w3.org/TR/wai-aria-practices/examples/tabs/tabs-1/tabs.html\n    private onKeyDown = (ev: React.KeyboardEvent): void => {\n        let handled = true;\n\n        const action = getKeyBindingsManager().getAccessibilityAction(ev);\n        switch (action) {\n            case KeyBindingAction.ArrowLeft:\n                this.changeCategoryRelative(-1);\n                break;\n            case KeyBindingAction.ArrowRight:\n                this.changeCategoryRelative(1);\n                break;\n\n            case KeyBindingAction.Home:\n                this.changeCategoryAbsolute(0);\n                break;\n            case KeyBindingAction.End:\n                this.changeCategoryAbsolute(this.props.categories.length - 1, -1);\n                break;\n            default:\n                handled = false;\n        }\n\n        if (handled) {\n            ev.preventDefault();\n            ev.stopPropagation();\n        }\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <nav\n                className=\"mx_EmojiPicker_header\"\n                role=\"tablist\"\n                aria-label={_t(\"emoji|categories\")}\n                onKeyDown={this.onKeyDown}\n            >\n                {this.props.categories.map((category) => {\n                    const classes = classNames(\"mx_EmojiPicker_anchor\", {\n                        mx_EmojiPicker_anchor_visible: category.visible,\n                    });\n                    // Properties of this button are also modified by EmojiPicker's updateVisibility in DOM.\n                    return (\n                        <button\n                            disabled={!category.enabled}\n                            key={category.id}\n                            ref={category.ref}\n                            className={classes}\n                            onClick={() => this.props.onAnchorClick(category.id)}\n                            title={category.name}\n                            role=\"tab\"\n                            tabIndex={category.firstVisible ? 0 : -1} // roving\n                            aria-selected={category.visible}\n                            aria-controls={`mx_EmojiPicker_category_${category.id}`}\n                        >\n                            {category.emoji}\n                        </button>\n                    );\n                })}\n            </nav>\n        );\n    }\n}\n\nexport default Header;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Tulir Asokan <tulir@maunium.net>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { CloseIcon, SearchIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { RovingTabIndexContext } from \"../../../accessibility/RovingTabIndex\";\n\ninterface IProps {\n    query: string;\n    onChange(value: string): void;\n    onEnter(): void;\n    onKeyDown(event: React.KeyboardEvent): void;\n}\n\nclass Search extends React.PureComponent<IProps> {\n    public static contextType = RovingTabIndexContext;\n    declare public context: React.ContextType<typeof RovingTabIndexContext>;\n\n    private inputRef = React.createRef<HTMLInputElement>();\n\n    public componentDidMount(): void {\n        // For some reason, neither the autoFocus nor just calling focus() here worked, so here's a window.setTimeout\n        window.setTimeout(() => this.inputRef.current?.focus(), 0);\n    }\n\n    private onKeyDown = (ev: React.KeyboardEvent): void => {\n        const action = getKeyBindingsManager().getAccessibilityAction(ev);\n        switch (action) {\n            case KeyBindingAction.Enter:\n                this.props.onEnter();\n                ev.stopPropagation();\n                ev.preventDefault();\n                break;\n\n            default:\n                this.props.onKeyDown(ev);\n        }\n    };\n\n    public render(): React.ReactNode {\n        let rightButton: JSX.Element;\n        if (this.props.query) {\n            rightButton = (\n                <button\n                    onClick={() => this.props.onChange(\"\")}\n                    className=\"mx_EmojiPicker_search_clear\"\n                    title={_t(\"emoji_picker|cancel_search_label\")}\n                >\n                    <CloseIcon />\n                </button>\n            );\n        } else {\n            rightButton = (\n                <span className=\"mx_EmojiPicker_search_icon\">\n                    <SearchIcon />\n                </span>\n            );\n        }\n\n        return (\n            <div className=\"mx_EmojiPicker_search\">\n                <input\n                    autoFocus\n                    type=\"text\"\n                    placeholder={_t(\"action|search\")}\n                    aria-label={_t(\"action|search\")}\n                    value={this.props.query}\n                    onChange={(ev) => this.props.onChange(ev.target.value)}\n                    onKeyDown={this.onKeyDown}\n                    ref={this.inputRef}\n                    // Setting aria-activedescendant on the input allows screen readers to identify the active emoji.\n                    // Setting it when there is not a query causes screen readers to read out the first emoji when focusing the input, and it continually tells you you are in the table vs the input.\n                    aria-activedescendant={this.props.query ? this.context.state.activeNode?.id : undefined}\n                    aria-controls=\"mx_EmojiPicker_body\"\n                    aria-haspopup=\"grid\"\n                    aria-autocomplete=\"list\"\n                />\n                {rightButton}\n            </div>\n        );\n    }\n}\n\nexport default Search;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Tulir Asokan <tulir@maunium.net>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type Emoji } from \"@matrix-org/emojibase-bindings\";\n\ninterface IProps {\n    emoji: Emoji;\n}\n\nclass Preview extends React.PureComponent<IProps> {\n    public render(): React.ReactNode {\n        const {\n            unicode,\n            label,\n            shortcodes: [shortcode],\n        } = this.props.emoji;\n\n        return (\n            <div className=\"mx_EmojiPicker_footer mx_EmojiPicker_preview\">\n                <div className=\"mx_EmojiPicker_preview_emoji\">{unicode}</div>\n                <div className=\"mx_EmojiPicker_preview_text\">\n                    <div className=\"mx_EmojiPicker_name mx_EmojiPicker_preview_name\">{label}</div>\n                    <div className=\"mx_EmojiPicker_shortcode\">{shortcode}</div>\n                </div>\n            </div>\n        );\n    }\n}\n\nexport default Preview;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Tulir Asokan <tulir@maunium.net>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type Emoji as IEmoji } from \"@matrix-org/emojibase-bindings\";\n\nimport { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport { RovingAccessibleButton } from \"../../../accessibility/RovingTabIndex\";\n\ninterface IProps {\n    emoji: IEmoji;\n    /**\n     * Set of which emojis are already selected and should be decorated as such.\n     * If specified, emoji will use a checkbox role with aria-checked set appropriately.\n     */\n    selectedEmojis?: Set<string>;\n    onClick(ev: ButtonEvent, emoji: IEmoji): void;\n    onMouseEnter(emoji: IEmoji): void;\n    onMouseLeave(emoji: IEmoji): void;\n    disabled?: boolean;\n    id?: string;\n    className?: string;\n}\n\nclass Emoji extends React.PureComponent<IProps> {\n    public render(): React.ReactNode {\n        const { onClick, onMouseEnter, onMouseLeave, emoji, selectedEmojis } = this.props;\n        const isSelected = selectedEmojis?.has(emoji.unicode);\n        return (\n            <RovingAccessibleButton\n                id={this.props.id}\n                onClick={(ev: ButtonEvent) => onClick(ev, emoji)}\n                onMouseEnter={() => onMouseEnter(emoji)}\n                onMouseLeave={() => onMouseLeave(emoji)}\n                className={this.props.className}\n                disabled={this.props.disabled || undefined}\n                role={selectedEmojis ? \"checkbox\" : undefined}\n                aria-checked={this.props.disabled ? undefined : isSelected}\n                focusOnMouseOver\n            >\n                <div className={`mx_EmojiPicker_item ${isSelected ? \"mx_EmojiPicker_item_selected\" : \"\"}`}>\n                    {emoji.unicode}\n                </div>\n            </RovingAccessibleButton>\n        );\n    }\n}\n\nexport default Emoji;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Tulir Asokan <tulir@maunium.net>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { getEmojiFromUnicode, type Emoji as IEmoji } from \"@matrix-org/emojibase-bindings\";\n\nimport { _t } from \"../../../languageHandler\";\nimport Emoji from \"./Emoji\";\nimport { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport Toolbar from \"../../../accessibility/Toolbar\";\n\n// We use the variation-selector Heart in Quick Reactions for some reason\nconst QUICK_REACTIONS = [\"👍\", \"👎\", \"😄\", \"🎉\", \"😕\", \"❤️\", \"🚀\", \"👀\"].map((emoji) => {\n    const data = getEmojiFromUnicode(emoji);\n    if (!data) {\n        throw new Error(`Emoji ${emoji} doesn't exist in emojibase`);\n    }\n    return data;\n});\n\ninterface IProps {\n    selectedEmojis?: Set<string>;\n    onClick(ev: ButtonEvent, emoji: IEmoji): void;\n}\n\ninterface IState {\n    hover?: IEmoji;\n}\n\nclass QuickReactions extends React.Component<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n        this.state = {};\n    }\n\n    private onMouseEnter = (emoji: IEmoji): void => {\n        this.setState({\n            hover: emoji,\n        });\n    };\n\n    private onMouseLeave = (): void => {\n        this.setState({\n            hover: undefined,\n        });\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <section className=\"mx_EmojiPicker_footer mx_EmojiPicker_quick mx_EmojiPicker_category\">\n                <h2 className=\"mx_EmojiPicker_quick_header mx_EmojiPicker_category_label\">\n                    {!this.state.hover ? (\n                        _t(\"emoji|quick_reactions\")\n                    ) : (\n                        <React.Fragment>\n                            <span className=\"mx_EmojiPicker_name\">{this.state.hover.label}</span>\n                            <span className=\"mx_EmojiPicker_shortcode\">{this.state.hover.shortcodes[0]}</span>\n                        </React.Fragment>\n                    )}\n                </h2>\n                <Toolbar className=\"mx_EmojiPicker_list\" aria-label={_t(\"emoji|quick_reactions\")}>\n                    {QUICK_REACTIONS.map((emoji) => (\n                        <Emoji\n                            key={emoji.hexcode}\n                            emoji={emoji}\n                            onClick={this.props.onClick}\n                            onMouseEnter={this.onMouseEnter}\n                            onMouseLeave={this.onMouseLeave}\n                            selectedEmojis={this.props.selectedEmojis}\n                            className=\"mx_EmojiPicker_item_wrapper\"\n                        />\n                    ))}\n                </Toolbar>\n            </section>\n        );\n    }\n}\n\nexport default QuickReactions;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Tulir Asokan <tulir@maunium.net>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type RefObject } from \"react\";\nimport { type DATA_BY_CATEGORY, type Emoji as IEmoji } from \"@matrix-org/emojibase-bindings\";\n\nimport { CATEGORY_HEADER_HEIGHT, EMOJI_HEIGHT, EMOJIS_PER_ROW } from \"./EmojiPicker\";\nimport LazyRenderList from \"../elements/LazyRenderList\";\nimport Emoji from \"./Emoji\";\nimport { type ButtonEvent } from \"../elements/AccessibleButton\";\n\nconst OVERFLOW_ROWS = 3;\n\nexport type CategoryKey = keyof typeof DATA_BY_CATEGORY | \"recent\";\n\nexport interface ICategory {\n    id: CategoryKey;\n    name: string;\n    // Emoji to show in the header for this category\n    emoji: string;\n    enabled: boolean;\n    // Whether the category is currently visible\n    visible: boolean;\n    // Whether the category is the first visible category\n    firstVisible: boolean;\n    ref: RefObject<HTMLButtonElement | null>;\n}\n\ninterface IProps {\n    id: string;\n    name: string;\n    emojis: IEmoji[];\n    selectedEmojis?: Set<string>;\n    heightBefore: number;\n    viewportHeight: number;\n    scrollTop: number;\n    onClick(ev: ButtonEvent, emoji: IEmoji): void;\n    onMouseEnter(emoji: IEmoji): void;\n    onMouseLeave(emoji: IEmoji): void;\n    isEmojiDisabled?: (unicode: string) => boolean;\n}\n\nfunction hexEncode(str: string): string {\n    let hex: string;\n    let i: number;\n\n    let result = \"\";\n    for (i = 0; i < str.length; i++) {\n        hex = str.charCodeAt(i).toString(16);\n        result += (\"000\" + hex).slice(-4);\n    }\n\n    return result;\n}\n\nclass Category extends React.PureComponent<IProps> {\n    private renderEmojiRow = (rowIndex: number): JSX.Element => {\n        const { onClick, onMouseEnter, onMouseLeave, selectedEmojis, emojis } = this.props;\n        const emojisForRow = emojis.slice(rowIndex * 8, (rowIndex + 1) * 8);\n        return (\n            <div key={rowIndex} role=\"row\">\n                {emojisForRow.map((emoji) => (\n                    <div role=\"gridcell\" className=\"mx_EmojiPicker_item_wrapper\" key={emoji.hexcode}>\n                        <Emoji\n                            emoji={emoji}\n                            selectedEmojis={selectedEmojis}\n                            onClick={onClick}\n                            onMouseEnter={onMouseEnter}\n                            onMouseLeave={onMouseLeave}\n                            disabled={this.props.isEmojiDisabled?.(emoji.unicode)}\n                            id={`mx_EmojiPicker_item_${this.props.id}_${hexEncode(emoji.unicode)}`}\n                        />\n                    </div>\n                ))}\n            </div>\n        );\n    };\n\n    public render(): React.ReactNode {\n        const { emojis, name, heightBefore, viewportHeight, scrollTop } = this.props;\n        if (!emojis || emojis.length === 0) {\n            return null;\n        }\n        const rows = new Array(Math.ceil(emojis.length / EMOJIS_PER_ROW));\n        for (let counter = 0; counter < rows.length; ++counter) {\n            rows[counter] = counter;\n        }\n\n        const viewportTop = scrollTop;\n        const viewportBottom = viewportTop + viewportHeight;\n        const listTop = heightBefore + CATEGORY_HEADER_HEIGHT;\n        const listBottom = listTop + rows.length * EMOJI_HEIGHT;\n        const top = Math.max(viewportTop, listTop);\n        const bottom = Math.min(viewportBottom, listBottom);\n        // the viewport height and scrollTop passed to the LazyRenderList\n        // is capped at the intersection with the real viewport, so lists\n        // out of view are passed height 0, so they won't render any items.\n        const localHeight = Math.max(0, bottom - top);\n        const localScrollTop = Math.max(0, scrollTop - listTop);\n\n        return (\n            <section\n                id={`mx_EmojiPicker_category_${this.props.id}`}\n                className=\"mx_EmojiPicker_category\"\n                data-category-id={this.props.id}\n                role=\"tabpanel\"\n                aria-label={name}\n            >\n                <h2 className=\"mx_EmojiPicker_category_label\">{name}</h2>\n                <LazyRenderList\n                    className=\"mx_EmojiPicker_list\"\n                    itemHeight={EMOJI_HEIGHT}\n                    items={rows}\n                    scrollTop={localScrollTop}\n                    height={localHeight}\n                    overflowItems={OVERFLOW_ROWS}\n                    overflowMargin={0}\n                    renderItem={this.renderEmojiRow}\n                    role=\"grid\"\n                    aria-multiselectable\n                />\n            </section>\n        );\n    }\n}\n\nexport default Category;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Tulir Asokan <tulir@maunium.net>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type Dispatch } from \"react\";\nimport { DATA_BY_CATEGORY, getEmojiFromUnicode, type Emoji as IEmoji } from \"@matrix-org/emojibase-bindings\";\nimport { clamp } from \"@element-hq/web-shared-components\";\nimport classNames from \"classnames\";\n\nimport { _t } from \"../../../languageHandler\";\nimport * as recent from \"../../../emojipicker/recent\";\nimport AutoHideScrollbar from \"../../structures/AutoHideScrollbar\";\nimport Header from \"./Header\";\nimport Search from \"./Search\";\nimport Preview from \"./Preview\";\nimport QuickReactions from \"./QuickReactions\";\nimport Category, { type CategoryKey, type ICategory } from \"./Category\";\nimport { filterBoolean } from \"../../../utils/arrays\";\nimport {\n    type IAction as RovingAction,\n    type IState as RovingState,\n    RovingTabIndexProvider,\n    Type,\n} from \"../../../accessibility/RovingTabIndex\";\nimport { Key } from \"../../../Keyboard\";\nimport { type ButtonEvent } from \"../elements/AccessibleButton\";\n\nexport const CATEGORY_HEADER_HEIGHT = 20;\nexport const EMOJI_HEIGHT = 35;\nexport const EMOJIS_PER_ROW = 8;\n\nconst ZERO_WIDTH_JOINER = \"\\u200D\";\n\ninterface IProps {\n    selectedEmojis?: Set<string>;\n    onChoose(unicode: string): boolean;\n    onFinished(): void;\n    isEmojiDisabled?: (unicode: string) => boolean;\n}\n\ninterface IState {\n    filter: string;\n    previewEmoji?: IEmoji;\n    scrollTop: number;\n    // initial estimation of height, dialog is hardcoded to 450px height.\n    // should be enough to never have blank rows of emojis as\n    // 3 rows of overflow are also rendered. The actual value is updated on scroll.\n    viewportHeight: number;\n    // Track if user has interacted with arrow keys or search\n    showHighlight: boolean;\n}\n\nclass EmojiPicker extends React.Component<IProps, IState> {\n    private readonly recentlyUsed: IEmoji[];\n    private readonly memoizedDataByCategory: Record<CategoryKey, IEmoji[]>;\n    private readonly categories: ICategory[];\n\n    private scrollRef = React.createRef<AutoHideScrollbar<\"div\">>();\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            filter: \"\",\n            scrollTop: 0,\n            viewportHeight: 280,\n            showHighlight: false,\n        };\n\n        // Convert recent emoji characters to emoji data, removing unknowns and duplicates\n        this.recentlyUsed = Array.from(new Set(filterBoolean(recent.get().map(getEmojiFromUnicode))));\n        this.memoizedDataByCategory = {\n            recent: this.recentlyUsed,\n            ...DATA_BY_CATEGORY,\n        };\n\n        const hasRecentlyUsed = this.recentlyUsed.length > 0;\n\n        const categoryConfig: Pick<ICategory, \"id\" | \"name\" | \"emoji\">[] = [\n            { id: \"recent\", name: _t(\"emoji|category_frequently_used\"), emoji: \"🕒\" },\n            { id: \"people\", name: _t(\"emoji|category_smileys_people\"), emoji: \"😀\" },\n            { id: \"nature\", name: _t(\"emoji|category_animals_nature\"), emoji: \"🐕\" },\n            { id: \"foods\", name: _t(\"emoji|category_food_drink\"), emoji: \"🍎\" },\n            { id: \"activity\", name: _t(\"emoji|category_activities\"), emoji: \"⚽️\" },\n            { id: \"places\", name: _t(\"emoji|category_travel_places\"), emoji: \"🚗\" },\n            { id: \"objects\", name: _t(\"emoji|category_objects\"), emoji: \"💡\" },\n            { id: \"symbols\", name: _t(\"emoji|category_symbols\"), emoji: \"⁉️\" },\n            { id: \"flags\", name: _t(\"emoji|category_flags\"), emoji: \"🏁\" },\n        ];\n\n        this.categories = categoryConfig.map((config) => {\n            let isEnabled = true;\n            let isVisible = false;\n            let firstVisible = false;\n            if (config.id === \"recent\") {\n                isEnabled = hasRecentlyUsed;\n                isVisible = hasRecentlyUsed;\n                firstVisible = hasRecentlyUsed;\n            } else if (config.id === \"people\") {\n                isVisible = true;\n                firstVisible = !hasRecentlyUsed;\n            }\n            return {\n                ...config,\n                enabled: isEnabled,\n                visible: isVisible,\n                firstVisible: firstVisible,\n                ref: React.createRef(),\n            };\n        });\n    }\n\n    private onScroll = (): void => {\n        const body = this.scrollRef.current?.containerRef.current;\n        if (!body) return;\n        this.setState({\n            scrollTop: body.scrollTop,\n            viewportHeight: body.clientHeight,\n        });\n        this.updateVisibility();\n    };\n\n    // Given a roving emoji button returns the role=row element containing it\n    private getRow(rovingNode?: Element): Element | undefined {\n        return this.getGridcell(rovingNode)?.parentElement ?? undefined;\n    }\n\n    // Given a roving emoji button returns the role=gridcell element containing it\n    private getGridcell(rovingNode?: Element): Element | undefined {\n        return rovingNode?.parentElement ?? undefined;\n    }\n\n    // Given a role=gridcell node returns the roving emoji button contained within\n    private getRovingNode(gridcellNode?: Element): Element | undefined {\n        return gridcellNode?.children[0];\n    }\n\n    private keyboardNavigation(ev: React.KeyboardEvent, state: RovingState, dispatch: Dispatch<RovingAction>): void {\n        const rowElement = this.getRow(state.activeNode);\n        const gridcellNode = this.getGridcell(state.activeNode);\n        if (!rowElement || !gridcellNode || !state.activeNode) return;\n\n        // Index of element within row container\n        const columnIndex = Array.from(rowElement.children).indexOf(gridcellNode);\n        // Index of element within the list of roving nodes\n        const refIndex = state.nodes.indexOf(state.activeNode);\n\n        let focusNode: HTMLElement | undefined;\n        let newRowElement: Element | undefined;\n        switch (ev.key) {\n            case Key.ARROW_LEFT:\n                focusNode = state.nodes[refIndex - 1];\n                newRowElement = this.getRow(focusNode);\n                break;\n\n            case Key.ARROW_RIGHT:\n                focusNode = state.nodes[refIndex + 1];\n                newRowElement = this.getRow(focusNode);\n                break;\n\n            case Key.ARROW_UP:\n            case Key.ARROW_DOWN: {\n                // For up/down we find the prev/next parent by inspecting the refs either side of our row\n                const node =\n                    ev.key === Key.ARROW_UP\n                        ? state.nodes[refIndex - columnIndex - 1]\n                        : state.nodes[refIndex - columnIndex + EMOJIS_PER_ROW];\n                newRowElement = this.getRow(node);\n                if (newRowElement) {\n                    const newColumnIndex = clamp(columnIndex, 0, newRowElement.children.length - 1);\n                    const newTarget = this.getRovingNode(newRowElement?.children[newColumnIndex]);\n                    focusNode = state.nodes.find((r) => r === newTarget);\n                }\n                break;\n            }\n        }\n\n        if (focusNode) {\n            // Only move actual DOM focus if an emoji already has focus\n            // If the input has focus, keep using aria-activedescendant for virtual focus\n            if (document.activeElement !== document.querySelector(\".mx_EmojiPicker_search input\")) {\n                focusNode?.focus();\n            }\n            dispatch({\n                type: Type.SetFocus,\n                payload: { node: focusNode },\n            });\n\n            if (rowElement !== newRowElement) {\n                focusNode?.scrollIntoView({\n                    behavior: \"auto\",\n                    block: \"center\",\n                    inline: \"center\",\n                });\n            }\n        }\n\n        ev.preventDefault();\n        ev.stopPropagation();\n    }\n\n    private onKeyDown = (ev: React.KeyboardEvent, state: RovingState, dispatch: Dispatch<RovingAction>): void => {\n        if (state.activeNode && [Key.ARROW_DOWN, Key.ARROW_RIGHT, Key.ARROW_LEFT, Key.ARROW_UP].includes(ev.key)) {\n            // If highlight is not shown yet, show it and reset to first emoji\n            if (!this.state.showHighlight) {\n                this.setState({ showHighlight: true });\n                // Reset to first emoji when showing highlight for the first time (or after it was hidden)\n                if (state.nodes.length > 0) {\n                    dispatch({\n                        type: Type.SetFocus,\n                        payload: { node: state.nodes[0] },\n                    });\n                }\n                ev.preventDefault();\n                ev.stopPropagation();\n                return;\n            }\n            this.keyboardNavigation(ev, state, dispatch);\n        }\n    };\n\n    private updateVisibility = (): void => {\n        const body = this.scrollRef.current?.containerRef.current;\n        if (!body) return;\n        const rect = body.getBoundingClientRect();\n        let firstVisibleFound = false;\n        for (const cat of this.categories) {\n            const elem = body.querySelector(`[data-category-id=\"${cat.id}\"]`);\n            if (!elem) {\n                cat.visible = false;\n                cat.ref.current?.classList.remove(\"mx_EmojiPicker_anchor_visible\");\n                continue;\n            }\n            const elemRect = elem.getBoundingClientRect();\n            const y = elemRect.y - rect.y;\n            const yEnd = elemRect.y + elemRect.height - rect.y;\n            cat.visible = y < rect.height && yEnd > 0;\n            if (cat.visible && !firstVisibleFound) {\n                firstVisibleFound = true;\n                cat.firstVisible = true;\n            } else {\n                cat.firstVisible = false;\n            }\n            // We update this here instead of through React to avoid re-render on scroll.\n            if (!cat.ref.current) continue;\n            if (cat.visible) {\n                cat.ref.current.classList.add(\"mx_EmojiPicker_anchor_visible\");\n                cat.ref.current.setAttribute(\"aria-selected\", \"true\");\n            } else {\n                cat.ref.current.classList.remove(\"mx_EmojiPicker_anchor_visible\");\n                cat.ref.current.setAttribute(\"aria-selected\", \"false\");\n            }\n            if (cat.firstVisible) {\n                cat.ref.current.setAttribute(\"tabindex\", \"0\");\n            } else {\n                cat.ref.current.setAttribute(\"tabindex\", \"-1\");\n            }\n        }\n    };\n\n    private scrollToCategory = (category: string): void => {\n        this.scrollRef.current?.containerRef.current\n            ?.querySelector(`[data-category-id=\"${category}\"]`)\n            ?.scrollIntoView();\n    };\n\n    private onChangeFilter = (filter: string): void => {\n        const lcFilter = filter.toLowerCase().trim(); // filter is case insensitive\n\n        // User has typed a query, show highlight\n        // If filter is cleared, hide highlight again\n        if (lcFilter && !this.state.showHighlight) {\n            this.setState({ showHighlight: true });\n        } else if (!lcFilter && this.state.showHighlight) {\n            this.setState({ showHighlight: false });\n        }\n\n        for (const cat of this.categories) {\n            let emojis: IEmoji[];\n            // If the new filter string includes the old filter string, we don't have to re-filter the whole dataset.\n            if (lcFilter.includes(this.state.filter)) {\n                emojis = this.memoizedDataByCategory[cat.id];\n            } else {\n                emojis = cat.id === \"recent\" ? this.recentlyUsed : DATA_BY_CATEGORY[cat.id];\n            }\n\n            if (lcFilter !== \"\") {\n                emojis = emojis.filter((emoji) => this.emojiMatchesFilter(emoji, lcFilter));\n                // Copy the array to not clobber the original unfiltered sorting\n                emojis = [...emojis].sort((a, b) => {\n                    const indexA = a.shortcodes[0].indexOf(lcFilter);\n                    const indexB = b.shortcodes[0].indexOf(lcFilter);\n\n                    // Prioritize emojis containing the filter in its shortcode\n                    if (indexA == -1 || indexB == -1) {\n                        return indexB - indexA;\n                    }\n\n                    // If both emojis start with the filter\n                    // put the shorter emoji first\n                    if (indexA == 0 && indexB == 0) {\n                        return a.shortcodes[0].length - b.shortcodes[0].length;\n                    }\n\n                    // Prioritize emojis starting with the filter\n                    return indexA - indexB;\n                });\n            }\n\n            this.memoizedDataByCategory[cat.id] = emojis;\n            cat.enabled = emojis.length > 0;\n            // The setState below doesn't re-render the header and we already have the refs for updateVisibility, so...\n            if (cat.ref.current) {\n                cat.ref.current.disabled = !cat.enabled;\n            }\n        }\n        this.setState({ filter });\n        // Header underlines need to be updated, but updating requires knowing\n        // where the categories are, so we wait for a tick.\n        window.setTimeout(this.updateVisibility, 0);\n    };\n\n    private emojiMatchesFilter = (emoji: IEmoji, filter: string): boolean => {\n        // If the query is an emoji containing a variation then strip it to provide more useful matches\n        if (filter.includes(ZERO_WIDTH_JOINER)) {\n            filter = filter.split(ZERO_WIDTH_JOINER, 2)[0];\n        }\n        return (\n            emoji.label.toLowerCase().includes(filter) ||\n            (Array.isArray(emoji.emoticon)\n                ? emoji.emoticon.some((x) => x.includes(filter))\n                : emoji.emoticon?.includes(filter)) ||\n            emoji.shortcodes.some((x) => x.toLowerCase().includes(filter)) ||\n            emoji.unicode.split(ZERO_WIDTH_JOINER).includes(filter)\n        );\n    };\n\n    private onEnterFilter = (): void => {\n        // Only select emoji if highlight is shown\n        if (!this.state.showHighlight) return;\n\n        const btn = this.scrollRef.current?.containerRef.current?.querySelector<HTMLButtonElement>(\n            '.mx_EmojiPicker_item_wrapper [tabindex=\"0\"]',\n        );\n        btn?.click();\n        this.props.onFinished();\n    };\n\n    private onHoverEmoji = (emoji: IEmoji): void => {\n        this.setState({\n            previewEmoji: emoji,\n        });\n    };\n\n    private onHoverEmojiEnd = (): void => {\n        this.setState({\n            previewEmoji: undefined,\n        });\n    };\n\n    private onClickEmoji = (ev: ButtonEvent, emoji: IEmoji): void => {\n        if (this.props.onChoose(emoji.unicode) !== false) {\n            recent.add(emoji.unicode);\n        }\n        if ((ev as React.KeyboardEvent).key === Key.ENTER) {\n            this.props.onFinished();\n        }\n    };\n\n    private static categoryHeightForEmojiCount(count: number): number {\n        if (count === 0) {\n            return 0;\n        }\n        return CATEGORY_HEADER_HEIGHT + Math.ceil(count / EMOJIS_PER_ROW) * EMOJI_HEIGHT;\n    }\n\n    public render(): React.ReactNode {\n        return (\n            <RovingTabIndexProvider onKeyDown={this.onKeyDown}>\n                {({ onKeyDownHandler }) => {\n                    let heightBefore = 0;\n                    return (\n                        <section\n                            className=\"mx_EmojiPicker\"\n                            data-testid=\"mx_EmojiPicker\"\n                            onKeyDown={onKeyDownHandler}\n                            aria-label={_t(\"a11y|emoji_picker\")}\n                        >\n                            <Header categories={this.categories} onAnchorClick={this.scrollToCategory} />\n                            <Search\n                                query={this.state.filter}\n                                onChange={this.onChangeFilter}\n                                onEnter={this.onEnterFilter}\n                                onKeyDown={onKeyDownHandler}\n                            />\n                            <AutoHideScrollbar\n                                id=\"mx_EmojiPicker_body\"\n                                className={classNames(\"mx_EmojiPicker_body\", {\n                                    mx_EmojiPicker_body_showHighlight: this.state.showHighlight,\n                                })}\n                                ref={this.scrollRef}\n                                onScroll={this.onScroll}\n                            >\n                                {this.categories.map((category) => {\n                                    const emojis = this.memoizedDataByCategory[category.id];\n                                    const categoryElement = (\n                                        <Category\n                                            key={category.id}\n                                            id={category.id}\n                                            name={category.name}\n                                            heightBefore={heightBefore}\n                                            viewportHeight={this.state.viewportHeight}\n                                            scrollTop={this.state.scrollTop}\n                                            emojis={emojis}\n                                            onClick={this.onClickEmoji}\n                                            onMouseEnter={this.onHoverEmoji}\n                                            onMouseLeave={this.onHoverEmojiEnd}\n                                            isEmojiDisabled={this.props.isEmojiDisabled}\n                                            selectedEmojis={this.props.selectedEmojis}\n                                        />\n                                    );\n                                    const height = EmojiPicker.categoryHeightForEmojiCount(emojis.length);\n                                    heightBefore += height;\n                                    return categoryElement;\n                                })}\n                            </AutoHideScrollbar>\n                            {this.state.previewEmoji ? (\n                                <Preview emoji={this.state.previewEmoji} />\n                            ) : (\n                                <QuickReactions\n                                    onClick={this.onClickEmoji}\n                                    selectedEmojis={this.props.selectedEmojis}\n                                />\n                            )}\n                        </section>\n                    );\n                }}\n            </RovingTabIndexProvider>\n        );\n    }\n}\n\nexport default EmojiPicker;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Tulir Asokan <tulir@maunium.net>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type MatrixEvent, EventType, RelationType, type Relations, RelationsEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport EmojiPicker from \"./EmojiPicker\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport RoomContext from \"../../../contexts/RoomContext\";\nimport { type FocusComposerPayload } from \"../../../dispatcher/payloads/FocusComposerPayload\";\n\ninterface IProps {\n    mxEvent: MatrixEvent;\n    reactions?: Relations | null | undefined;\n    onFinished(): void;\n}\n\ninterface IState {\n    selectedEmojis: Set<string>;\n}\n\nclass ReactionPicker extends React.Component<IProps, IState> {\n    public static contextType = RoomContext;\n    declare public context: React.ContextType<typeof RoomContext>;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            selectedEmojis: new Set(Object.keys(this.getReactions())),\n        };\n    }\n\n    public componentDidMount(): void {\n        this.addListeners();\n    }\n\n    public componentDidUpdate(prevProps: IProps): void {\n        if (prevProps.reactions !== this.props.reactions) {\n            this.addListeners();\n            this.onReactionsChange();\n        }\n    }\n\n    private addListeners(): void {\n        if (this.props.reactions) {\n            this.props.reactions.on(RelationsEvent.Add, this.onReactionsChange);\n            this.props.reactions.on(RelationsEvent.Remove, this.onReactionsChange);\n            this.props.reactions.on(RelationsEvent.Redaction, this.onReactionsChange);\n        }\n    }\n\n    public componentWillUnmount(): void {\n        if (this.props.reactions) {\n            this.props.reactions.removeListener(RelationsEvent.Add, this.onReactionsChange);\n            this.props.reactions.removeListener(RelationsEvent.Remove, this.onReactionsChange);\n            this.props.reactions.removeListener(RelationsEvent.Redaction, this.onReactionsChange);\n        }\n    }\n\n    private getReactions(): Record<string, string> {\n        if (!this.props.reactions) {\n            return {};\n        }\n        const userId = MatrixClientPeg.safeGet().getSafeUserId();\n        const myAnnotations = this.props.reactions.getAnnotationsBySender()?.[userId] ?? new Set<MatrixEvent>();\n        return Object.fromEntries(\n            [...myAnnotations]\n                .filter((event) => !event.isRedacted())\n                .map((event) => [event.getRelation()?.key, event.getId()]),\n        );\n    }\n\n    private onReactionsChange = (): void => {\n        this.setState({\n            selectedEmojis: new Set(Object.keys(this.getReactions())),\n        });\n    };\n\n    private onChoose = (reaction: string): boolean => {\n        this.componentWillUnmount();\n        this.props.onFinished();\n        const myReactions = this.getReactions();\n        if (myReactions.hasOwnProperty(reaction)) {\n            if (this.props.mxEvent.isRedacted() || !this.context.canSelfRedact) return false;\n\n            MatrixClientPeg.safeGet().redactEvent(this.props.mxEvent.getRoomId()!, myReactions[reaction]);\n            dis.dispatch<FocusComposerPayload>({\n                action: Action.FocusAComposer,\n                context: this.context.timelineRenderingType,\n            });\n            // Tell the emoji picker not to bump this in the more frequently used list.\n            return false;\n        } else {\n            MatrixClientPeg.safeGet().sendEvent(this.props.mxEvent.getRoomId()!, EventType.Reaction, {\n                \"m.relates_to\": {\n                    rel_type: RelationType.Annotation,\n                    event_id: this.props.mxEvent.getId()!,\n                    key: reaction,\n                },\n            });\n            dis.dispatch({ action: \"message_sent\" });\n            dis.dispatch<FocusComposerPayload>({\n                action: Action.FocusAComposer,\n                context: this.context.timelineRenderingType,\n            });\n            return true;\n        }\n    };\n\n    private isEmojiDisabled = (unicode: string): boolean => {\n        if (!this.getReactions()[unicode]) return false;\n        if (this.context.canSelfRedact) return false;\n\n        return true;\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <EmojiPicker\n                onChoose={this.onChoose}\n                isEmojiDisabled={this.isEmojiDisabled}\n                onFinished={this.props.onFinished}\n                selectedEmojis={this.state.selectedEmojis}\n            />\n        );\n    }\n}\n\nexport default ReactionPicker;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport classNames from \"classnames\";\nimport { ErrorIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { getLocationShareErrorMessage, type LocationShareError } from \"../../../utils/location\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport Heading from \"../typography/Heading\";\n\nexport interface MapErrorProps {\n    error: LocationShareError;\n    onFinished?: () => void;\n    isMinimised?: boolean;\n    className?: string;\n    onClick?: () => void;\n}\n\nexport const MapError: React.FC<MapErrorProps> = ({ error, isMinimised, className, onFinished, onClick }) => (\n    <div\n        data-testid=\"map-rendering-error\"\n        className={classNames(\"mx_MapError\", className, { mx_MapError_isMinimised: isMinimised })}\n        onClick={onClick}\n    >\n        <ErrorIcon className=\"mx_MapError_icon\" />\n        <Heading className=\"mx_MapError_heading\" size=\"3\">\n            {_t(\"location_sharing|failed_load_map\")}\n        </Heading>\n        <p className=\"mx_MapError_message\">{getLocationShareErrorMessage(error)}</p>\n        {onFinished && (\n            <AccessibleButton element=\"button\" kind=\"primary\" onClick={onFinished}>\n                {_t(\"action|ok\")}\n            </AccessibleButton>\n        )}\n    </div>\n);\n","var _path, _g;\nfunction _extends() { return _extends = Object.assign ? Object.assign.bind() : function (n) { for (var e = 1; e < arguments.length; e++) { var t = arguments[e]; for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]); } return n; }, _extends.apply(null, arguments); }\nimport * as React from \"react\";\nimport { forwardRef } from \"react\";\nvar SvgMap = function SvgMap(props, ref) {\n  return /*#__PURE__*/React.createElement(\"svg\", _extends({\n    xmlns: \"http://www.w3.org/2000/svg\",\n    fill: \"none\",\n    viewBox: \"0 0 848 556\",\n    role: \"presentation\",\n    \"aria-hidden\": true,\n    ref: ref\n  }, props), /*#__PURE__*/React.createElement(\"mask\", {\n    id: \"map_svg__a\",\n    width: 848,\n    height: 556,\n    x: 0,\n    y: 0,\n    maskUnits: \"userSpaceOnUse\",\n    style: {\n      maskType: \"alpha\"\n    }\n  }, _path || (_path = /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"currentColor\",\n    d: \"M0 0h847.147v555.685H0z\"\n  }))), _g || (_g = /*#__PURE__*/React.createElement(\"g\", {\n    mask: \"url(#map_svg__a)\"\n  }, /*#__PURE__*/React.createElement(\"circle\", {\n    cx: 424.936,\n    cy: 277.842,\n    r: 495.758\n  }), /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"currentColor\",\n    fillRule: \"evenodd\",\n    d: \"M424.935 874.689c329.63 0 596.845-267.217 596.845-596.847S754.565-319.005 424.935-319.005c-329.629 0-596.846 267.218-596.846 596.847 0 329.63 267.217 596.847 596.846 596.847M-46.544 6.905 920.48 442.347l-47.338 105.126-434.953-195.856-219.202 482.882-104.982-47.656L333.061 304.28-93.881 112.031z\",\n    clipRule: \"evenodd\"\n  }))));\n};\nvar ForwardRef = /*#__PURE__*/forwardRef(SvgMap);\nexport { ForwardRef as Icon };\nexport default \"img/location/map.a3d1233.svg\";","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport classNames from \"classnames\";\nimport LocationMarkerIcon from \"@vector-im/compound-design-tokens/assets/web/icons/location-pin-solid\";\n\nimport { Icon as MapFallbackImage } from \"../../../../res/img/location/map.svg\";\nimport Spinner from \"../elements/Spinner\";\n\ninterface Props extends React.HTMLAttributes<HTMLDivElement> {\n    className?: string;\n    isLoading?: boolean;\n}\n\nconst MapFallback: React.FC<Props> = ({ className, isLoading, children, ...rest }) => {\n    return (\n        <div className={classNames(\"mx_MapFallback\", className)} {...rest}>\n            <MapFallbackImage className=\"mx_MapFallback_bg\" />\n            {isLoading ? <Spinner size={32} /> : <LocationMarkerIcon className=\"mx_MapFallback_icon\" />}\n            {children}\n        </div>\n    );\n};\n\nexport default MapFallback;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// Exports location components which touch maplibre-gs wrapped in React Suspense to enable code splitting\n\nimport React, { type JSX, type ComponentProps, lazy, Suspense } from \"react\";\n\nimport Spinner from \"../elements/Spinner\";\n\nconst MapComponent = lazy(() => import(\"./Map\"));\n\nexport function Map(props: ComponentProps<typeof MapComponent>): JSX.Element {\n    return (\n        <Suspense fallback={<Spinner />}>\n            <MapComponent {...props} />\n        </Suspense>\n    );\n}\n\nconst SmartMarkerComponent = lazy(() => import(\"./SmartMarker\"));\n\nexport function SmartMarker(props: ComponentProps<typeof SmartMarkerComponent>): JSX.Element {\n    return (\n        <Suspense fallback={<Spinner />}>\n            <SmartMarkerComponent {...props} />\n        </Suspense>\n    );\n}\n\nconst LocationButtonComponent = lazy(() => import(\"./LocationButton\"));\n\nexport function LocationButton(props: ComponentProps<typeof LocationButtonComponent>): JSX.Element {\n    return (\n        <Suspense fallback={<Spinner />}>\n            <LocationButtonComponent {...props} />\n        </Suspense>\n    );\n}\n\nconst LocationViewDialogComponent = lazy(() => import(\"./LocationViewDialog\"));\n\nexport function LocationViewDialog(props: ComponentProps<typeof LocationViewDialogComponent>): JSX.Element {\n    return (\n        <Suspense fallback={<Spinner />}>\n            <LocationViewDialogComponent {...props} />\n        </Suspense>\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useState, type FormEvent } from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\nimport Field from \"../elements/Field\";\nimport { RovingAccessibleButton, useRovingTabIndex } from \"../../../accessibility/RovingTabIndex\";\nimport { formatDateForInput } from \"../../../DateUtils\";\n\ninterface IProps {\n    ts: number;\n    onDatePicked: (dateString: string) => void;\n}\n\nconst JumpToDatePicker: React.FC<IProps> = ({ ts, onDatePicked }: IProps) => {\n    const date = new Date(ts);\n    const dateInputDefaultValue = formatDateForInput(date);\n\n    const [dateValue, setDateValue] = useState(dateInputDefaultValue);\n    const [onFocus, isActive, refCallback] = useRovingTabIndex<HTMLInputElement>();\n\n    const onDateValueInput = (ev: React.InputEvent<HTMLInputElement>): void => setDateValue(ev.currentTarget.value);\n    const onJumpToDateSubmit = (ev: FormEvent): void => {\n        ev.preventDefault();\n        onDatePicked(dateValue);\n    };\n\n    return (\n        <form className=\"mx_JumpToDatePicker_form\" onSubmit={onJumpToDateSubmit}>\n            <span className=\"mx_JumpToDatePicker_label\">{_t(\"room|jump_to_date\")}</span>\n            <Field\n                element=\"input\"\n                type=\"date\"\n                onInput={onDateValueInput}\n                value={dateValue}\n                // Prevent people from selecting a day in the future (there won't be any\n                // events there anyway).\n                max={formatDateForInput(new Date())}\n                className=\"mx_JumpToDatePicker_datePicker\"\n                label={_t(\"room|jump_to_date_prompt\")}\n                onFocus={onFocus}\n                inputRef={refCallback}\n                tabIndex={isActive ? 0 : -1}\n            />\n            <RovingAccessibleButton\n                element=\"button\"\n                type=\"submit\"\n                kind=\"primary\"\n                className=\"mx_JumpToDatePicker_submitButton\"\n                onClick={onJumpToDateSubmit}\n            >\n                {_t(\"action|go\")}\n            </RovingAccessibleButton>\n        </form>\n    );\n};\n\nexport default JumpToDatePicker;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\nCopyright 2018 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { Direction, ConnectionError, MatrixError, HTTPError } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { capitalize } from \"lodash\";\nimport { ChevronDownIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\nimport { TimelineSeparator } from \"@element-hq/web-shared-components\";\n\nimport { _t, getUserLanguage } from \"../../../languageHandler\";\nimport { formatFullDateNoDay, formatFullDateNoTime, getDaysArray } from \"../../../DateUtils\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport dispatcher from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { UIFeature } from \"../../../settings/UIFeature\";\nimport Modal from \"../../../Modal\";\nimport ErrorDialog from \"../dialogs/ErrorDialog\";\nimport BugReportDialog from \"../dialogs/BugReportDialog\";\nimport AccessibleButton, { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport { contextMenuBelow } from \"../rooms/RoomTile\";\nimport { ContextMenuTooltipButton } from \"../../structures/ContextMenu\";\nimport IconizedContextMenu, {\n    IconizedContextMenuOption,\n    IconizedContextMenuOptionList,\n} from \"../context_menus/IconizedContextMenu\";\nimport JumpToDatePicker from \"./JumpToDatePicker\";\nimport { type ViewRoomPayload } from \"../../../dispatcher/payloads/ViewRoomPayload\";\nimport RoomContext from \"../../../contexts/RoomContext\";\n\ninterface IProps {\n    roomId: string;\n    ts: number;\n    forExport?: boolean;\n}\n\ninterface IState {\n    contextMenuPosition?: DOMRect;\n    jumpToDateEnabled: boolean;\n}\n\n/**\n * Timeline separator component to render within a MessagePanel bearing the date of the ts given\n *\n * Has additional jump to date functionality when labs flag is enabled\n */\nexport default class DateSeparator extends React.Component<IProps, IState> {\n    public static contextType = RoomContext;\n    declare public context: React.ContextType<typeof RoomContext>;\n    private settingWatcherRef?: string;\n\n    public constructor(props: IProps) {\n        super(props);\n        this.state = {\n            jumpToDateEnabled: SettingsStore.getValue(\"feature_jump_to_date\"),\n        };\n    }\n\n    public componentDidMount(): void {\n        // We're using a watcher so the date headers in the timeline are updated\n        // when the lab setting is toggled.\n        this.settingWatcherRef = SettingsStore.watchSetting(\n            \"feature_jump_to_date\",\n            null,\n            (settingName, roomId, level, newValAtLevel, newVal) => {\n                this.setState({ jumpToDateEnabled: newVal });\n            },\n        );\n    }\n\n    public componentWillUnmount(): void {\n        SettingsStore.unwatchSetting(this.settingWatcherRef);\n    }\n\n    private onContextMenuOpenClick = (e: ButtonEvent): void => {\n        e.preventDefault();\n        e.stopPropagation();\n        const target = e.target as HTMLButtonElement;\n        this.setState({ contextMenuPosition: target.getBoundingClientRect() });\n    };\n\n    private onContextMenuCloseClick = (): void => {\n        this.closeMenu();\n    };\n\n    private closeMenu = (): void => {\n        this.setState({\n            contextMenuPosition: undefined,\n        });\n    };\n\n    private get relativeTimeFormat(): Intl.RelativeTimeFormat {\n        return new Intl.RelativeTimeFormat(getUserLanguage(), { style: \"long\", numeric: \"auto\" });\n    }\n\n    private getLabel(): string {\n        try {\n            const date = new Date(this.props.ts);\n            const disableRelativeTimestamps = !SettingsStore.getValue(UIFeature.TimelineEnableRelativeDates);\n\n            // During the time the archive is being viewed, a specific day might not make sense, so we return the full date\n            if (this.props.forExport || disableRelativeTimestamps) return formatFullDateNoTime(date);\n\n            const today = new Date();\n            const yesterday = new Date();\n            const days = getDaysArray(\"long\");\n            yesterday.setDate(today.getDate() - 1);\n\n            if (date.toDateString() === today.toDateString()) {\n                return this.relativeTimeFormat.format(0, \"day\"); // Today\n            } else if (date.toDateString() === yesterday.toDateString()) {\n                return this.relativeTimeFormat.format(-1, \"day\"); // Yesterday\n            } else if (today.getTime() - date.getTime() < 6 * 24 * 60 * 60 * 1000) {\n                return days[date.getDay()]; // Sunday-Saturday\n            } else {\n                return formatFullDateNoTime(date);\n            }\n        } catch {\n            return _t(\"common|message_timestamp_invalid\");\n        }\n    }\n\n    private pickDate = async (inputTimestamp: number | string | Date): Promise<void> => {\n        const unixTimestamp = new Date(inputTimestamp).getTime();\n        const roomIdForJumpRequest = this.props.roomId;\n\n        try {\n            const cli = MatrixClientPeg.safeGet();\n            const { event_id: eventId, origin_server_ts: originServerTs } = await cli.timestampToEvent(\n                roomIdForJumpRequest,\n                unixTimestamp,\n                Direction.Forward,\n            );\n            logger.log(\n                `/timestamp_to_event: ` +\n                    `found ${eventId} (${originServerTs}) for timestamp=${unixTimestamp} (looking forward)`,\n            );\n\n            // Only try to navigate to the room if the user is still viewing the same\n            // room. We don't want to jump someone back to a room after a slow request\n            // if they've already navigated away to another room.\n            const currentRoomId = this.context.roomViewStore.getRoomId();\n            if (currentRoomId === roomIdForJumpRequest) {\n                dispatcher.dispatch<ViewRoomPayload>({\n                    action: Action.ViewRoom,\n                    event_id: eventId,\n                    highlighted: true,\n                    room_id: roomIdForJumpRequest,\n                    metricsTrigger: undefined, // room doesn't change\n                });\n            } else {\n                logger.debug(\n                    `No longer navigating to date in room (jump to date) because the user already switched ` +\n                        `to another room: currentRoomId=${currentRoomId}, roomIdForJumpRequest=${roomIdForJumpRequest}`,\n                );\n            }\n        } catch (err) {\n            logger.error(\n                `Error occured while trying to find event in ${roomIdForJumpRequest} ` +\n                    `at timestamp=${unixTimestamp}:`,\n                err,\n            );\n\n            // Only display an error if the user is still viewing the same room. We\n            // don't want to worry someone about an error in a room they no longer care\n            // about after a slow request if they've already navigated away to another\n            // room.\n            const currentRoomId = this.context.roomViewStore.getRoomId();\n            if (currentRoomId === roomIdForJumpRequest) {\n                let friendlyErrorMessage = \"An error occured while trying to find and jump to the given date.\";\n                let submitDebugLogsContent: JSX.Element = <></>;\n                if (err instanceof ConnectionError) {\n                    friendlyErrorMessage = _t(\"room|error_jump_to_date_connection\");\n                } else if (err instanceof MatrixError) {\n                    if (err?.errcode === \"M_NOT_FOUND\") {\n                        friendlyErrorMessage = _t(\"room|error_jump_to_date_not_found\", {\n                            dateString: formatFullDateNoDay(new Date(unixTimestamp)),\n                        });\n                    } else {\n                        friendlyErrorMessage = _t(\"room|error_jump_to_date\", {\n                            statusCode: err?.httpStatus || _t(\"room|unknown_status_code_for_timeline_jump\"),\n                            errorCode: err?.errcode || _t(\"common|unavailable\"),\n                        });\n                    }\n                } else if (err instanceof HTTPError) {\n                    friendlyErrorMessage = err.message;\n                } else {\n                    // We only give the option to submit logs for actual errors, not network problems.\n                    submitDebugLogsContent = (\n                        <p>\n                            {_t(\n                                \"room|error_jump_to_date_send_logs_prompt\",\n                                {},\n                                {\n                                    debugLogsLink: (sub) => (\n                                        <AccessibleButton\n                                            // This is by default a `<div>` which we\n                                            // can't nest within a `<p>` here so update\n                                            // this to a be a inline anchor element.\n                                            element=\"a\"\n                                            kind=\"link\"\n                                            onClick={() => this.onBugReport(err instanceof Error ? err : undefined)}\n                                            data-testid=\"jump-to-date-error-submit-debug-logs-button\"\n                                        >\n                                            {sub}\n                                        </AccessibleButton>\n                                    ),\n                                },\n                            )}\n                        </p>\n                    );\n                }\n\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"room|error_jump_to_date_title\"),\n                    description: (\n                        <div data-testid=\"jump-to-date-error-content\">\n                            <p>{friendlyErrorMessage}</p>\n                            {submitDebugLogsContent}\n                            <details>\n                                <summary>{_t(\"room|error_jump_to_date_details\")}</summary>\n                                <p>{String(err)}</p>\n                            </details>\n                        </div>\n                    ),\n                });\n            }\n        }\n    };\n\n    private onBugReport = (err?: Error): void => {\n        Modal.createDialog(BugReportDialog, {\n            error: err,\n            initialText: \"Error occured while using jump to date #jump-to-date\",\n        });\n    };\n\n    private onLastWeekClicked = (): void => {\n        const date = new Date();\n        date.setDate(date.getDate() - 7);\n        this.pickDate(date);\n        this.closeMenu();\n    };\n\n    private onLastMonthClicked = (): void => {\n        const date = new Date();\n        // Month numbers are 0 - 11 and `setMonth` handles the negative rollover\n        date.setMonth(date.getMonth() - 1, 1);\n        this.pickDate(date);\n        this.closeMenu();\n    };\n\n    private onTheBeginningClicked = (): void => {\n        const date = new Date(0);\n        this.pickDate(date);\n        this.closeMenu();\n    };\n\n    private onDatePicked = (dateString: string): void => {\n        this.pickDate(dateString);\n        this.closeMenu();\n    };\n\n    private renderJumpToDateMenu(): React.ReactElement {\n        let contextMenu: JSX.Element | undefined;\n        if (this.state.contextMenuPosition) {\n            const relativeTimeFormat = this.relativeTimeFormat;\n            contextMenu = (\n                <IconizedContextMenu\n                    {...contextMenuBelow(this.state.contextMenuPosition)}\n                    onFinished={this.onContextMenuCloseClick}\n                >\n                    <IconizedContextMenuOptionList first>\n                        <IconizedContextMenuOption\n                            label={capitalize(relativeTimeFormat.format(-1, \"week\"))}\n                            onClick={this.onLastWeekClicked}\n                            data-testid=\"jump-to-date-last-week\"\n                        />\n                        <IconizedContextMenuOption\n                            label={capitalize(relativeTimeFormat.format(-1, \"month\"))}\n                            onClick={this.onLastMonthClicked}\n                            data-testid=\"jump-to-date-last-month\"\n                        />\n                        <IconizedContextMenuOption\n                            label={_t(\"room|jump_to_date_beginning\")}\n                            onClick={this.onTheBeginningClicked}\n                            data-testid=\"jump-to-date-beginning\"\n                        />\n                    </IconizedContextMenuOptionList>\n\n                    <IconizedContextMenuOptionList>\n                        <JumpToDatePicker ts={this.props.ts} onDatePicked={this.onDatePicked} />\n                    </IconizedContextMenuOptionList>\n                </IconizedContextMenu>\n            );\n        }\n\n        return (\n            <ContextMenuTooltipButton\n                className=\"mx_DateSeparator_jumpToDateMenu mx_DateSeparator_dateContent\"\n                data-testid=\"jump-to-date-separator-button\"\n                onClick={this.onContextMenuOpenClick}\n                isExpanded={!!this.state.contextMenuPosition}\n                title={_t(\"room|jump_to_date\")}\n            >\n                <h2 className=\"mx_DateSeparator_dateHeading\" aria-hidden=\"true\">\n                    {this.getLabel()}\n                </h2>\n                <ChevronDownIcon className=\"mx_DateSeparator_chevron\" />\n                {contextMenu}\n            </ContextMenuTooltipButton>\n        );\n    }\n\n    public render(): React.ReactNode {\n        const label = this.getLabel();\n\n        let dateHeaderContent: JSX.Element;\n        if (this.state.jumpToDateEnabled && !this.props.forExport) {\n            dateHeaderContent = this.renderJumpToDateMenu();\n        } else {\n            dateHeaderContent = (\n                <div className=\"mx_DateSeparator_dateContent\">\n                    <h2 className=\"mx_DateSeparator_dateHeading\" aria-hidden=\"true\">\n                        {label}\n                    </h2>\n                </div>\n            );\n        }\n\n        return (\n            <TimelineSeparator label={label} className=\"mx_TimelineSeparator\">\n                {dateHeaderContent}\n            </TimelineSeparator>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode } from \"react\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { ErrorSolidIcon, LockSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\nimport { EventTileBubble } from \"@element-hq/web-shared-components\";\n\nimport type { RoomEncryptionEventContent } from \"matrix-js-sdk/src/types\";\nimport { _t } from \"../../../languageHandler\";\nimport { useMatrixClientContext } from \"../../../contexts/MatrixClientContext\";\nimport DMRoomMap from \"../../../utils/DMRoomMap\";\nimport { objectHasDiff } from \"../../../utils/objects\";\nimport { isLocalRoom } from \"../../../utils/localRoom/isLocalRoom\";\nimport { MEGOLM_ENCRYPTION_ALGORITHM } from \"../../../utils/crypto\";\nimport { useIsEncrypted } from \"../../../hooks/useIsEncrypted.ts\";\n\ninterface IProps {\n    mxEvent: MatrixEvent;\n    timestamp?: JSX.Element;\n    ref?: React.RefObject<HTMLDivElement>;\n}\n\nconst EncryptionEvent = ({ mxEvent, timestamp, ref }: IProps): ReactNode => {\n    const cli = useMatrixClientContext();\n    const roomId = mxEvent.getRoomId()!;\n    const isRoomEncrypted = useIsEncrypted(cli, cli.getRoom(roomId) || undefined);\n\n    const prevContent = mxEvent.getPrevContent() as RoomEncryptionEventContent;\n    const content = mxEvent.getContent<RoomEncryptionEventContent>();\n\n    // if no change happened then skip rendering this, a shallow check is enough as all known fields are top-level.\n    if (!objectHasDiff(prevContent, content)) return null; // nop\n\n    if (content.algorithm === MEGOLM_ENCRYPTION_ALGORITHM && isRoomEncrypted) {\n        let subtitle: string;\n        const dmPartner = DMRoomMap.shared().getUserIdForRoomId(roomId);\n        const room = cli?.getRoom(roomId);\n\n        const stateEncrypted = content[\"io.element.msc4362.encrypt_state_events\"] && cli.enableEncryptedStateEvents;\n\n        if (prevContent.algorithm === MEGOLM_ENCRYPTION_ALGORITHM) {\n            subtitle = _t(\"timeline|m.room.encryption|parameters_changed\");\n        } else if (dmPartner) {\n            const displayName = room?.getMember(dmPartner)?.rawDisplayName || dmPartner;\n            subtitle = _t(\"timeline|m.room.encryption|enabled_dm\", { displayName });\n        } else if (room && isLocalRoom(room)) {\n            subtitle = _t(\"timeline|m.room.encryption|enabled_local\");\n        } else if (stateEncrypted) {\n            subtitle = _t(\"timeline|m.room.encryption|state_enabled\");\n        } else {\n            subtitle = _t(\"timeline|m.room.encryption|enabled\");\n        }\n\n        return (\n            <EventTileBubble\n                icon={<LockSolidIcon />}\n                className=\"mx_EventTileBubble mx_cryptoEvent mx_cryptoEvent_icon\"\n                title={stateEncrypted ? _t(\"common|state_encryption_enabled\") : _t(\"common|encryption_enabled\")}\n                subtitle={subtitle}\n            >\n                {timestamp}\n            </EventTileBubble>\n        );\n    }\n\n    if (isRoomEncrypted) {\n        return (\n            <EventTileBubble\n                icon={<LockSolidIcon />}\n                className=\"mx_EventTileBubble mx_cryptoEvent mx_cryptoEvent_icon\"\n                title={_t(\"common|encryption_enabled\")}\n                subtitle={_t(\"timeline|m.room.encryption|disable_attempt\")}\n            >\n                {timestamp}\n            </EventTileBubble>\n        );\n    }\n\n    return (\n        <EventTileBubble\n            icon={<ErrorSolidIcon color=\"var(--cpd-color-icon-critical-primary)\" />}\n            className=\"mx_EventTileBubble mx_cryptoEvent\"\n            title={_t(\"timeline|m.room.encryption|disabled\")}\n            subtitle={_t(\"timeline|m.room.encryption|unsupported\")}\n            ref={ref}\n        >\n            {timestamp}\n        </EventTileBubble>\n    );\n};\n\nexport default EncryptionEvent;\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type PropsWithChildren, type MouseEventHandler } from \"react\";\nimport { VisibilityOnIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\ninterface IProps {\n    onClick: MouseEventHandler<HTMLButtonElement>;\n}\n\nexport const HiddenMediaPlaceholder: React.FunctionComponent<PropsWithChildren<IProps>> = ({ onClick, children }) => {\n    return (\n        <button onClick={onClick} className=\"mx_HiddenMediaPlaceholder\">\n            <div>\n                <VisibilityOnIcon />\n                <span>{children}</span>\n            </div>\n        </button>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef, type JSX } from \"react\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { CallErrorCode, CallState } from \"matrix-js-sdk/src/webrtc/call\";\nimport classNames from \"classnames\";\nimport { Clock } from \"@element-hq/web-shared-components\";\nimport {\n    EndCallIcon,\n    VideoCallDeclinedSolidIcon,\n    VideoCallMissedSolidIcon,\n    VideoCallSolidIcon,\n    VoiceCallMissedSolidIcon,\n    VoiceCallSolidIcon,\n    VolumeOffSolidIcon,\n    VolumeOnSolidIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport MemberAvatar from \"../avatars/MemberAvatar\";\nimport type LegacyCallEventGrouper from \"../../structures/LegacyCallEventGrouper\";\nimport { LegacyCallEventGrouperEvent } from \"../../structures/LegacyCallEventGrouper\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport InfoTooltip, { InfoTooltipKind } from \"../elements/InfoTooltip\";\nimport { formatPreciseDuration } from \"../../../DateUtils\";\n\nconst MAX_NON_NARROW_WIDTH = (450 / 70) * 100;\n\ninterface IProps {\n    mxEvent: MatrixEvent;\n    callEventGrouper: LegacyCallEventGrouper;\n    timestamp?: JSX.Element;\n}\n\ninterface IState {\n    callState?: CallState;\n    silenced: boolean;\n    narrow: boolean;\n    length: number;\n}\n\nexport function getCallStateIcon(isVoice: boolean, state: undefined | \"missed\" | \"declined\"): JSX.Element {\n    let icon = isVoice ? <VoiceCallSolidIcon /> : <VideoCallSolidIcon />;\n    if (state === \"missed\") {\n        icon = isVoice ? <VoiceCallMissedSolidIcon /> : <VideoCallMissedSolidIcon />;\n    } else if (state === \"declined\") {\n        icon = isVoice ? <EndCallIcon /> : <VideoCallDeclinedSolidIcon />;\n    }\n\n    return <div className=\"mx_LegacyCallEvent_type_icon\">{icon}</div>;\n}\n\nexport default class LegacyCallEvent extends React.PureComponent<IProps, IState> {\n    private wrapperElement = createRef<HTMLDivElement>();\n    private resizeObserver?: ResizeObserver;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            callState: this.props.callEventGrouper.state,\n            silenced: false,\n            narrow: false,\n            length: 0,\n        };\n    }\n\n    public componentDidMount(): void {\n        this.props.callEventGrouper.addListener(LegacyCallEventGrouperEvent.StateChanged, this.onStateChanged);\n        this.props.callEventGrouper.addListener(LegacyCallEventGrouperEvent.SilencedChanged, this.onSilencedChanged);\n        this.props.callEventGrouper.addListener(LegacyCallEventGrouperEvent.LengthChanged, this.onLengthChanged);\n\n        this.resizeObserver = new ResizeObserver(this.resizeObserverCallback);\n        if (this.wrapperElement.current) this.resizeObserver.observe(this.wrapperElement.current);\n    }\n\n    public componentWillUnmount(): void {\n        this.props.callEventGrouper.removeListener(LegacyCallEventGrouperEvent.StateChanged, this.onStateChanged);\n        this.props.callEventGrouper.removeListener(LegacyCallEventGrouperEvent.SilencedChanged, this.onSilencedChanged);\n        this.props.callEventGrouper.removeListener(LegacyCallEventGrouperEvent.LengthChanged, this.onLengthChanged);\n\n        this.resizeObserver?.disconnect();\n    }\n\n    private onLengthChanged = (length: number): void => {\n        this.setState({ length });\n    };\n\n    private resizeObserverCallback = (entries: ResizeObserverEntry[]): void => {\n        const wrapperElementEntry = entries.find((entry) => entry.target === this.wrapperElement.current);\n        if (!wrapperElementEntry) return;\n\n        this.setState({ narrow: wrapperElementEntry.contentRect.width < MAX_NON_NARROW_WIDTH });\n    };\n\n    private onSilencedChanged = (newState: boolean): void => {\n        this.setState({ silenced: newState });\n    };\n\n    private onStateChanged = (newState: CallState): void => {\n        this.setState({ callState: newState });\n    };\n\n    private renderCallBackButton(text: string): JSX.Element {\n        return (\n            <AccessibleButton\n                className=\"mx_LegacyCallEvent_content_button\"\n                onClick={this.props.callEventGrouper.callBack}\n                kind=\"primary\"\n            >\n                {this.props.callEventGrouper.isVoice ? <VoiceCallSolidIcon /> : <VideoCallSolidIcon />}\n                {text}\n            </AccessibleButton>\n        );\n    }\n\n    private renderSilenceIcon(): JSX.Element {\n        return (\n            <AccessibleButton\n                className=\"mx_LegacyCallEvent_iconButton\"\n                onClick={this.props.callEventGrouper.toggleSilenced}\n                title={this.state.silenced ? _t(\"voip|unsilence\") : _t(\"voip|silence\")}\n            >\n                {this.state.silenced ? <VolumeOffSolidIcon /> : <VolumeOnSolidIcon />}\n            </AccessibleButton>\n        );\n    }\n\n    private renderContent(): JSX.Element {\n        if (this.state.callState === CallState.Ringing) {\n            let silenceIcon;\n            if (!this.state.narrow) {\n                silenceIcon = this.renderSilenceIcon();\n            }\n\n            return (\n                <div className=\"mx_LegacyCallEvent_content\">\n                    {silenceIcon}\n                    <AccessibleButton\n                        className=\"mx_LegacyCallEvent_content_button\"\n                        onClick={this.props.callEventGrouper.rejectCall}\n                        kind=\"danger\"\n                    >\n                        <EndCallIcon />\n                        {_t(\"action|decline\")}\n                    </AccessibleButton>\n                    <AccessibleButton\n                        className=\"mx_LegacyCallEvent_content_button\"\n                        onClick={this.props.callEventGrouper.answerCall}\n                        kind=\"primary\"\n                    >\n                        {this.props.callEventGrouper.isVoice ? <VoiceCallSolidIcon /> : <VideoCallSolidIcon />}\n                        {_t(\"action|accept\")}\n                    </AccessibleButton>\n                    {this.props.timestamp}\n                </div>\n            );\n        }\n        if (this.state.callState === CallState.Ended) {\n            const hangupReason = this.props.callEventGrouper.hangupReason;\n            const gotRejected = this.props.callEventGrouper.gotRejected;\n\n            if (gotRejected) {\n                return (\n                    <div className=\"mx_LegacyCallEvent_content\">\n                        {_t(\"timeline|m.call.invite|declined\")}\n                        {this.renderCallBackButton(_t(\"timeline|m.call.invite|call_back_prompt\"))}\n                        {this.props.timestamp}\n                    </div>\n                );\n            } else if (hangupReason === CallErrorCode.AnsweredElsewhere) {\n                return (\n                    <div className=\"mx_LegacyCallEvent_content\">\n                        {_t(\"timeline|m.call.invite|answered_elsewhere\")}\n                        {this.props.timestamp}\n                    </div>\n                );\n            } else if (this.props.callEventGrouper.callWasMissed) {\n                return (\n                    <div className=\"mx_LegacyCallEvent_content\">\n                        {_t(\"timeline|m.call.invite|missed_call\")}\n                        {this.renderCallBackButton(_t(\"timeline|m.call.invite|call_back_prompt\"))}\n                        {this.props.timestamp}\n                    </div>\n                );\n            } else if (!hangupReason || [CallErrorCode.UserHangup, \"user hangup\"].includes(hangupReason)) {\n                // workaround for https://github.com/vector-im/element-web/issues/5178\n                // it seems Android randomly sets a reason of \"user hangup\" which is\n                // interpreted as an error code :(\n                // https://github.com/vector-im/riot-android/issues/2623\n                // Also the correct hangup code as of VoIP v1 (with underscore)\n                // Also, if we don't have a reason\n                const duration = this.props.callEventGrouper.duration!;\n                let text = _t(\"timeline|m.call.hangup|dm\");\n                if (duration) {\n                    text += \" • \" + formatPreciseDuration(duration);\n                }\n                return (\n                    <div className=\"mx_LegacyCallEvent_content\">\n                        {text}\n                        {this.props.timestamp}\n                    </div>\n                );\n            } else if (hangupReason === CallErrorCode.InviteTimeout) {\n                return (\n                    <div className=\"mx_LegacyCallEvent_content\">\n                        {_t(\"timeline|m.call.invite|no_answer\")}\n                        {this.renderCallBackButton(_t(\"timeline|m.call.invite|call_back_prompt\"))}\n                        {this.props.timestamp}\n                    </div>\n                );\n            }\n\n            let reason;\n            if (hangupReason === CallErrorCode.IceFailed) {\n                // We couldn't establish a connection at all\n                reason = _t(\"timeline|m.call.invite|failed_connect_media\");\n            } else if (hangupReason === \"ice_timeout\") {\n                // We established a connection but it died\n                reason = _t(\"timeline|m.call.invite|failed_connection\");\n            } else if (hangupReason === CallErrorCode.NoUserMedia) {\n                // The other side couldn't open capture devices\n                reason = _t(\"timeline|m.call.invite|failed_opponent_media\");\n            } else if (hangupReason === \"unknown_error\") {\n                // An error code the other side doesn't have a way to express\n                // (as opposed to an error code they gave but we don't know about,\n                // in which case we show the error code)\n                reason = _t(\"timeline|m.call.invite|unknown_error\");\n            } else if (hangupReason === CallErrorCode.UserBusy) {\n                reason = _t(\"voip|user_busy_description\");\n            } else {\n                reason = _t(\"timeline|m.call.invite|unknown_failure\", { reason: hangupReason });\n            }\n\n            return (\n                <div className=\"mx_LegacyCallEvent_content\">\n                    <InfoTooltip\n                        tooltip={reason}\n                        className=\"mx_LegacyCallEvent_content_tooltip\"\n                        kind={InfoTooltipKind.Warning}\n                    />\n                    {_t(\"timeline|m.call.invite|failed_connection\")}\n                    {this.renderCallBackButton(_t(\"action|retry\"))}\n                    {this.props.timestamp}\n                </div>\n            );\n        }\n        if (this.state.callState === CallState.Connected) {\n            return (\n                <div className=\"mx_LegacyCallEvent_content\">\n                    <Clock seconds={this.state.length} aria-live=\"off\" />\n                    {this.props.timestamp}\n                </div>\n            );\n        }\n        if (this.state.callState === CallState.Connecting) {\n            return (\n                <div className=\"mx_LegacyCallEvent_content\">\n                    {_t(\"voip|connecting\")}\n                    {this.props.timestamp}\n                </div>\n            );\n        }\n\n        return (\n            <div className=\"mx_LegacyCallEvent_content\">\n                {_t(\"timeline|m.call.invite|unknown_state\")}\n                {this.props.timestamp}\n            </div>\n        );\n    }\n\n    public render(): React.ReactNode {\n        const event = this.props.mxEvent;\n        const sender = event.sender ? event.sender.name : event.getSender();\n        const isVoice = this.props.callEventGrouper.isVoice;\n        const callType = isVoice ? _t(\"voip|voice_call\") : _t(\"voip|video_call\");\n        const callState = this.state.callState;\n        const hangupReason = this.props.callEventGrouper.hangupReason;\n        const content = this.renderContent();\n        const className = classNames(\"mx_LegacyCallEvent\", {\n            mx_LegacyCallEvent_voice: isVoice,\n            mx_LegacyCallEvent_video: !isVoice,\n            mx_LegacyCallEvent_narrow: this.state.narrow,\n        });\n\n        let silenceIcon;\n        if (this.state.narrow && this.state.callState === CallState.Ringing) {\n            silenceIcon = this.renderSilenceIcon();\n        }\n\n        let iconState: Parameters<typeof getCallStateIcon>[1] = undefined;\n        if (this.props.callEventGrouper.callWasMissed) {\n            iconState = \"missed\";\n        } else if (\n            callState === CallState.Ended &&\n            (hangupReason === CallErrorCode.InviteTimeout || this.props.callEventGrouper.gotRejected)\n        ) {\n            iconState = \"declined\";\n        }\n\n        return (\n            <div className=\"mx_LegacyCallEvent_wrapper\" ref={this.wrapperElement}>\n                <div className={className}>\n                    {silenceIcon}\n                    <div className=\"mx_LegacyCallEvent_info\">\n                        <MemberAvatar member={event.sender} size=\"32px\" />\n                        <div className=\"mx_LegacyCallEvent_info_basic\">\n                            <div className=\"mx_LegacyCallEvent_sender\">{sender}</div>\n                            <div className=\"mx_LegacyCallEvent_type\">\n                                {getCallStateIcon(!!isVoice, iconState)}\n                                {callType}\n                            </div>\n                        </div>\n                    </div>\n                    {content}\n                </div>\n            </div>\n        );\n    }\n}\n","/*\n * Copyright 2025 New Vector Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type ChangeEvent, type KeyboardEvent } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport {\n    percentageOf,\n    BaseViewModel,\n    type AudioPlayerViewSnapshot,\n    type AudioPlayerViewModel as AudioPlayerViewModelInterface,\n} from \"@element-hq/web-shared-components\";\n\nimport { type Playback } from \"../../audio/Playback\";\nimport { UPDATE_EVENT } from \"../../stores/AsyncStore\";\nimport { getKeyBindingsManager } from \"../../KeyBindingsManager\";\nimport { KeyBindingAction } from \"../../accessibility/KeyboardShortcuts\";\n\n/**\n * The number of seconds to skip when the user presses the left or right arrow keys.\n */\nconst ARROW_SKIP_SECONDS = 5;\n\ninterface Props {\n    /**\n     * The playback instance that manages the audio playback.\n     */\n    playback: Playback;\n    /**\n     * Optional name of the media being played.\n     */\n    mediaName?: string;\n}\n\n/**\n * ViewModel for the audio player, providing the current state of the audio playback.\n * It listens to updates from the Playback instance and computes a snapshot.\n */\nexport class AudioPlayerViewModel\n    extends BaseViewModel<AudioPlayerViewSnapshot, Props>\n    implements AudioPlayerViewModelInterface\n{\n    /**\n     * Indicates if there was an error processing the audio file.\n     * @private\n     */\n    private error = false;\n\n    /**\n     * Computes the snapshot of the audio player based on the current playback state.\n     * This includes the media name, size in bytes, playback state, duration, percentage complete,\n     * played seconds, and whether there was an error.\n     * @param playback - The playback instance managing the audio playback.\n     * @param mediaName - Optional name of the media being played.\n     * @param error - Indicates if there was an error processing the audio file.\n     */\n    private static readonly computeSnapshot = (\n        playback: Playback,\n        mediaName?: string,\n        error = false,\n    ): AudioPlayerViewSnapshot => {\n        const percentComplete = percentageOf(playback.timeSeconds, 0, playback.durationSeconds) * 100;\n\n        return {\n            mediaName,\n            sizeBytes: playback.sizeBytes,\n            playbackState: playback.currentState,\n            durationSeconds: playback.durationSeconds,\n            percentComplete,\n            playedSeconds: playback.timeSeconds,\n            error,\n        };\n    };\n\n    public constructor(props: Props) {\n        super(props, AudioPlayerViewModel.computeSnapshot(props.playback, props.mediaName));\n        this.disposables.trackListener(props.playback, UPDATE_EVENT, this.setSnapshot);\n        // There is no unsubscribe method in SimpleObservable\n        this.props.playback.clockInfo.liveData.onUpdate(this.setSnapshot);\n\n        // Don't wait for the promise to complete - it will emit a progress update when it\n        // is done, and it's not meant to take long anyhow.\n        this.preparePlayback();\n    }\n\n    /**\n     * Prepares the playback by calling the prepare method on the playback instance.\n     * @private\n     */\n    private async preparePlayback(): Promise<void> {\n        try {\n            await this.props.playback.prepare();\n        } catch (e) {\n            logger.error(\"Error processing audio file:\", e, this.props.playback.currentState);\n            this.error = true;\n            this.setSnapshot();\n        }\n    }\n\n    /**\n     * Sets the snapshot and emits an update to subscribers.\n     */\n    private readonly setSnapshot = (): void => {\n        this.snapshot.set(AudioPlayerViewModel.computeSnapshot(this.props.playback, this.props.mediaName, this.error));\n    };\n\n    public onKeyDown = (ev: KeyboardEvent<HTMLDivElement>): void => {\n        let handled = true;\n        const action = getKeyBindingsManager().getAccessibilityAction(ev);\n\n        switch (action) {\n            case KeyBindingAction.Space:\n                this.togglePlay();\n                break;\n            case KeyBindingAction.ArrowLeft:\n                this.props.playback.skipTo(this.props.playback.timeSeconds - ARROW_SKIP_SECONDS);\n                break;\n            case KeyBindingAction.ArrowRight:\n                this.props.playback.skipTo(this.props.playback.timeSeconds + ARROW_SKIP_SECONDS);\n                break;\n            default:\n                handled = false;\n                break;\n        }\n\n        // stopPropagation() prevents the FocusComposer catch-all from triggering,\n        // but we need to do it on key down instead of press (even though the user\n        // interaction is typically on press).\n        if (handled) {\n            ev.stopPropagation();\n        }\n    };\n\n    public togglePlay = async (): Promise<void> => {\n        await this.props.playback.toggle();\n    };\n\n    public onSeekbarChange = async (ev: ChangeEvent<HTMLInputElement>): Promise<void> => {\n        await this.props.playback.skipTo((Number(ev.target.value) / 100) * this.props.playback.durationSeconds);\n    };\n\n    /**\n     * Updates the properties of the view model and recomputes the snapshot.\n     * @param newProps\n     */\n    public setProps(newProps: Partial<Props>): void {\n        this.props = { ...this.props, ...newProps };\n        this.setSnapshot();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useEffect } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type IContent } from \"matrix-js-sdk/src/matrix\";\nimport { type MediaEventContent } from \"matrix-js-sdk/src/types\";\nimport { AudioPlayerView, useCreateAutoDisposedViewModel } from \"@element-hq/web-shared-components\";\n\nimport { type Playback } from \"../../../audio/Playback\";\nimport InlineSpinner from \"../elements/InlineSpinner\";\nimport { _t } from \"../../../languageHandler\";\nimport MFileBody from \"./MFileBody\";\nimport { type IBodyProps } from \"./IBodyProps\";\nimport { PlaybackManager } from \"../../../audio/PlaybackManager\";\nimport RoomContext, { TimelineRenderingType } from \"../../../contexts/RoomContext\";\nimport MediaProcessingError from \"./shared/MediaProcessingError\";\nimport { AudioPlayerViewModel } from \"../../../viewmodels/audio/AudioPlayerViewModel\";\n\ninterface IState {\n    error?: boolean;\n    playback?: Playback;\n}\n\nexport default class MAudioBody extends React.PureComponent<IBodyProps, IState> {\n    public static contextType = RoomContext;\n    declare public context: React.ContextType<typeof RoomContext>;\n\n    public state: IState = {};\n\n    public async componentDidMount(): Promise<void> {\n        let buffer: ArrayBuffer;\n        try {\n            try {\n                const blob = await this.props.mediaEventHelper!.sourceBlob.value;\n                buffer = await blob.arrayBuffer();\n            } catch (e) {\n                this.setState({ error: true });\n                logger.warn(\"Unable to decrypt audio message\", e);\n                return; // stop processing the audio file\n            }\n        } catch (e) {\n            this.setState({ error: true });\n            logger.warn(\"Unable to decrypt/download audio message\", e);\n            return; // stop processing the audio file\n        }\n\n        // We should have a buffer to work with now: let's set it up\n\n        // Note: we don't actually need a waveform to render an audio event, but voice messages do.\n        const content = this.props.mxEvent.getContent<MediaEventContent & IContent>();\n        const waveform = content?.[\"org.matrix.msc1767.audio\"]?.waveform?.map((p: number) => p / 1024);\n\n        // We should have a buffer to work with now: let's set it up\n        const playback = PlaybackManager.instance.createPlaybackInstance(buffer, waveform);\n        playback.clockInfo.populatePlaceholdersFrom(this.props.mxEvent);\n        this.setState({ playback });\n\n        this.onMount(playback);\n        // Note: the components later on will handle preparing the Playback class for us\n    }\n\n    protected onMount(playback: Playback): void {}\n\n    public componentWillUnmount(): void {\n        this.state.playback?.destroy();\n    }\n\n    protected get showFileBody(): boolean {\n        return (\n            this.context.timelineRenderingType !== TimelineRenderingType.Room &&\n            this.context.timelineRenderingType !== TimelineRenderingType.Pinned &&\n            this.context.timelineRenderingType !== TimelineRenderingType.Search\n        );\n    }\n\n    public render(): React.ReactNode {\n        if (this.state.error) {\n            return (\n                <MediaProcessingError className=\"mx_MAudioBody\">\n                    {_t(\"timeline|m.audio|error_processing_audio\")}\n                </MediaProcessingError>\n            );\n        }\n\n        if (this.props.forExport) {\n            const content = this.props.mxEvent.getContent();\n            // During export, the content url will point to the MSC, which will later point to a local url\n            const contentUrl = content.file?.url || content.url;\n            return (\n                <span className=\"mx_MAudioBody\">\n                    <audio src={contentUrl} controls />\n                </span>\n            );\n        }\n\n        if (!this.state.playback) {\n            return (\n                <span className=\"mx_MAudioBody\">\n                    <InlineSpinner />\n                </span>\n            );\n        }\n\n        // At this point we should have a playable state\n        return (\n            <span className=\"mx_MAudioBody\">\n                <AudioPlayer playback={this.state.playback} mediaName={this.props.mxEvent.getContent().body} />\n                {this.showFileBody && <MFileBody {...this.props} showGenericPlaceholder={false} />}\n            </span>\n        );\n    }\n}\n\ninterface AudioPlayerProps {\n    /**\n     * The playback instance to control audio playback.\n     */\n    playback: Playback;\n    /**\n     * The name of the media being played\n     */\n    mediaName: string;\n}\n\n/**\n * AudioPlayer component that initializes the AudioPlayerViewModel and renders the AudioPlayerView.\n */\nfunction AudioPlayer({ playback, mediaName }: AudioPlayerProps): JSX.Element {\n    const vm = useCreateAutoDisposedViewModel(() => new AudioPlayerViewModel({ playback, mediaName }));\n    useEffect(() => {\n        vm.setProps({ playback, mediaName });\n    }, [playback, mediaName, vm]);\n\n    return <AudioPlayerView vm={vm} />;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type AllHTMLAttributes, createRef } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type MediaEventContent } from \"matrix-js-sdk/src/types\";\nimport { MsgType } from \"matrix-js-sdk/src/matrix\";\nimport { Button } from \"@vector-im/compound-web\";\nimport {\n    AttachmentIcon,\n    DownloadIcon,\n    VideoCallSolidIcon,\n    VolumeOnSolidIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport Modal from \"../../../Modal\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport { mediaFromContent } from \"../../../customisations/Media\";\nimport ErrorDialog from \"../dialogs/ErrorDialog\";\nimport { downloadLabelForFile, presentableTextForFile } from \"../../../utils/FileUtils\";\nimport { type IBodyProps } from \"./IBodyProps\";\nimport { FileDownloader } from \"../../../utils/FileDownloader\";\nimport TextWithTooltip from \"../elements/TextWithTooltip\";\nimport RoomContext, { TimelineRenderingType } from \"../../../contexts/RoomContext\";\n\nexport let DOWNLOAD_ICON_URL: string; // cached copy of the download.svg asset for the sandboxed iframe later on\n\nasync function cacheDownloadIcon(): Promise<void> {\n    if (DOWNLOAD_ICON_URL) return; // cached already\n    // eslint-disable-next-line @typescript-eslint/no-require-imports\n    const svg = await fetch(require(\"@vector-im/compound-design-tokens/icons/download.svg\").default).then((r) =>\n        r.text(),\n    );\n    DOWNLOAD_ICON_URL = \"data:image/svg+xml;base64,\" + window.btoa(svg);\n}\n\n// Cache the asset immediately\n// noinspection JSIgnoredPromiseFromCall\ncacheDownloadIcon();\n\n// User supplied content can contain scripts, we have to be careful that\n// we don't accidentally run those script within the same origin as the\n// client. Otherwise those scripts written by remote users can read\n// the access token and end-to-end keys that are in local storage.\n//\n// For attachments downloaded directly from the homeserver we can use\n// Content-Security-Policy headers to disable script execution.\n//\n// But attachments with end-to-end encryption are more difficult to handle.\n// We need to decrypt the attachment on the client and then display it.\n// To display the attachment we need to turn the decrypted bytes into a URL.\n//\n// There are two ways to turn bytes into URLs, data URL and blob URLs.\n// Data URLs aren't suitable for downloading a file because Chrome has a\n// 2MB limit on the size of URLs that can be viewed in the browser or\n// downloaded. This limit does not seem to apply when the url is used as\n// the source attribute of an image tag.\n//\n// Blob URLs are generated using window.URL.createObjectURL and unfortunately\n// for our purposes they inherit the origin of the page that created them.\n// This means that any scripts that run when the URL is viewed will be able\n// to access local storage.\n//\n// The easiest solution is to host the code that generates the blob URL on\n// a different domain to the client.\n// Another possibility is to generate the blob URL within a sandboxed iframe.\n// The downside of using a second domain is that it complicates hosting,\n// the downside of using a sandboxed iframe is that the browers are overly\n// restrictive in what you are allowed to do with the generated URL.\n\n/**\n * Get the current CSS style for a DOMElement.\n * @param {HTMLElement} element The element to get the current style of.\n * @return {string} The CSS style encoded as a string.\n */\nexport function computedStyle(element: HTMLElement | null): string {\n    if (!element) {\n        return \"\";\n    }\n    const style = window.getComputedStyle(element, null);\n    let cssText = style.cssText;\n    // noinspection EqualityComparisonWithCoercionJS\n    if (cssText == \"\") {\n        // Firefox doesn't implement \".cssText\" for computed styles.\n        // https://bugzilla.mozilla.org/show_bug.cgi?id=137687\n        for (const rule of style) {\n            cssText += rule + \":\";\n            cssText += style.getPropertyValue(rule) + \";\";\n        }\n    }\n    return cssText;\n}\n\ninterface IProps extends IBodyProps {\n    /* whether or not to show the default placeholder for the file. Defaults to true. */\n    showGenericPlaceholder?: boolean;\n}\n\ninterface IState {\n    decryptedBlob?: Blob;\n}\n\nexport default class MFileBody extends React.Component<IProps, IState> {\n    public static contextType = RoomContext;\n    declare public context: React.ContextType<typeof RoomContext>;\n\n    public state: IState = {};\n    private iframe = createRef<HTMLIFrameElement>();\n    private dummyLink = createRef<HTMLAnchorElement>();\n    private userDidClick = false;\n    private fileDownloader: FileDownloader = new FileDownloader(() => this.iframe.current);\n\n    private getContentUrl(): string | null {\n        if (this.props.forExport) return null;\n        const media = mediaFromContent(this.props.mxEvent.getContent());\n        return media.srcHttp;\n    }\n    private get content(): MediaEventContent {\n        return this.props.mxEvent.getContent<MediaEventContent>();\n    }\n\n    private get fileName(): string {\n        return this.props.mediaEventHelper?.fileName || _t(\"common|attachment\");\n    }\n\n    private get linkText(): string {\n        return downloadLabelForFile(this.content, true);\n    }\n\n    private downloadFile(fileName: string, text: string): void {\n        if (!this.state.decryptedBlob) return;\n        this.fileDownloader.download({\n            blob: this.state.decryptedBlob,\n            name: fileName,\n            autoDownload: this.userDidClick,\n            opts: {\n                imgSrc: DOWNLOAD_ICON_URL,\n                imgStyle: null,\n                style: computedStyle(this.dummyLink.current),\n                textContent: text,\n            },\n        });\n    }\n\n    private decryptFile = async (): Promise<void> => {\n        if (this.state.decryptedBlob) {\n            return;\n        }\n        try {\n            this.userDidClick = true;\n            this.setState({\n                decryptedBlob: await this.props.mediaEventHelper!.sourceBlob.value,\n            });\n        } catch (err) {\n            logger.warn(\"Unable to decrypt attachment: \", err);\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"common|error\"),\n                description: _t(\"timeline|m.file|error_decrypting\"),\n            });\n        }\n    };\n\n    private onPlaceholderClick = async (): Promise<void> => {\n        const mediaHelper = this.props.mediaEventHelper;\n        if (mediaHelper?.media.isEncrypted) {\n            await this.decryptFile();\n            this.downloadFile(this.fileName, this.linkText);\n        } else {\n            // As a button we're missing the `download` attribute for styling reasons, so\n            // download with the file downloader.\n            this.fileDownloader.download({\n                blob: await mediaHelper!.sourceBlob.value,\n                name: this.fileName,\n            });\n        }\n    };\n\n    public render(): React.ReactNode {\n        const isEncrypted = this.props.mediaEventHelper?.media.isEncrypted;\n        const contentUrl = this.getContentUrl();\n        const fileType = this.content.info?.mimetype ?? \"application/octet-stream\";\n        // defaultProps breaks types on IBodyProps, so instead define the default here.\n        const showGenericPlaceholder = this.props.showGenericPlaceholder ?? true;\n\n        let showDownloadLink =\n            !showGenericPlaceholder ||\n            (this.context.timelineRenderingType !== TimelineRenderingType.Room &&\n                this.context.timelineRenderingType !== TimelineRenderingType.Search &&\n                this.context.timelineRenderingType !== TimelineRenderingType.Pinned);\n\n        let placeholder: React.ReactNode = null;\n        if (showGenericPlaceholder) {\n            let icon = <AttachmentIcon />;\n            // MFileBody is not generally used for Audio/Video but can be as part of ReplyTile\n            if (this.content.msgtype === MsgType.Audio) {\n                icon = <VolumeOnSolidIcon />;\n            } else if (this.content.msgtype === MsgType.Video) {\n                icon = <VideoCallSolidIcon />;\n            }\n\n            placeholder = (\n                <AccessibleButton className=\"mx_MediaBody mx_MFileBody_info\" onClick={this.onPlaceholderClick}>\n                    <span className=\"mx_MFileBody_info_icon\">{icon}</span>\n                    <TextWithTooltip tooltip={presentableTextForFile(this.content, _t(\"common|attachment\"), true)}>\n                        <span className=\"mx_MFileBody_info_filename\">\n                            {presentableTextForFile(this.content, _t(\"common|attachment\"), true, true)}\n                        </span>\n                    </TextWithTooltip>\n                </AccessibleButton>\n            );\n            showDownloadLink = false;\n        }\n\n        if (this.props.forExport) {\n            const content = this.props.mxEvent.getContent();\n            // During export, the content url will point to the MSC, which will later point to a local url\n            return (\n                <span className=\"mx_MFileBody\">\n                    <a href={content.file?.url || content.url}>{placeholder}</a>\n                </span>\n            );\n        }\n\n        if (this.context.timelineRenderingType === TimelineRenderingType.Thread) {\n            showDownloadLink = false;\n        }\n\n        if (isEncrypted) {\n            if (!this.state.decryptedBlob) {\n                // Need to decrypt the attachment\n                // Wait for the user to click on the link before downloading\n                // and decrypting the attachment.\n\n                // This button should actually Download because usercontent/ will try to click itself\n                // but it is not guaranteed between various browsers' settings.\n                return (\n                    <span className=\"mx_MFileBody\">\n                        {placeholder}\n                        {showDownloadLink && (\n                            <div className=\"mx_MFileBody_download\">\n                                <Button size=\"sm\" kind=\"secondary\" Icon={DownloadIcon} onClick={this.decryptFile}>\n                                    {this.linkText}\n                                </Button>\n                            </div>\n                        )}\n                    </span>\n                );\n            }\n\n            const url = \"usercontent/\"; // XXX: this path should probably be passed from the skin\n\n            // If the attachment is encrypted then put the link inside an iframe.\n            return (\n                <span className=\"mx_MFileBody\">\n                    {placeholder}\n                    {showDownloadLink && (\n                        <div className=\"mx_MFileBody_download\">\n                            <div aria-hidden style={{ display: \"none\" }}>\n                                {/*\n                                 * Add dummy copy of the button\n                                 * We'll use it to learn how the download button\n                                 * would have been styled if it was rendered inline.\n                                 */}\n                                {/* this violates multiple eslint rules\n                            so ignore it completely */}\n                                <Button size=\"sm\" kind=\"secondary\" Icon={DownloadIcon} as=\"a\" ref={this.dummyLink} />\n                            </div>\n                            {/*\n                            TODO: Move iframe (and dummy link) into FileDownloader.\n                            We currently have it set up this way because of styles applied to the iframe\n                            itself which cannot be easily handled/overridden by the FileDownloader. In\n                            future, the download link may disappear entirely at which point it could also\n                            be suitable to just remove this bit of code.\n                         */}\n                            <iframe\n                                aria-hidden\n                                title={presentableTextForFile(this.content, _t(\"common|attachment\"), true, true)}\n                                src={url}\n                                onLoad={() => this.downloadFile(this.fileName, this.linkText)}\n                                ref={this.iframe}\n                                sandbox=\"allow-scripts allow-downloads\"\n                            />\n                        </div>\n                    )}\n                </span>\n            );\n        } else if (contentUrl) {\n            const downloadProps: Pick<\n                AllHTMLAttributes<HTMLAnchorElement>,\n                \"target\" | \"rel\" | \"href\" | \"onClick\" | \"download\"\n            > = {\n                target: \"_blank\",\n                rel: \"noreferrer noopener\",\n\n                // We cannot rely on href+download to download media due to the authenticated media API as it relies\n                // on authentication via headers, so we'll have to download the file into memory and then download it.\n                onClick: (e) => {\n                    logger.log(`Downloading ${fileType} as blob (unencrypted)`);\n\n                    // Avoid letting the <a> do its thing\n                    e.preventDefault();\n                    e.stopPropagation();\n\n                    // Start a fetch for the download\n                    // Based upon https://stackoverflow.com/a/49500465\n                    this.props.mediaEventHelper?.sourceBlob.value.then((blob) => {\n                        const blobUrl = URL.createObjectURL(blob);\n\n                        // We have to create an anchor to download the file\n                        const tempAnchor = document.createElement(\"a\");\n                        tempAnchor.download = this.fileName;\n                        tempAnchor.href = blobUrl;\n                        document.body.appendChild(tempAnchor); // for firefox: https://stackoverflow.com/a/32226068\n                        tempAnchor.click();\n                        tempAnchor.remove();\n                    });\n                },\n            };\n\n            return (\n                <span className=\"mx_MFileBody\">\n                    {placeholder}\n                    {showDownloadLink && (\n                        <div className=\"mx_MFileBody_download\">\n                            <Button size=\"sm\" kind=\"secondary\" Icon={DownloadIcon} as=\"a\" {...downloadProps}>\n                                {this.linkText}\n                            </Button>\n                        </div>\n                    )}\n                </span>\n            );\n        } else {\n            return (\n                <span className=\"mx_MFileBody\">\n                    {placeholder}\n                    {_t(\"timeline|m.file|error_invalid\")}\n                </span>\n            );\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\nCopyright 2018, 2019 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ComponentProps, createRef, type ReactNode } from \"react\";\nimport { Blurhash } from \"react-blurhash\";\nimport classNames from \"classnames\";\nimport { CSSTransition, SwitchTransition } from \"react-transition-group\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { ClientEvent } from \"matrix-js-sdk/src/matrix\";\nimport { type ImageContent } from \"matrix-js-sdk/src/types\";\nimport { Tooltip } from \"@vector-im/compound-web\";\nimport { ImageErrorIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport MFileBody from \"./MFileBody\";\nimport Modal from \"../../../Modal\";\nimport { _t } from \"../../../languageHandler\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport Spinner from \"../elements/Spinner\";\nimport { type Media, mediaFromContent } from \"../../../customisations/Media\";\nimport { BLURHASH_FIELD, createThumbnail } from \"../../../utils/image-media\";\nimport ImageView from \"../elements/ImageView\";\nimport { type IBodyProps } from \"./IBodyProps\";\nimport { type ImageSize, suggestedSize as suggestedImageSize } from \"../../../settings/enums/ImageSize\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport RoomContext, { TimelineRenderingType } from \"../../../contexts/RoomContext\";\nimport { blobIsAnimated, mayBeAnimated } from \"../../../utils/Image\";\nimport { presentableTextForFile } from \"../../../utils/FileUtils\";\nimport { createReconnectedListener } from \"../../../utils/connection\";\nimport MediaProcessingError from \"./shared/MediaProcessingError\";\nimport { DecryptError, DownloadError } from \"../../../utils/DecryptFile\";\nimport { HiddenMediaPlaceholder } from \"./HiddenMediaPlaceholder\";\nimport { useMediaVisible } from \"../../../hooks/useMediaVisible\";\nimport { isMimeTypeAllowed } from \"../../../utils/blobs.ts\";\n\nenum Placeholder {\n    NoImage,\n    Blurhash,\n}\n\ninterface IState {\n    contentUrl: string | null;\n    thumbUrl: string | null;\n    isAnimated?: boolean;\n    error?: unknown;\n    imgError: boolean;\n    imgLoaded: boolean;\n    loadedImageDimensions?: {\n        naturalWidth: number;\n        naturalHeight: number;\n    };\n    hover: boolean;\n    focus: boolean;\n    placeholder: Placeholder;\n}\n\ninterface IProps extends IBodyProps {\n    /**\n     * Should the media be behind a preview.\n     */\n    mediaVisible: boolean;\n    /**\n     * Set the visibility of the media event.\n     * @param visible Should the event be visible.\n     */\n    setMediaVisible: (visible: boolean) => void;\n}\n\n/**\n * @private Only use for inheritance. Use the default export for presentation.\n */\nexport class MImageBodyInner extends React.Component<IProps, IState> {\n    public static contextType = RoomContext;\n    declare public context: React.ContextType<typeof RoomContext>;\n\n    private unmounted = false;\n    private image = createRef<HTMLImageElement>();\n    private placeholder = createRef<HTMLDivElement>();\n    private timeout?: number;\n    private sizeWatcher?: string;\n\n    public state: IState = {\n        contentUrl: null,\n        thumbUrl: null,\n        imgError: false,\n        imgLoaded: false,\n        hover: false,\n        focus: false,\n        placeholder: Placeholder.NoImage,\n    };\n\n    protected onClick = (ev: React.MouseEvent): void => {\n        if (ev.button === 0 && !ev.metaKey) {\n            ev.preventDefault();\n            if (!this.props.mediaVisible) {\n                this.props.setMediaVisible(true);\n                return;\n            }\n\n            const content = this.props.mxEvent.getContent<ImageContent>();\n\n            let httpUrl = this.state.contentUrl;\n            if (\n                this.props.mediaEventHelper?.media.isEncrypted &&\n                !isMimeTypeAllowed(this.props.mediaEventHelper.sourceBlob.cachedValue?.type ?? \"\")\n            ) {\n                // contentUrl will be a blob URI mime-type=application/octet-stream so fall back to the thumbUrl instead\n                httpUrl = this.state.thumbUrl;\n            }\n\n            if (!httpUrl) return;\n            const params: Omit<ComponentProps<typeof ImageView>, \"onFinished\"> = {\n                src: httpUrl,\n                name: content.body && content.body.length > 0 ? content.body : _t(\"common|attachment\"),\n                mxEvent: this.props.mxEvent,\n                permalinkCreator: this.props.permalinkCreator,\n            };\n\n            if (content.info) {\n                params.width = content.info.w;\n                params.height = content.info.h;\n                params.fileSize = content.info.size;\n            }\n\n            if (this.image.current) {\n                const clientRect = this.image.current.getBoundingClientRect();\n\n                params.thumbnailInfo = {\n                    width: clientRect.width,\n                    height: clientRect.height,\n                    positionX: clientRect.x,\n                    positionY: clientRect.y,\n                };\n            }\n\n            Modal.createDialog(ImageView, params, \"mx_Dialog_lightbox\", undefined, true);\n        }\n    };\n\n    private get shouldAutoplay(): boolean {\n        return !(\n            !this.state.contentUrl ||\n            !this.props.mediaVisible ||\n            !this.state.isAnimated ||\n            SettingsStore.getValue(\"autoplayGifs\")\n        );\n    }\n\n    protected onImageEnter = (): void => {\n        this.setState({ hover: true });\n    };\n\n    protected onImageLeave = (): void => {\n        this.setState({ hover: false });\n    };\n\n    private onFocus = (): void => {\n        this.setState({ focus: true });\n    };\n\n    private onBlur = (): void => {\n        this.setState({ focus: false });\n    };\n\n    private reconnectedListener = createReconnectedListener((): void => {\n        MatrixClientPeg.get()?.off(ClientEvent.Sync, this.reconnectedListener);\n        this.setState({ imgError: false });\n    });\n\n    private onImageError = (): void => {\n        // If the thumbnail failed to load then try again using the contentUrl\n        if (this.state.thumbUrl) {\n            this.setState({\n                thumbUrl: null,\n            });\n            return;\n        }\n\n        this.clearBlurhashTimeout();\n        this.setState({\n            imgError: true,\n        });\n        MatrixClientPeg.safeGet().on(ClientEvent.Sync, this.reconnectedListener);\n    };\n\n    private onImageLoad = (): void => {\n        this.clearBlurhashTimeout();\n\n        let loadedImageDimensions: IState[\"loadedImageDimensions\"];\n\n        if (this.image.current) {\n            const { naturalWidth, naturalHeight } = this.image.current;\n            // this is only used as a fallback in case content.info.w/h is missing\n            loadedImageDimensions = { naturalWidth, naturalHeight };\n        }\n        this.setState({ imgLoaded: true, loadedImageDimensions });\n    };\n\n    private getContentUrl(): string | null {\n        // During export, the content url will point to the MSC, which will later point to a local url\n        if (this.props.forExport) return this.media.srcMxc;\n        return this.media.srcHttp;\n    }\n\n    private get media(): Media {\n        return mediaFromContent(this.props.mxEvent.getContent());\n    }\n\n    private getThumbUrl(): string | null {\n        // FIXME: we let images grow as wide as you like, rather than capped to 800x600.\n        // So either we need to support custom timeline widths here, or reimpose the cap, otherwise the\n        // thumbnail resolution will be unnecessarily reduced.\n        // custom timeline widths seems preferable.\n        const thumbWidth = 800;\n        const thumbHeight = 600;\n\n        const content = this.props.mxEvent.getContent<ImageContent>();\n        const media = mediaFromContent(content);\n        const info = content.info;\n\n        if (info?.mimetype === \"image/svg+xml\" && media.hasThumbnail) {\n            // Special-case to return clientside sender-generated thumbnails for SVGs, if any,\n            // given we deliberately don't thumbnail them serverside to prevent billion lol attacks and similar.\n            return media.getThumbnailHttp(thumbWidth, thumbHeight, \"scale\");\n        }\n\n        // we try to download the correct resolution for hi-res images (like retina screenshots).\n        // Synapse only supports 800x600 thumbnails for now though,\n        // so we'll need to download the original image for this to work  well for now.\n        // First, let's try a few cases that let us avoid downloading the original, including:\n        //   - When displaying a GIF, we always want to thumbnail so that we can\n        //     properly respect the user's GIF autoplay setting (which relies on\n        //     thumbnailing to produce the static preview image)\n        //   - On a low DPI device, always thumbnail to save bandwidth\n        //   - If there's no sizing info in the event, default to thumbnail\n        if (this.state.isAnimated || window.devicePixelRatio === 1.0 || !info || !info.w || !info.h || !info.size) {\n            return media.getThumbnailOfSourceHttp(thumbWidth, thumbHeight);\n        }\n\n        // We should only request thumbnails if the image is bigger than 800x600 (or 1600x1200 on retina) otherwise\n        // the image in the timeline will just end up resampled and de-retina'd for no good reason.\n        // Ideally the server would pre-gen 1600x1200 thumbnails in order to provide retina thumbnails,\n        // but we don't do this currently in synapse for fear of disk space.\n        // As a compromise, let's switch to non-retina thumbnails only if the original image is both\n        // physically too large and going to be massive to load in the timeline (e.g. >1MB).\n\n        const isLargerThanThumbnail = info.w > thumbWidth || info.h > thumbHeight;\n        const isLargeFileSize = info.size > 1 * 1024 * 1024; // 1mb\n\n        if (isLargeFileSize && isLargerThanThumbnail) {\n            // image is too large physically and byte-wise to clutter our timeline so,\n            // we ask for a thumbnail, despite knowing that it will be max 800x600\n            // despite us being retina (as synapse doesn't do 1600x1200 thumbs yet).\n            return media.getThumbnailOfSourceHttp(thumbWidth, thumbHeight);\n        }\n\n        // download the original image otherwise, so we can scale it client side to take pixelRatio into account.\n        return media.srcHttp;\n    }\n\n    private async downloadImage(): Promise<void> {\n        if (this.state.contentUrl) return; // already downloaded\n\n        let thumbUrl: string | null;\n        let contentUrl: string | null;\n        if (this.props.mediaEventHelper?.media.isEncrypted) {\n            try {\n                [contentUrl, thumbUrl] = await Promise.all([\n                    this.props.mediaEventHelper.sourceUrl.value,\n                    this.props.mediaEventHelper.thumbnailUrl.value,\n                ]);\n            } catch (error) {\n                if (this.unmounted) return;\n\n                if (error instanceof DecryptError) {\n                    logger.error(\"Unable to decrypt attachment: \", error);\n                } else if (error instanceof DownloadError) {\n                    logger.error(\"Unable to download attachment to decrypt it: \", error);\n                } else {\n                    logger.error(\"Error encountered when downloading encrypted attachment: \", error);\n                }\n\n                // Set a placeholder image when we can't decrypt the image.\n                this.setState({ error });\n                return;\n            }\n        } else {\n            thumbUrl = this.getThumbUrl();\n            contentUrl = this.getContentUrl();\n        }\n\n        const content = this.props.mxEvent.getContent<ImageContent>();\n        let isAnimated = content.info?.[\"org.matrix.msc4230.is_animated\"] ?? mayBeAnimated(content.info?.mimetype);\n\n        // If there is no included non-animated thumbnail then we will generate our own, we can't depend on the server\n        // because 1. encryption and 2. we can't ask the server specifically for a non-animated thumbnail.\n        if (isAnimated && !SettingsStore.getValue(\"autoplayGifs\")) {\n            if (!thumbUrl || !content?.info?.thumbnail_info || mayBeAnimated(content.info.thumbnail_info.mimetype)) {\n                const img = document.createElement(\"img\");\n                const loadPromise = new Promise((resolve, reject) => {\n                    img.onload = resolve;\n                    img.onerror = reject;\n                });\n                img.crossOrigin = \"Anonymous\"; // CORS allow canvas access\n                img.src = contentUrl ?? \"\";\n\n                try {\n                    await loadPromise;\n                } catch (error) {\n                    logger.error(\"Unable to download attachment: \", error);\n                    this.setState({ error: error as Error });\n                    return;\n                }\n\n                try {\n                    // If we didn't receive the MSC4230 is_animated flag\n                    // then we need to check if the image is animated by downloading it.\n                    if (\n                        content.info?.[\"org.matrix.msc4230.is_animated\"] === false ||\n                        (await blobIsAnimated(await this.props.mediaEventHelper!.sourceBlob.value)) === false\n                    ) {\n                        isAnimated = false;\n                    }\n\n                    if (isAnimated) {\n                        const thumb = await createThumbnail(\n                            img,\n                            img.width,\n                            img.height,\n                            content.info?.mimetype ?? \"image/jpeg\",\n                            false,\n                        );\n                        thumbUrl = URL.createObjectURL(thumb.thumbnail);\n                    }\n                } catch (error) {\n                    // This is a non-critical failure, do not surface the error or bail the method here\n                    logger.warn(\"Unable to generate thumbnail for animated image: \", error);\n                }\n            }\n        }\n\n        if (this.unmounted) return;\n        this.setState({\n            contentUrl,\n            thumbUrl,\n            isAnimated,\n        });\n    }\n\n    private clearBlurhashTimeout(): void {\n        if (this.timeout) {\n            clearTimeout(this.timeout);\n            this.timeout = undefined;\n        }\n    }\n\n    public componentDidMount(): void {\n        this.unmounted = false;\n\n        if (this.props.mediaVisible) {\n            // noinspection JSIgnoredPromiseFromCall\n            this.downloadImage();\n        }\n\n        // Add a 150ms timer for blurhash to first appear.\n        if (this.props.mxEvent.getContent().info?.[BLURHASH_FIELD]) {\n            this.clearBlurhashTimeout();\n            this.timeout = window.setTimeout(() => {\n                if (!this.state.imgLoaded || !this.state.imgError) {\n                    this.setState({\n                        placeholder: Placeholder.Blurhash,\n                    });\n                }\n            }, 150);\n        }\n\n        this.sizeWatcher = SettingsStore.watchSetting(\"Images.size\", null, () => {\n            this.forceUpdate(); // we don't really have a reliable thing to update, so just update the whole thing\n        });\n    }\n\n    public componentDidUpdate(prevProps: Readonly<IProps>): void {\n        if (!prevProps.mediaVisible && this.props.mediaVisible) {\n            // noinspection JSIgnoredPromiseFromCall\n            this.downloadImage();\n        }\n    }\n\n    public componentWillUnmount(): void {\n        this.unmounted = true;\n        MatrixClientPeg.get()?.off(ClientEvent.Sync, this.reconnectedListener);\n        this.clearBlurhashTimeout();\n        SettingsStore.unwatchSetting(this.sizeWatcher);\n        if (this.state.isAnimated && this.state.thumbUrl) {\n            URL.revokeObjectURL(this.state.thumbUrl);\n        }\n    }\n\n    protected getBanner(content: ImageContent): ReactNode {\n        // Hide it for the threads list & the file panel where we show it as text anyway.\n        if (\n            [TimelineRenderingType.ThreadsList, TimelineRenderingType.File].includes(this.context.timelineRenderingType)\n        ) {\n            return null;\n        }\n\n        return (\n            <span className=\"mx_MImageBody_banner\">\n                {presentableTextForFile(content, _t(\"common|image\"), true, true)}\n            </span>\n        );\n    }\n\n    protected messageContent(\n        contentUrl: string | null,\n        thumbUrl: string | null,\n        content: ImageContent,\n        forcedHeight?: number,\n    ): ReactNode {\n        if (!thumbUrl) thumbUrl = contentUrl; // fallback\n\n        // magic number\n        // edge case for this not to be set by conditions below\n        let infoWidth = 500;\n        let infoHeight = 500;\n        let infoSvg = false;\n\n        if (content.info?.w && content.info?.h) {\n            infoWidth = content.info.w;\n            infoHeight = content.info.h;\n            infoSvg = content.info.mimetype === \"image/svg+xml\";\n        } else if (thumbUrl && contentUrl) {\n            // Whilst the image loads, display nothing. We also don't display a blurhash image\n            // because we don't really know what size of image we'll end up with.\n            //\n            // Once loaded, use the loaded image dimensions stored in `loadedImageDimensions`.\n            //\n            // By doing this, the image \"pops\" into the timeline, but is still restricted\n            // by the same width and height logic below.\n            if (!this.state.loadedImageDimensions) {\n                let imageElement: JSX.Element;\n                if (!this.props.mediaVisible) {\n                    imageElement = (\n                        <HiddenMediaPlaceholder onClick={this.onClick}>\n                            {_t(\"timeline|m.image|show_image\")}\n                        </HiddenMediaPlaceholder>\n                    );\n                } else {\n                    imageElement = (\n                        <img\n                            style={{ display: \"none\" }}\n                            src={thumbUrl}\n                            ref={this.image}\n                            alt={content.body}\n                            onError={this.onImageError}\n                            onLoad={this.onImageLoad}\n                        />\n                    );\n                }\n                return this.wrapImage(contentUrl, imageElement);\n            }\n            infoWidth = this.state.loadedImageDimensions.naturalWidth;\n            infoHeight = this.state.loadedImageDimensions.naturalHeight;\n        }\n\n        // The maximum size of the thumbnail as it is rendered as an <img>,\n        // accounting for any height constraints\n        const { w: maxWidth, h: maxHeight } = suggestedImageSize(\n            SettingsStore.getValue(\"Images.size\") as ImageSize,\n            { w: infoWidth, h: infoHeight },\n            forcedHeight ?? this.props.maxImageHeight,\n        );\n\n        let img: JSX.Element | undefined;\n        let placeholder: JSX.Element | undefined;\n        let gifLabel: JSX.Element | undefined;\n\n        if (!this.props.forExport && !this.state.imgLoaded) {\n            const classes = classNames(\"mx_MImageBody_placeholder\", {\n                \"mx_MImageBody_placeholder--blurhash\": this.props.mxEvent.getContent().info?.[BLURHASH_FIELD],\n            });\n\n            placeholder = (\n                <div className={classes} ref={this.placeholder}>\n                    {this.getPlaceholder(maxWidth, maxHeight)}\n                </div>\n            );\n        }\n\n        let showPlaceholder = Boolean(placeholder);\n\n        const hoverOrFocus = this.state.hover || this.state.focus;\n        if (thumbUrl && !this.state.imgError) {\n            let url = thumbUrl;\n            if (hoverOrFocus && this.shouldAutoplay) {\n                url = this.state.contentUrl!;\n            }\n\n            // Restrict the width of the thumbnail here, otherwise it will fill the container\n            // which has the same width as the timeline\n            // mx_MImageBody_thumbnail resizes img to exactly container size\n            img = (\n                <img\n                    className=\"mx_MImageBody_thumbnail\"\n                    src={url}\n                    ref={this.image}\n                    alt={content.body}\n                    onError={this.onImageError}\n                    onLoad={this.onImageLoad}\n                    onMouseEnter={this.onImageEnter}\n                    onMouseLeave={this.onImageLeave}\n                />\n            );\n        }\n\n        if (!this.props.mediaVisible) {\n            img = (\n                <div style={{ width: maxWidth, height: maxHeight }}>\n                    <HiddenMediaPlaceholder onClick={this.onClick}>\n                        {_t(\"timeline|m.image|show_image\")}\n                    </HiddenMediaPlaceholder>\n                </div>\n            );\n            showPlaceholder = false; // because we're hiding the image, so don't show the placeholder.\n        }\n\n        if (this.state.isAnimated && !SettingsStore.getValue(\"autoplayGifs\") && !hoverOrFocus) {\n            // XXX: Arguably we may want a different label when the animated image is WEBP and not GIF\n            gifLabel = <p className=\"mx_MImageBody_gifLabel\">GIF</p>;\n        }\n\n        let banner: ReactNode | undefined;\n        if (this.props.mediaVisible && hoverOrFocus) {\n            banner = this.getBanner(content);\n        }\n\n        // many SVGs don't have an intrinsic size if used in <img> elements.\n        // due to this we have to set our desired width directly.\n        // this way if the image is forced to shrink, the height adapts appropriately.\n        const sizing = infoSvg ? { maxHeight, maxWidth, width: maxWidth } : { maxHeight, maxWidth };\n\n        if (!this.props.forExport) {\n            placeholder = (\n                <SwitchTransition mode=\"out-in\">\n                    <CSSTransition\n                        classNames=\"mx_rtg--fade\"\n                        key={`img-${showPlaceholder}`}\n                        timeout={300}\n                        nodeRef={this.placeholder}\n                    >\n                        {\n                            showPlaceholder ? (\n                                placeholder\n                            ) : (\n                                <div ref={this.placeholder} />\n                            ) /* Transition always expects a child */\n                        }\n                    </CSSTransition>\n                </SwitchTransition>\n            );\n        }\n\n        const tooltipProps = this.getTooltipProps();\n        let thumbnail = (\n            <div\n                className=\"mx_MImageBody_thumbnail_container\"\n                style={{ maxHeight, maxWidth, aspectRatio: `${infoWidth}/${infoHeight}` }}\n                tabIndex={tooltipProps ? 0 : undefined}\n            >\n                {placeholder}\n\n                <div style={sizing}>\n                    {img}\n                    {gifLabel}\n                    {banner}\n                </div>\n\n                {/* HACK: This div fills out space while the image loads, to prevent scroll jumps */}\n                {!this.props.forExport && !this.state.imgLoaded && !placeholder && (\n                    <div style={{ height: maxHeight, width: maxWidth }} />\n                )}\n            </div>\n        );\n\n        if (tooltipProps) {\n            // We specify isTriggerInteractive=true and make the div interactive manually as a workaround for\n            // https://github.com/element-hq/compound/issues/294\n            thumbnail = (\n                <Tooltip {...tooltipProps} isTriggerInteractive={true}>\n                    {thumbnail}\n                </Tooltip>\n            );\n        }\n\n        return this.wrapImage(contentUrl, thumbnail);\n    }\n\n    // Overridden by MStickerBody\n    protected wrapImage(contentUrl: string | null | undefined, children: JSX.Element): ReactNode {\n        if (contentUrl) {\n            return (\n                <a\n                    href={contentUrl}\n                    target={this.props.forExport ? \"_blank\" : undefined}\n                    onClick={this.onClick}\n                    onFocus={this.onFocus}\n                    onBlur={this.onBlur}\n                >\n                    {children}\n                </a>\n            );\n        }\n        return children;\n    }\n\n    // Overridden by MStickerBody\n    protected getPlaceholder(width: number, height: number): ReactNode {\n        const blurhash = this.props.mxEvent.getContent().info?.[BLURHASH_FIELD];\n\n        if (blurhash) {\n            if (this.state.placeholder === Placeholder.NoImage) {\n                return null;\n            } else if (this.state.placeholder === Placeholder.Blurhash) {\n                return <Blurhash className=\"mx_Blurhash\" hash={blurhash} width={width} height={height} />;\n            }\n        }\n        return <Spinner size={32} />;\n    }\n\n    // Overridden by MStickerBody\n    protected getTooltipProps(): ComponentProps<typeof Tooltip> | null {\n        return null;\n    }\n\n    // Overridden by MStickerBody\n    protected getFileBody(): ReactNode {\n        if (this.props.forExport) return null;\n        /*\n         * In the room timeline or the thread context we don't need the download\n         * link as the message action bar will fulfill that\n         */\n        const hasMessageActionBar =\n            this.context.timelineRenderingType === TimelineRenderingType.Room ||\n            this.context.timelineRenderingType === TimelineRenderingType.Pinned ||\n            this.context.timelineRenderingType === TimelineRenderingType.Search ||\n            this.context.timelineRenderingType === TimelineRenderingType.Thread ||\n            this.context.timelineRenderingType === TimelineRenderingType.ThreadsList;\n        if (!hasMessageActionBar) {\n            return <MFileBody {...this.props} showGenericPlaceholder={false} />;\n        }\n    }\n\n    public render(): React.ReactNode {\n        const content = this.props.mxEvent.getContent<ImageContent>();\n\n        // Fall back to MFileBody if we are unable to render this image e.g. in the case of a blob svg\n        if (\n            this.props.mediaEventHelper?.media.isEncrypted &&\n            !isMimeTypeAllowed(content.info?.mimetype ?? \"\") &&\n            !content.info?.thumbnail_info\n        ) {\n            return <MFileBody {...this.props} />;\n        }\n\n        if (this.state.error) {\n            let errorText = _t(\"timeline|m.image|error\");\n            if (this.state.error instanceof DecryptError) {\n                errorText = _t(\"timeline|m.image|error_decrypting\");\n            } else if (this.state.error instanceof DownloadError) {\n                errorText = _t(\"timeline|m.image|error_downloading\");\n            }\n\n            return (\n                <MediaProcessingError className=\"mx_MImageBody\" Icon={ImageErrorIcon}>\n                    {errorText}\n                </MediaProcessingError>\n            );\n        }\n\n        let contentUrl = this.state.contentUrl;\n        let thumbUrl: string | null;\n        if (this.props.forExport) {\n            contentUrl = this.props.mxEvent.getContent().url ?? this.props.mxEvent.getContent().file?.url;\n            thumbUrl = contentUrl;\n        } else if (this.state.isAnimated && SettingsStore.getValue(\"autoplayGifs\")) {\n            thumbUrl = contentUrl;\n        } else {\n            thumbUrl = this.state.thumbUrl ?? this.state.contentUrl;\n        }\n\n        const thumbnail = this.messageContent(contentUrl, thumbUrl, content);\n        const fileBody = this.getFileBody();\n\n        return (\n            <div className=\"mx_MImageBody\">\n                {thumbnail}\n                {fileBody}\n            </div>\n        );\n    }\n}\n\n// Wrap MImageBody component so we can use a hook here.\nconst MImageBody: React.FC<IBodyProps> = (props) => {\n    const [mediaVisible, setVisible] = useMediaVisible(props.mxEvent);\n    return <MImageBodyInner mediaVisible={mediaVisible} setMediaVisible={setVisible} {...props} />;\n};\n\nexport default MImageBody;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport {\n    type MatrixEvent,\n    type MatrixClient,\n    type Relations,\n    type Poll,\n    PollEvent,\n    M_POLL_KIND_DISCLOSED,\n    M_POLL_RESPONSE,\n    M_POLL_START,\n    type TimelineEvents,\n} from \"matrix-js-sdk/src/matrix\";\nimport { RelatedRelations } from \"matrix-js-sdk/src/models/related-relations\";\nimport { type PollStartEvent, type PollAnswerSubevent } from \"matrix-js-sdk/src/extensible_events_v1/PollStartEvent\";\nimport { PollResponseEvent } from \"matrix-js-sdk/src/extensible_events_v1/PollResponseEvent\";\nimport PollsIcon from \"@vector-im/compound-design-tokens/assets/web/icons/polls\";\nimport PollsEndIcon from \"@vector-im/compound-design-tokens/assets/web/icons/polls-end\";\n\nimport { _t } from \"../../../languageHandler\";\nimport Modal from \"../../../Modal\";\nimport { type IBodyProps } from \"./IBodyProps\";\nimport { formatList } from \"../../../utils/FormattingUtils\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport ErrorDialog from \"../dialogs/ErrorDialog\";\nimport { type GetRelationsForEvent } from \"../rooms/EventTile\";\nimport PollCreateDialog from \"../elements/PollCreateDialog\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport Spinner from \"../elements/Spinner\";\nimport { PollOption } from \"../polls/PollOption\";\n\ninterface IState {\n    poll?: Poll;\n    // poll instance has fetched at least one page of responses\n    pollInitialised: boolean;\n    selected?: string | null | undefined; // Which option was clicked by the local user\n    voteRelations?: Relations; // Voting (response) events\n}\n\nexport function createVoteRelations(getRelationsForEvent: GetRelationsForEvent, eventId: string): RelatedRelations {\n    const relationsList: Relations[] = [];\n\n    const pollResponseRelations = getRelationsForEvent(eventId, \"m.reference\", M_POLL_RESPONSE.name);\n    if (pollResponseRelations) {\n        relationsList.push(pollResponseRelations);\n    }\n\n    const pollResposnseAltRelations = getRelationsForEvent(eventId, \"m.reference\", M_POLL_RESPONSE.altName);\n    if (pollResposnseAltRelations) {\n        relationsList.push(pollResposnseAltRelations);\n    }\n\n    return new RelatedRelations(relationsList);\n}\n\nexport function findTopAnswer(pollEvent: MatrixEvent, voteRelations: Relations): string {\n    const pollEventId = pollEvent.getId();\n    if (!pollEventId) {\n        logger.warn(\n            \"findTopAnswer: Poll event needs an event ID to fetch relations in order to determine \" +\n                \"the top answer - assuming no best answer\",\n        );\n        return \"\";\n    }\n\n    const poll = pollEvent.unstableExtensibleEvent as PollStartEvent;\n    if (!poll?.isEquivalentTo(M_POLL_START)) {\n        logger.warn(\"Failed to parse poll to determine top answer - assuming no best answer\");\n        return \"\";\n    }\n\n    const findAnswerText = (answerId: string): string => {\n        return poll.answers.find((a) => a.id === answerId)?.text ?? \"\";\n    };\n\n    const userVotes: Map<string, UserVote> = collectUserVotes(allVotes(voteRelations));\n\n    const votes: Map<string, number> = countVotes(userVotes, poll);\n    const highestScore: number = Math.max(...votes.values());\n\n    const bestAnswerIds: string[] = [];\n    for (const [answerId, score] of votes) {\n        if (score == highestScore) {\n            bestAnswerIds.push(answerId);\n        }\n    }\n\n    const bestAnswerTexts = bestAnswerIds.map(findAnswerText);\n\n    return formatList(bestAnswerTexts, 3);\n}\n\nexport function isPollEnded(pollEvent: MatrixEvent, matrixClient: MatrixClient): boolean {\n    const room = matrixClient.getRoom(pollEvent.getRoomId());\n    const poll = room?.polls.get(pollEvent.getId()!);\n    if (!poll || poll.isFetchingResponses) {\n        return false;\n    }\n    return poll.isEnded;\n}\n\nexport function pollAlreadyHasVotes(mxEvent: MatrixEvent, getRelationsForEvent?: GetRelationsForEvent): boolean {\n    if (!getRelationsForEvent) return false;\n\n    const eventId = mxEvent.getId();\n    if (!eventId) return false;\n\n    const voteRelations = createVoteRelations(getRelationsForEvent, eventId);\n    return voteRelations.getRelations().length > 0;\n}\n\nexport function launchPollEditor(mxEvent: MatrixEvent, getRelationsForEvent?: GetRelationsForEvent): void {\n    const room = MatrixClientPeg.safeGet().getRoom(mxEvent.getRoomId());\n    if (pollAlreadyHasVotes(mxEvent, getRelationsForEvent)) {\n        Modal.createDialog(ErrorDialog, {\n            title: _t(\"poll|unable_edit_title\"),\n            description: _t(\"poll|unable_edit_description\"),\n        });\n    } else if (room) {\n        Modal.createDialog(\n            PollCreateDialog,\n            {\n                room,\n                threadId: mxEvent.getThread()?.id,\n                editingMxEvent: mxEvent,\n            },\n            \"mx_CompoundDialog\",\n            false, // isPriorityModal\n            true, // isStaticModal\n        );\n    }\n}\n\nexport default class MPollBody extends React.Component<IBodyProps, IState> {\n    public static contextType = MatrixClientContext;\n    declare public context: React.ContextType<typeof MatrixClientContext>;\n    private seenEventIds: string[] = []; // Events we have already seen\n\n    public constructor(props: IBodyProps) {\n        super(props);\n\n        this.state = {\n            selected: null,\n            pollInitialised: false,\n        };\n    }\n\n    public componentDidMount(): void {\n        const room = this.context?.getRoom(this.props.mxEvent.getRoomId());\n        const poll = room?.polls.get(this.props.mxEvent.getId()!);\n        if (poll) {\n            this.setPollInstance(poll);\n        } else {\n            room?.on(PollEvent.New, this.setPollInstance.bind(this));\n        }\n    }\n\n    public componentWillUnmount(): void {\n        this.removeListeners();\n    }\n\n    private async setPollInstance(poll: Poll): Promise<void> {\n        if (poll.pollId !== this.props.mxEvent.getId()) {\n            return;\n        }\n        this.setState({ poll }, () => {\n            this.addListeners();\n        });\n        const responses = await poll.getResponses();\n        const voteRelations = responses;\n\n        this.setState({ pollInitialised: true, voteRelations });\n    }\n\n    private addListeners(): void {\n        this.state.poll?.on(PollEvent.Responses, this.onResponsesChange);\n        this.state.poll?.on(PollEvent.End, this.onRelationsChange);\n        this.state.poll?.on(PollEvent.UndecryptableRelations, this.render.bind(this));\n    }\n\n    private removeListeners(): void {\n        if (this.state.poll) {\n            this.state.poll.off(PollEvent.Responses, this.onResponsesChange);\n            this.state.poll.off(PollEvent.End, this.onRelationsChange);\n            this.state.poll.off(PollEvent.UndecryptableRelations, this.render.bind(this));\n        }\n    }\n\n    private onResponsesChange = (responses: Relations): void => {\n        this.setState({ voteRelations: responses });\n        this.onRelationsChange();\n    };\n\n    private onRelationsChange = (): void => {\n        // We hold Relations in our state, and they changed under us.\n        // Check whether we should delete our selection, and then\n        // re-render.\n        // Note: re-rendering is a side effect of unselectIfNewEventFromMe().\n        this.unselectIfNewEventFromMe();\n    };\n\n    private selectOption(answerId: string): void {\n        if (this.state.poll?.isEnded) {\n            return;\n        }\n        const userVotes = this.collectUserVotes();\n        const userId = this.context.getSafeUserId();\n        const myVote = userVotes.get(userId)?.answers[0];\n        if (answerId === myVote) {\n            return;\n        }\n\n        const response = PollResponseEvent.from([answerId], this.props.mxEvent.getId()!).serialize();\n\n        this.context\n            .sendEvent(\n                this.props.mxEvent.getRoomId()!,\n                response.type as keyof TimelineEvents,\n                response.content as TimelineEvents[keyof TimelineEvents],\n            )\n            .catch((e: any) => {\n                console.error(\"Failed to submit poll response event:\", e);\n\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"poll|error_voting_title\"),\n                    description: _t(\"poll|error_voting_description\"),\n                });\n            });\n\n        this.setState({ selected: answerId });\n    }\n\n    /**\n     * @returns userId -> UserVote\n     */\n    private collectUserVotes(): Map<string, UserVote> {\n        if (!this.state.voteRelations || !this.context) {\n            return new Map<string, UserVote>();\n        }\n        return collectUserVotes(allVotes(this.state.voteRelations), this.context.getUserId(), this.state.selected);\n    }\n\n    /**\n     * If we've just received a new event that we hadn't seen\n     * before, and that event is me voting (e.g. from a different\n     * device) then forget when the local user selected.\n     *\n     * Either way, calls setState to update our list of events we\n     * have already seen.\n     */\n    private unselectIfNewEventFromMe(): void {\n        const relations = this.state.voteRelations?.getRelations() || [];\n        const newEvents: MatrixEvent[] = relations.filter(\n            (mxEvent: MatrixEvent) => !this.seenEventIds.includes(mxEvent.getId()!),\n        );\n        let newSelected = this.state.selected;\n\n        if (newEvents.length > 0) {\n            for (const mxEvent of newEvents) {\n                if (mxEvent.getSender() === this.context.getUserId()) {\n                    newSelected = null;\n                }\n            }\n        }\n        const newEventIds = newEvents.map((mxEvent: MatrixEvent) => mxEvent.getId()!);\n        this.seenEventIds = this.seenEventIds.concat(newEventIds);\n        this.setState({ selected: newSelected });\n    }\n\n    private totalVotes(collectedVotes: Map<string, number>): number {\n        let sum = 0;\n        for (const v of collectedVotes.values()) {\n            sum += v;\n        }\n        return sum;\n    }\n\n    public render(): ReactNode {\n        const { poll, pollInitialised } = this.state;\n        if (!poll?.pollEvent) {\n            return null;\n        }\n\n        const pollEvent = poll.pollEvent;\n\n        const pollId = this.props.mxEvent.getId()!;\n        const isFetchingResponses = !pollInitialised || poll.isFetchingResponses;\n        const userVotes = this.collectUserVotes();\n        const votes = countVotes(userVotes, pollEvent);\n        const totalVotes = this.totalVotes(votes);\n        const winCount = Math.max(...votes.values());\n        const userId = this.context.getSafeUserId();\n        const myVote = userVotes?.get(userId)?.answers[0];\n        const disclosed = M_POLL_KIND_DISCLOSED.matches(pollEvent.kind.name);\n\n        // Disclosed: votes are hidden until I vote or the poll ends\n        // Undisclosed: votes are hidden until poll ends\n        const showResults = poll.isEnded || (disclosed && myVote !== undefined);\n\n        let totalText: string;\n        if (showResults && poll.undecryptableRelationsCount) {\n            totalText = _t(\"poll|total_decryption_errors\");\n        } else if (poll.isEnded) {\n            totalText = _t(\"right_panel|poll|final_result\", { count: totalVotes });\n        } else if (!disclosed) {\n            totalText = _t(\"poll|total_not_ended\");\n        } else if (myVote === undefined) {\n            if (totalVotes === 0) {\n                totalText = _t(\"poll|total_no_votes\");\n            } else {\n                totalText = _t(\"poll|total_n_votes\", { count: totalVotes });\n            }\n        } else {\n            totalText = _t(\"poll|total_n_votes_voted\", { count: totalVotes });\n        }\n\n        const editedSpan = this.props.mxEvent.replacingEvent() ? (\n            <span className=\"mx_MPollBody_edited\"> ({_t(\"common|edited\")})</span>\n        ) : null;\n\n        const PollIcon = poll.isEnded ? PollsEndIcon : PollsIcon;\n        const pollLabel = poll.isEnded ? _t(\"poll|ended_poll_label\") : _t(\"poll|poll_label\");\n\n        return (\n            <fieldset className=\"mx_MPollBody\">\n                <legend data-testid=\"pollQuestion\">\n                    <PollIcon width=\"20\" height=\"20\" aria-label={pollLabel} />\n                    {pollEvent.question.text}\n                    {editedSpan}\n                </legend>\n                <div className=\"mx_MPollBody_allOptions\">\n                    {pollEvent.answers.map((answer: PollAnswerSubevent, index: number) => {\n                        let answerVotes = 0;\n\n                        if (showResults) {\n                            answerVotes = votes.get(answer.id) ?? 0;\n                        }\n\n                        const checked =\n                            (!poll.isEnded && myVote === answer.id) || (poll.isEnded && answerVotes === winCount);\n\n                        return (\n                            <PollOption\n                                key={answer.id}\n                                pollId={pollId}\n                                answer={answer}\n                                optionNumber={index + 1}\n                                isChecked={checked}\n                                isEnded={poll.isEnded}\n                                voteCount={answerVotes}\n                                totalVoteCount={totalVotes}\n                                displayVoteCount={showResults}\n                                onOptionSelected={this.selectOption.bind(this)}\n                            />\n                        );\n                    })}\n                </div>\n                <div data-testid=\"totalVotes\" className=\"mx_MPollBody_totalVotes\">\n                    {totalText}\n                    {isFetchingResponses && <Spinner size={16} />}\n                </div>\n            </fieldset>\n        );\n    }\n}\nexport class UserVote {\n    public constructor(\n        public readonly ts: number,\n        public readonly sender: string,\n        public readonly answers: string[],\n    ) {}\n}\n\nfunction userResponseFromPollResponseEvent(event: MatrixEvent): UserVote {\n    const response = event.unstableExtensibleEvent as PollResponseEvent;\n    if (!response?.isEquivalentTo(M_POLL_RESPONSE)) {\n        throw new Error(\"Failed to parse Poll Response Event to determine user response\");\n    }\n\n    return new UserVote(event.getTs(), event.getSender()!, response.answerIds);\n}\n\nexport function allVotes(voteRelations: Relations): Array<UserVote> {\n    if (voteRelations) {\n        return voteRelations\n            .getRelations()\n            .filter((e) => !e.isRedacted())\n            .map(userResponseFromPollResponseEvent);\n    } else {\n        return [];\n    }\n}\n\n/**\n * Figure out the correct vote for each user.\n * @param userResponses current vote responses in the poll\n * @param {string?} userId The userId for which the `selected` option will apply to.\n *                  Should be set to the current user ID.\n * @param {string?} selected Local echo selected option for the userId\n * @returns a Map of user ID to their vote info\n */\nexport function collectUserVotes(\n    userResponses: Array<UserVote>,\n    userId?: string | null | undefined,\n    selected?: string | null | undefined,\n): Map<string, UserVote> {\n    const userVotes: Map<string, UserVote> = new Map();\n\n    for (const response of userResponses) {\n        const otherResponse = userVotes.get(response.sender);\n        if (!otherResponse || otherResponse.ts < response.ts) {\n            userVotes.set(response.sender, response);\n        }\n    }\n\n    if (selected && userId) {\n        userVotes.set(userId, new UserVote(0, userId, [selected]));\n    }\n\n    return userVotes;\n}\n\nexport function countVotes(userVotes: Map<string, UserVote>, pollStart: PollStartEvent): Map<string, number> {\n    const collected = new Map<string, number>();\n\n    for (const response of userVotes.values()) {\n        const tempResponse = PollResponseEvent.from(response.answers, \"$irrelevant\");\n        tempResponse.validateAgainst(pollStart);\n        if (!tempResponse.spoiled) {\n            for (const answerId of tempResponse.answerIds) {\n                if (collected.has(answerId)) {\n                    collected.set(answerId, collected.get(answerId)! + 1);\n                } else {\n                    collected.set(answerId, 1);\n                }\n            }\n        }\n    }\n\n    return collected;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021, 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EventType, type MatrixEvent, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { type Playback, PlaybackState } from \"./Playback\";\nimport { UPDATE_EVENT } from \"../stores/AsyncStore\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { arrayFastClone } from \"../utils/arrays\";\nimport { PlaybackManager } from \"./PlaybackManager\";\nimport { isVoiceMessage } from \"../utils/EventUtils\";\nimport { type RoomViewStore } from \"../stores/RoomViewStore\";\n\n/**\n * Audio playback queue management for a given room. This keeps track of where the user\n * was at for each playback, what order the playbacks were played in, and triggers subsequent\n * playbacks.\n *\n * Currently this is only intended to be used by voice messages.\n *\n * The primary mechanics are:\n * * Persisted clock state for each playback instance (tied to Event ID).\n * * Limited memory of playback order (see code; not persisted).\n * * Autoplay of next eligible playback instance.\n */\nexport class PlaybackQueue {\n    private static queues = new Map<string, PlaybackQueue>(); // keyed by room ID\n\n    private playbacks = new Map<string, Playback>(); // keyed by event ID\n    private clockStates = new Map<string, number>(); // keyed by event ID\n    private playbackIdOrder: string[] = []; // event IDs, last == current\n    private currentPlaybackId: string | null = null; // event ID, broken out from above for ease of use\n    private recentFullPlays = new Set<string>(); // event IDs\n\n    /**\n     * Create a PlaybackQueue for a given room.\n     * @param room The room\n     * @param roomViewStore The RoomViewStore instance\n     */\n    public constructor(\n        private room: Room,\n        private roomViewStore: RoomViewStore,\n    ) {\n        this.loadClocks();\n\n        this.roomViewStore.addRoomListener(this.room.roomId, (isActive) => {\n            if (!isActive) return;\n\n            // Reset the state of the playbacks before they start mounting and enqueuing updates.\n            // We reset the entirety of the queue, including order, to ensure the user isn't left\n            // confused with what order the messages are playing in.\n            this.currentPlaybackId = null; // this in particular stops autoplay when the room is switched to\n            this.recentFullPlays = new Set<string>();\n            this.playbackIdOrder = [];\n        });\n    }\n\n    /**\n     * Get the PlaybackQueue for a given room, creating it if necessary.\n     * @param roomId The ID of the room\n     * @param roomViewStore The RoomViewStore instance\n     * @returns The PlaybackQueue for the room\n     */\n    public static forRoom(roomId: string, roomViewStore: RoomViewStore): PlaybackQueue {\n        const cli = MatrixClientPeg.safeGet();\n        const room = cli.getRoom(roomId);\n        if (!room) throw new Error(\"Unknown room\");\n        if (PlaybackQueue.queues.has(room.roomId)) {\n            return PlaybackQueue.queues.get(room.roomId)!;\n        }\n        const queue = new PlaybackQueue(room, roomViewStore);\n        PlaybackQueue.queues.set(room.roomId, queue);\n        return queue;\n    }\n\n    private persistClocks(): void {\n        localStorage.setItem(\n            `mx_voice_message_clocks_${this.room.roomId}`,\n            JSON.stringify(Array.from(this.clockStates.entries())),\n        );\n    }\n\n    private loadClocks(): void {\n        const val = localStorage.getItem(`mx_voice_message_clocks_${this.room.roomId}`);\n        if (!!val) {\n            this.clockStates = new Map<string, number>(JSON.parse(val));\n            // Clean out any null values (from older versions)\n            for (const [key, value] of this.clockStates.entries()) {\n                if (value == null) {\n                    this.clockStates.delete(key);\n                }\n            }\n        }\n    }\n\n    public unsortedEnqueue(mxEvent: MatrixEvent, playback: Playback): void {\n        // We don't ever detach our listeners: we expect the Playback to clean up for us\n        this.playbacks.set(mxEvent.getId()!, playback);\n        playback.on(UPDATE_EVENT, (state) => this.onPlaybackStateChange(playback, mxEvent, state));\n        playback.clockInfo.liveData.onUpdate((clock) => this.onPlaybackClock(playback, mxEvent, clock));\n    }\n\n    private onPlaybackStateChange(playback: Playback, mxEvent: MatrixEvent, newState: PlaybackState): void {\n        // Remember where the user got to in playback\n        const wasLastPlaying = this.currentPlaybackId === mxEvent.getId();\n        const currentClockState = this.clockStates.get(mxEvent.getId()!);\n\n        if (newState === PlaybackState.Stopped && currentClockState !== undefined && !wasLastPlaying) {\n            // noinspection JSIgnoredPromiseFromCall\n            playback.skipTo(currentClockState);\n        } else if (newState === PlaybackState.Stopped) {\n            // Remove the now-useless clock for some space savings\n            this.clockStates.delete(mxEvent.getId()!);\n\n            if (wasLastPlaying && this.currentPlaybackId) {\n                this.recentFullPlays.add(this.currentPlaybackId);\n                const orderClone = arrayFastClone(this.playbackIdOrder);\n                const last = orderClone.pop();\n                if (last === this.currentPlaybackId) {\n                    const next = orderClone.pop();\n                    if (next) {\n                        const instance = this.playbacks.get(next);\n                        if (!instance) {\n                            logger.warn(\n                                \"Voice message queue desync: Missing playback for next message: \" +\n                                    `Current=${this.currentPlaybackId} Last=${last} Next=${next}`,\n                            );\n                        } else {\n                            this.playbackIdOrder = orderClone;\n                            PlaybackManager.instance.pauseAllExcept(instance);\n\n                            // This should cause a Play event, which will re-populate our playback order\n                            // and update our current playback ID.\n                            // noinspection JSIgnoredPromiseFromCall\n                            instance.play();\n                        }\n                    } else {\n                        // else no explicit next event, so find an event we haven't played that comes next. The live\n                        // timeline is already most recent last, so we can iterate down that.\n                        const timeline = arrayFastClone(this.room.getLiveTimeline().getEvents());\n                        let scanForVoiceMessage = false;\n                        let nextEv: MatrixEvent | undefined;\n                        for (const event of timeline) {\n                            if (event.getId() === mxEvent.getId()) {\n                                scanForVoiceMessage = true;\n                                continue;\n                            }\n                            if (!scanForVoiceMessage) continue;\n\n                            if (!isVoiceMessage(event)) {\n                                const evType = event.getType();\n                                if (evType !== EventType.RoomMessage && evType !== EventType.Sticker) {\n                                    continue; // Event can be skipped for automatic playback consideration\n                                }\n                                break; // Stop automatic playback: next useful event is not a voice message\n                            }\n\n                            const havePlayback = this.playbacks.has(event.getId()!);\n                            const isRecentlyCompleted = this.recentFullPlays.has(event.getId()!);\n                            if (havePlayback && !isRecentlyCompleted) {\n                                nextEv = event;\n                                break;\n                            }\n                        }\n                        if (!nextEv) {\n                            // if we don't have anywhere to go, reset the recent playback queue so the user\n                            // can start a new chain of playbacks.\n                            this.recentFullPlays = new Set<string>();\n                            this.playbackIdOrder = [];\n                        } else {\n                            this.playbackIdOrder = orderClone;\n\n                            const instance = this.playbacks.get(nextEv.getId()!);\n                            PlaybackManager.instance.pauseAllExcept(instance);\n\n                            // This should cause a Play event, which will re-populate our playback order\n                            // and update our current playback ID.\n                            // noinspection JSIgnoredPromiseFromCall\n                            instance?.play();\n                        }\n                    }\n                } else {\n                    logger.warn(\n                        \"Voice message queue desync: Expected playback stop to be last in order. \" +\n                            `Current=${this.currentPlaybackId} Last=${last} EventID=${mxEvent.getId()}`,\n                    );\n                }\n            }\n        }\n\n        if (newState === PlaybackState.Playing) {\n            const order = this.playbackIdOrder;\n            if (this.currentPlaybackId !== mxEvent.getId() && !!this.currentPlaybackId) {\n                if (order.length === 0 || order[order.length - 1] !== this.currentPlaybackId) {\n                    const lastInstance = this.playbacks.get(this.currentPlaybackId);\n                    if (\n                        lastInstance &&\n                        [PlaybackState.Playing, PlaybackState.Paused].includes(lastInstance.currentState)\n                    ) {\n                        order.push(this.currentPlaybackId);\n                    }\n                }\n            }\n\n            this.currentPlaybackId = mxEvent.getId()!;\n            if (order.length === 0 || order[order.length - 1] !== this.currentPlaybackId) {\n                order.push(this.currentPlaybackId);\n            }\n        }\n\n        // Only persist clock information on pause/stop (end) to avoid overwhelming the storage.\n        // This should get triggered from normal voice message component unmount due to the playback\n        // stopping itself for cleanup.\n        if (newState === PlaybackState.Paused || newState === PlaybackState.Stopped) {\n            this.persistClocks();\n        }\n    }\n\n    private onPlaybackClock(playback: Playback, mxEvent: MatrixEvent, clocks: number[]): void {\n        if (playback.currentState !== PlaybackState.Playing && playback.currentState !== PlaybackState.Paused) return; // ignore pre-ready values\n\n        this.clockStates.set(mxEvent.getId()!, clocks[0]); // [0] is the current seek position\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport InlineSpinner from \"../elements/InlineSpinner\";\nimport { _t } from \"../../../languageHandler\";\nimport RecordingPlayback from \"../audio_messages/RecordingPlayback\";\nimport MAudioBody from \"./MAudioBody\";\nimport MFileBody from \"./MFileBody\";\nimport MediaProcessingError from \"./shared/MediaProcessingError\";\nimport { isVoiceMessage } from \"../../../utils/EventUtils\";\nimport { PlaybackQueue } from \"../../../audio/PlaybackQueue\";\nimport { type Playback } from \"../../../audio/Playback\";\nimport RoomContext from \"../../../contexts/RoomContext\";\n\nexport default class MVoiceMessageBody extends MAudioBody {\n    public static contextType = RoomContext;\n    declare public context: React.ContextType<typeof RoomContext>;\n\n    protected onMount(playback: Playback): void {\n        if (isVoiceMessage(this.props.mxEvent)) {\n            PlaybackQueue.forRoom(this.props.mxEvent.getRoomId()!, this.context.roomViewStore).unsortedEnqueue(\n                this.props.mxEvent,\n                playback,\n            );\n        }\n    }\n\n    // A voice message is an audio file but rendered in a special way.\n    public render(): React.ReactNode {\n        if (this.state.error) {\n            return (\n                <MediaProcessingError className=\"mx_MVoiceMessageBody\">\n                    {_t(\"timeline|m.audio|error_processing_voice_message\")}\n                </MediaProcessingError>\n            );\n        }\n\n        if (!this.state.playback) {\n            return (\n                <span className=\"mx_MVoiceMessageBody\">\n                    <InlineSpinner />\n                </span>\n            );\n        }\n\n        // At this point we should have a playable state\n        return (\n            <span className=\"mx_MVoiceMessageBody\">\n                <RecordingPlayback playback={this.state.playback} />\n                {this.showFileBody && <MFileBody {...this.props} showGenericPlaceholder={false} />}\n            </span>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\n\nimport { type IBodyProps } from \"./IBodyProps\";\n\nexport default ({ mxEvent, ref }: IBodyProps): JSX.Element => {\n    const text = mxEvent.getContent().body;\n    return (\n        <div className=\"mx_UnknownBody\" ref={ref}>\n            {text}\n        </div>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n */\n\nimport React from \"react\";\n\nimport TextWithTooltip from \"./TextWithTooltip\";\n\ninterface IProps extends Omit<React.ComponentProps<typeof TextWithTooltip>, \"tabIndex\" | \"onClick\" | \"tooltip\"> {\n    tooltip: string;\n}\n\nexport default class LinkWithTooltip extends React.Component<IProps> {\n    public render(): React.ReactNode {\n        const { children, tooltip, ...props } = this.props;\n\n        return (\n            <TextWithTooltip\n                // Disable focusing on the tooltip target to avoid double / nested focus. The contained anchor element\n                // itself allows focusing which also triggers the tooltip.\n                tabIndex={-1}\n                tooltip={tooltip}\n                onClick={(e) => (e.target as HTMLElement).blur()} // Force tooltip to hide on clickout\n                {...props}\n            >\n                {children}\n            </TextWithTooltip>\n        );\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { type DOMNode, Element, type HTMLReactParserOptions, Text } from \"html-react-parser\";\nimport { type MatrixEvent, type Room } from \"matrix-js-sdk/src/matrix\";\n\n/**\n * The type of a parent node of an element, normally exported by domhandler but that is not a direct dependency of ours\n */\nexport type ParentNode = NonNullable<Element[\"parentNode\"]>;\n\n/**\n * Returns the text content of a node if it is the only child and that child is a text node\n * @param node - the node to check\n */\nexport const getSingleTextContentNode = (node: Element): string | null => {\n    if (node.childNodes.length === 1 && node.childNodes[0].type === \"text\") {\n        return node.childNodes[0].data;\n    }\n    return null;\n};\n\n/**\n * Returns true if the node has a parent that matches the given matcher\n * @param node - the node to check\n * @param matcher - a function that returns true if the node matches\n */\nexport const hasParentMatching = (node: Element, matcher: (node: ParentNode | null) => boolean): boolean => {\n    let parent = node.parentNode;\n    while (parent) {\n        if (matcher(parent)) return true;\n        parent = parent.parentNode;\n    }\n    return false;\n};\n\n/**\n * A replacer function that can be used with html-react-parser\n */\nexport type Replacer = HTMLReactParserOptions[\"replace\"];\n\n/**\n * Passes through any non-string inputs verbatim, as such they should only be used for emoji bodies\n */\nexport function applyReplacerOnString(\n    input: string | JSX.Element[],\n    replacer: Replacer,\n): JSX.Element | JSX.Element[] | string {\n    if (!replacer) return input;\n\n    const arr = Array.isArray(input) ? input : [input];\n    return arr.map((input, index): JSX.Element => {\n        if (typeof input === \"string\") {\n            return (\n                <React.Fragment key={index}>{(replacer(new Text(input), 0) as JSX.Element) || input}</React.Fragment>\n            );\n        }\n        return input;\n    });\n}\n\ninterface Parameters {\n    isHtml: boolean;\n    replace: Replacer;\n    // Required for keywordPillRenderer\n    keywordRegexpPattern?: RegExp;\n    // Required for mentionPillRenderer\n    mxEvent?: MatrixEvent;\n    room?: Room;\n    shouldShowPillAvatar?: boolean;\n}\n\ntype SpecialisedReplacer<T extends DOMNode> = (\n    node: T,\n    parameters: Parameters,\n    index: number,\n) => JSX.Element | string | void;\n\n/**\n * A map of replacer functions for different types of nodes/tags.\n * When a function returns a JSX element, the element will be rendered in place of the node.\n */\nexport type RendererMap = Partial<\n    {\n        [tagName in keyof HTMLElementTagNameMap]: SpecialisedReplacer<Element>;\n    } & {\n        [Node.TEXT_NODE]: SpecialisedReplacer<Text>;\n    }\n>;\n\ntype PreparedRenderer = (parameters: Omit<Parameters, \"replace\">) => Replacer;\n\n/**\n * Combines multiple renderers into a single Replacer function\n * @param renderers - the list of renderers to combine\n */\nexport const combineRenderers =\n    (...renderers: RendererMap[]): PreparedRenderer =>\n    (parameters) => {\n        const replace: Replacer = (node, index) => {\n            if (node.type === \"text\") {\n                for (const replacer of renderers) {\n                    const result = replacer[Node.TEXT_NODE]?.(node, parametersWithReplace, index);\n                    if (result) return result;\n                }\n            }\n            if (node instanceof Element) {\n                const tagName = node.tagName.toLowerCase() as keyof HTMLElementTagNameMap;\n                for (const replacer of renderers) {\n                    const result = replacer[tagName]?.(node, parametersWithReplace, index);\n                    if (result) return result;\n                }\n            }\n        };\n        const parametersWithReplace: Parameters = { ...parameters, replace };\n        return replace;\n    };\n","/*\nCopyright 2024-2025 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { domToReact } from \"html-react-parser\";\n\nimport LinkWithTooltip from \"../components/views/elements/LinkWithTooltip\";\nimport { getSingleTextContentNode, type RendererMap } from \"./utils.tsx\";\n\n/**\n * Wraps ambiguous links in a tooltip trigger that shows the full URL.\n */\nexport const ambiguousLinkTooltipRenderer: RendererMap = {\n    a: (anchor, { isHtml }) => {\n        // Ambiguous URLs are only possible in HTML content\n        if (!isHtml) return;\n\n        const href = anchor.attribs[\"href\"];\n        if (href && href !== getSingleTextContentNode(anchor)) {\n            let tooltip = href as string;\n            try {\n                tooltip = new URL(href, window.location.href).toString();\n            } catch {\n                // Not all hrefs will be valid URLs\n            }\n            return <LinkWithTooltip tooltip={tooltip}>{domToReact([anchor])}</LinkWithTooltip>;\n        }\n    },\n};\n","/*\nCopyright 2024-2025 New Vector Ltd.\nCopyright 2019-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { RuleId } from \"matrix-js-sdk/src/matrix\";\nimport { type Element } from \"html-react-parser\";\nimport { textContent } from \"domutils\";\nimport reactStringReplace from \"react-string-replace\";\nimport { PushProcessor } from \"matrix-js-sdk/src/pushprocessor\";\n\nimport { Pill, PillType } from \"../components/views/elements/Pill\";\nimport { parsePermalink } from \"../utils/permalinks/Permalinks\";\nimport { type PermalinkParts } from \"../utils/permalinks/PermalinkConstructor\";\nimport { hasParentMatching, type RendererMap, type ParentNode } from \"./utils.tsx\";\n\nconst AT_ROOM_REGEX = PushProcessor.getPushRuleGlobRegex(\"@room\", true, \"gmi\");\n\n/**\n * A node here is an A element with a href attribute tag.\n *\n * It should be pillified if the permalink parser returns a result and one of the following conditions match:\n * - Text content equals href. This is the case when sending a plain permalink inside a message.\n * - The link is not from linkify (isHtml=true).\n *   Composer completions already create an A tag.\n */\nconst shouldBePillified = (node: Element, href: string, parts: PermalinkParts | null, isHtml: boolean): boolean => {\n    // permalink parser didn't return any parts\n    if (!parts) return false;\n\n    const text = textContent(node);\n\n    // event permalink with custom label\n    if (parts.eventId && href !== text) return false;\n\n    return href === text || isHtml;\n};\n\nconst isPreCode = (domNode: ParentNode | null): boolean =>\n    (domNode as Element)?.tagName === \"PRE\" || (domNode as Element)?.tagName === \"CODE\";\n\n/**\n * Marks the text that activated a push-notification mention pattern.\n */\nexport const mentionPillRenderer: RendererMap = {\n    a: (anchor, { room, shouldShowPillAvatar, isHtml }) => {\n        if (!room) return;\n\n        const href = anchor.attribs[\"href\"];\n        if (\n            href &&\n            !hasParentMatching(anchor, isPreCode) &&\n            shouldBePillified(anchor, href, parsePermalink(href), isHtml)\n        ) {\n            return <Pill url={href} inMessage={true} room={room} shouldShowPillAvatar={shouldShowPillAvatar} />;\n        }\n    },\n\n    [Node.TEXT_NODE]: (text, { room, mxEvent, shouldShowPillAvatar }) => {\n        if (!room || !mxEvent) return;\n\n        const atRoomRule = room.client.pushProcessor.getPushRuleById(\n            mxEvent.getContent()[\"m.mentions\"] !== undefined ? RuleId.IsRoomMention : RuleId.AtRoomNotification,\n        );\n        if (atRoomRule && room.client.pushProcessor.ruleMatchesEvent(atRoomRule, mxEvent)) {\n            const parts = reactStringReplace(text.data, AT_ROOM_REGEX, (_match, i) => (\n                <Pill\n                    key={i}\n                    type={PillType.AtRoomMention}\n                    inMessage={true}\n                    room={room}\n                    shouldShowPillAvatar={shouldShowPillAvatar}\n                />\n            ));\n\n            if (parts.length <= 1) return; // no matches, skip replacing\n\n            return <>{parts}</>;\n        }\n    },\n};\n\n/**\n * Marks the text that activated a push-notification keyword pattern.\n */\nexport const keywordPillRenderer: RendererMap = {\n    [Node.TEXT_NODE]: (text, { keywordRegexpPattern }) => {\n        if (!keywordRegexpPattern) return;\n\n        const parts = reactStringReplace(text.data, keywordRegexpPattern, (match, i) => (\n            <Pill key={i} text={match} type={PillType.Keyword} />\n        ));\n\n        if (parts.length <= 1) return; // no matches, skip replacing\n\n        return <>{parts}</>;\n    },\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 Sorunome\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n */\n\nimport React, { type ReactNode } from \"react\";\n\ninterface IProps {\n    reason?: string;\n    children: ReactNode;\n}\n\ninterface IState {\n    visible: boolean;\n}\n\nexport default class Spoiler extends React.Component<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n        this.state = {\n            visible: false,\n        };\n    }\n\n    private toggleVisible = (e: React.MouseEvent): void => {\n        if (!this.state.visible) {\n            // we are un-blurring, we don't want this click to propagate to potential child pills\n            e.preventDefault();\n            e.stopPropagation();\n        }\n        this.setState({ visible: !this.state.visible });\n    };\n\n    public render(): React.ReactNode {\n        const reason = this.props.reason ? (\n            <span className=\"mx_EventTile_spoiler_reason\">{\"(\" + this.props.reason + \")\"}</span>\n        ) : null;\n        return (\n            <button\n                className={\"mx_EventTile_spoiler\" + (this.state.visible ? \" visible\" : \"\")}\n                onClick={this.toggleVisible}\n            >\n                {reason}\n                &nbsp;\n                <span className=\"mx_EventTile_spoiler_content\">{this.props.children}</span>\n            </button>\n        );\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { domToReact, type DOMNode } from \"html-react-parser\";\n\nimport { type RendererMap } from \"./utils.tsx\";\nimport Spoiler from \"../components/views/elements/Spoiler.tsx\";\n\n/**\n * Replaces spans with `data-mx-spoiler` with a Spoiler component.\n */\nexport const spoilerRenderer: RendererMap = {\n    span: (span, params) => {\n        const reason = span.attribs[\"data-mx-spoiler\"];\n        if (typeof reason === \"string\") {\n            return (\n                <Spoiler reason={reason}>{domToReact(span.children as DOMNode[], { replace: params.replace })}</Spoiler>\n            );\n        }\n    },\n};\n","/*\nCopyright 2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useState } from \"react\";\nimport classNames from \"classnames\";\nimport { type DOMNode, Element as ParserElement, domToReact } from \"html-react-parser\";\nimport { textContent, getInnerHTML } from \"domutils\";\nimport { CollapseIcon, CopyIcon, ExpandIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { useSettingValue } from \"../../../hooks/useSettings.ts\";\nimport { CopyTextButton } from \"../elements/CopyableText.tsx\";\n\nconst MAX_HIGHLIGHT_LENGTH = 4096;\nconst MAX_LINES_BEFORE_COLLAPSE = 5;\n\ninterface Props {\n    preNode: ParserElement;\n}\n\nconst ExpandCollapseButton: React.FC<{\n    expanded: boolean;\n    onClick(): void;\n}> = ({ expanded, onClick }) => {\n    return (\n        <span className=\"mx_EventTile_button\" onClick={onClick}>\n            {expanded ? <CollapseIcon /> : <ExpandIcon />}\n        </span>\n    );\n};\n\nconst CodeBlock: React.FC<Props> = ({ preNode }) => {\n    const enableSyntaxHighlightLanguageDetection = useSettingValue(\"enableSyntaxHighlightLanguageDetection\");\n    const showCodeLineNumbers = useSettingValue(\"showCodeLineNumbers\");\n    const expandCodeByDefault = useSettingValue(\"expandCodeByDefault\");\n    const [expanded, setExpanded] = useState(expandCodeByDefault);\n\n    const text = textContent(preNode);\n\n    let expandCollapseButton: JSX.Element | undefined;\n    if (text.split(\"\\n\").length >= MAX_LINES_BEFORE_COLLAPSE) {\n        expandCollapseButton = (\n            <ExpandCollapseButton\n                expanded={expanded}\n                onClick={() => {\n                    setExpanded(!expanded);\n                }}\n            />\n        );\n    }\n\n    const innerHTML = getInnerHTML(preNode);\n    let lineNumbers: JSX.Element | undefined;\n    if (showCodeLineNumbers) {\n        // Calculate number of lines in pre\n        const number = innerHTML.replace(/\\n(<\\/code>)?$/, \"\").split(/\\n/).length;\n        // Iterate through lines starting with 1 (number of the first line is 1)\n        lineNumbers = (\n            <span className=\"mx_EventTile_lineNumbers\">\n                {Array.from({ length: number }, (_, i) => i + 1).map((i) => (\n                    <span key={i}>{i}</span>\n                ))}\n            </span>\n        );\n    }\n\n    async function highlightCode(div: HTMLElement | null): Promise<void> {\n        const code = div?.getElementsByTagName(\"code\")[0];\n        if (!code) return;\n        const { default: highlight } = await import(\"highlight.js\");\n\n        if (code.textContent && code.textContent.length > MAX_HIGHLIGHT_LENGTH) {\n            console.log(\n                `Code block is bigger than highlight limit (${code.textContent.length} > ${MAX_HIGHLIGHT_LENGTH}): not highlighting`,\n            );\n            return;\n        }\n\n        let advertisedLang: string | undefined;\n        for (const cl of code.className.split(/\\s+/)) {\n            if (cl.startsWith(\"language-\")) {\n                const maybeLang = cl.split(\"-\", 2)[1];\n                if (highlight.getLanguage(maybeLang)) {\n                    advertisedLang = maybeLang;\n                    break;\n                }\n            }\n        }\n\n        if (advertisedLang) {\n            // If the code says what language it is, highlight it in that language\n            // We don't use highlightElement here because we can't force language detection\n            // off. It should use the one we've found in the CSS class but we'd rather pass\n            // it in explicitly to make sure.\n            code.innerHTML = highlight.highlight(code.textContent ?? \"\", { language: advertisedLang }).value;\n        } else if (enableSyntaxHighlightLanguageDetection) {\n            // User has language detection enabled, so highlight the block with auto-highlighting enabled.\n            // We pass highlightjs the text to highlight rather than letting it\n            // work on the DOM with highlightElement because that also adds CSS\n            // classes to the pre/code element that we don't want (the CSS\n            // conflicts with our own).\n            code.innerHTML = highlight.highlightAuto(code.textContent ?? \"\").value;\n        }\n    }\n\n    function highlightCodeRef(div: HTMLElement | null): void {\n        highlightCode(div);\n    }\n\n    let content = domToReact(preNode.children as DOMNode[]);\n\n    // Add code element if it's missing since we depend on it\n    if (!preNode.children.some((child) => child instanceof ParserElement && child.tagName.toUpperCase() === \"CODE\")) {\n        content = <code>{content}</code>;\n    }\n\n    return (\n        <div className=\"mx_EventTile_pre_container\">\n            <pre\n                className={classNames({\n                    mx_EventTile_collapsedCodeBlock: !expanded,\n                })}\n            >\n                {lineNumbers}\n                <div style={{ display: \"contents\" }} ref={highlightCodeRef}>\n                    {content}\n                </div>\n            </pre>\n            {expandCollapseButton}\n            <CopyTextButton\n                getTextToCopy={() => text}\n                className={classNames(\"mx_EventTile_button mx_EventTile_copyButton\", {\n                    mx_EventTile_buttonBottom: !!expandCollapseButton,\n                })}\n            >\n                <CopyIcon />\n            </CopyTextButton>\n        </div>\n    );\n};\n\nexport default CodeBlock;\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { type RendererMap } from \"./utils.tsx\";\nimport CodeBlock from \"../components/views/messages/CodeBlock.tsx\";\n\n/**\n * Replaces `pre` elements with a CodeBlock component\n */\nexport const codeBlockRenderer: RendererMap = {\n    pre: (pre) => {\n        return <CodeBlock preNode={pre} />;\n    },\n};\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { memo, useContext, useMemo, type Ref } from \"react\";\nimport { type IContent, type MatrixEvent, MsgType, PushRuleKind } from \"matrix-js-sdk/src/matrix\";\nimport parse from \"html-react-parser\";\nimport { PushProcessor } from \"matrix-js-sdk/src/pushprocessor\";\n\nimport { bodyToNode } from \"../../../HtmlUtils.tsx\";\nimport PlatformPeg from \"../../../PlatformPeg.ts\";\nimport {\n    applyReplacerOnString,\n    combineRenderers,\n    type Replacer,\n    type RendererMap,\n    keywordPillRenderer,\n    mentionPillRenderer,\n    ambiguousLinkTooltipRenderer,\n    codeBlockRenderer,\n    spoilerRenderer,\n} from \"../../../renderer\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext.tsx\";\nimport { useSettingValue } from \"../../../hooks/useSettings.ts\";\nimport { filterBoolean } from \"../../../utils/arrays.ts\";\nimport { useMediaVisible } from \"../../../hooks/useMediaVisible.ts\";\n\n/**\n * Returns a RegExp pattern for the keyword in the push rule of the given Matrix event, if any\n * @param mxEvent - the Matrix event to get the push rule keyword pattern from\n */\nconst getPushDetailsKeywordPatternRegexp = (mxEvent: MatrixEvent): RegExp | undefined => {\n    const pushDetails = mxEvent.getPushDetails();\n    if (\n        pushDetails.rule?.enabled &&\n        pushDetails.rule.kind === PushRuleKind.ContentSpecific &&\n        pushDetails.rule.pattern\n    ) {\n        return PushProcessor.getPushRuleGlobRegex(pushDetails.rule.pattern, true, \"gi\");\n    }\n    return undefined;\n};\n\ninterface ReplacerOptions {\n    /**\n     * Whether to render room/user mentions as pills\n     */\n    renderMentionPills?: boolean;\n    /**\n     * Whether to render push rule keywords as pills\n     */\n    renderKeywordPills?: boolean;\n    /**\n     * Whether to render spoilers as hidden content revealed on click\n     */\n    renderSpoilers?: boolean;\n    /**\n     * Whether to render code blocks as syntax highlighted code with a copy to clipboard button\n     */\n    renderCodeBlocks?: boolean;\n    /**\n     * Whether to render tooltips for ambiguous links, only effective on platforms which specify `needsUrlTooltips` true\n     */\n    renderTooltipsForAmbiguousLinks?: boolean;\n}\n\n// Returns a memoized Replacer based on the input parameters\nconst useReplacer = (content: IContent, mxEvent: MatrixEvent | undefined, options: ReplacerOptions): Replacer => {\n    const cli = useContext(MatrixClientContext);\n    const room = cli.getRoom(mxEvent?.getRoomId()) ?? undefined;\n\n    const shouldShowPillAvatar = useSettingValue(\"Pill.shouldShowPillAvatar\");\n    const isHtml = content.format === \"org.matrix.custom.html\";\n\n    const replacer = useMemo(() => {\n        const keywordRegexpPattern = mxEvent ? getPushDetailsKeywordPatternRegexp(mxEvent) : undefined;\n        const replacers = filterBoolean<RendererMap>([\n            options.renderMentionPills ? mentionPillRenderer : undefined,\n            options.renderKeywordPills && keywordRegexpPattern ? keywordPillRenderer : undefined,\n            options.renderTooltipsForAmbiguousLinks && PlatformPeg.get()?.needsUrlTooltips()\n                ? ambiguousLinkTooltipRenderer\n                : undefined,\n            options.renderSpoilers ? spoilerRenderer : undefined,\n            options.renderCodeBlocks ? codeBlockRenderer : undefined,\n        ]);\n        return combineRenderers(...replacers)({\n            isHtml,\n            mxEvent,\n            room,\n            shouldShowPillAvatar,\n            keywordRegexpPattern,\n        });\n    }, [\n        mxEvent,\n        options.renderMentionPills,\n        options.renderKeywordPills,\n        options.renderTooltipsForAmbiguousLinks,\n        options.renderSpoilers,\n        options.renderCodeBlocks,\n        isHtml,\n        room,\n        shouldShowPillAvatar,\n    ]);\n\n    return replacer;\n};\n\ninterface Props extends ReplacerOptions {\n    /**\n     * Whether to render the content in a div or span\n     */\n    as: \"span\" | \"div\";\n    /**\n     * Whether to render links as clickable anchors\n     */\n    linkify: boolean;\n    /**\n     * The Matrix event to render, required for renderMentionPills & renderKeywordPills\n     */\n    mxEvent?: MatrixEvent;\n    /**\n     * The content to render\n     */\n    content: IContent;\n    /**\n     * Whether to strip reply fallbacks from the content before rendering\n     */\n    stripReply?: boolean;\n    /**\n     * Highlights to emphasise in the content\n     */\n    highlights?: string[];\n    /**\n     * Whether to include the `dir=\"auto\"` attribute on the rendered element\n     */\n    includeDir?: boolean;\n    ref?: Ref<HTMLElement>;\n}\n\n/**\n * Component to render a Matrix event's content body.\n * If the content is formatted HTML then it will be sanitised before rendering.\n * A number of rendering features are supported as configured by {@link ReplacerOptions}\n * Returns a div or span depending on `as`, the `dir` on a `div` is always set to `\"auto\"` but set by `includeDir` otherwise.\n */\nconst EventContentBody = memo(\n    ({ as, mxEvent, stripReply, content, linkify, highlights, includeDir = true, ref, ...options }: Props) => {\n        const enableBigEmoji = useSettingValue(\"TextualBody.enableBigEmoji\");\n        const [mediaIsVisible] = useMediaVisible(mxEvent);\n\n        const replacer = useReplacer(content, mxEvent, options);\n\n        const isEmote = content.msgtype === MsgType.Emote;\n\n        const { strippedBody, formattedBody, emojiBodyElements, className } = useMemo(\n            () =>\n                bodyToNode(content, highlights, {\n                    disableBigEmoji: isEmote || !enableBigEmoji,\n                    // Part of Replies fallback support\n                    stripReplyFallback: stripReply,\n                    mediaIsVisible,\n                    linkify,\n                }),\n            [content, mediaIsVisible, enableBigEmoji, highlights, isEmote, stripReply, linkify],\n        );\n\n        if (as === \"div\") includeDir = true; // force dir=\"auto\" on divs\n\n        const As = as;\n        const body = formattedBody ? (\n            <As ref={ref as any} className={className} dir={includeDir ? \"auto\" : undefined}>\n                {parse(formattedBody, {\n                    replace: replacer,\n                })}\n            </As>\n        ) : (\n            <As ref={ref as any} className={className} dir={includeDir ? \"auto\" : undefined}>\n                {applyReplacerOnString(emojiBodyElements || strippedBody, replacer)}\n            </As>\n        );\n\n        return body;\n    },\n);\n\nexport default EventContentBody;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 , 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport classNames from \"classnames\";\nimport DiffMatchPatch from \"diff-match-patch\";\nimport { DiffDOM, type IDiff } from \"diff-dom\";\nimport { type IContent } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { unescape } from \"lodash\";\n\nimport { bodyToHtml, checkBlockNode, type EventRenderOpts } from \"../HtmlUtils\";\n\nfunction textToHtml(text: string): string {\n    const container = document.createElement(\"div\");\n    container.textContent = text;\n    return container.innerHTML;\n}\n\nfunction getSanitizedHtmlBody(content: IContent): string {\n    const opts: EventRenderOpts = {\n        stripReplyFallback: true,\n    };\n    if (content.format === \"org.matrix.custom.html\") {\n        return bodyToHtml(content, undefined, opts);\n    } else {\n        // convert the string to something that can be safely\n        // embedded in an html document, e.g. use html entities where needed\n        // This is also needed so that DiffDOM wouldn't interpret something\n        // as a tag when somebody types e.g. \"</sarcasm>\"\n\n        // as opposed to bodyToHtml, here we also render\n        // text messages with dangerouslySetInnerHTML, to unify\n        // the code paths and because we need html to show differences\n        return textToHtml(bodyToHtml(content, undefined, opts));\n    }\n}\n\nfunction wrapInsertion(child: Node): HTMLElement {\n    const wrapper = document.createElement(checkBlockNode(child) ? \"div\" : \"span\");\n    wrapper.className = \"mx_EditHistoryMessage_insertion\";\n    wrapper.appendChild(child);\n    return wrapper;\n}\n\nfunction wrapDeletion(child: Node): HTMLElement {\n    const wrapper = document.createElement(checkBlockNode(child) ? \"div\" : \"span\");\n    wrapper.className = \"mx_EditHistoryMessage_deletion\";\n    wrapper.appendChild(child);\n    return wrapper;\n}\n\nfunction findRefNodes(\n    root: Node,\n    route: number[],\n    isAddition = false,\n): {\n    refNode: Node | undefined;\n    refParentNode: Node | undefined;\n} {\n    let refNode: Node | undefined = root;\n    let refParentNode: Node | undefined;\n    const end = isAddition ? route.length - 1 : route.length;\n    for (let i = 0; i < end; ++i) {\n        refParentNode = refNode;\n        refNode = refNode?.childNodes[route[i]!];\n    }\n    return { refNode, refParentNode };\n}\n\nfunction isTextNode(node: Text | HTMLElement): node is Text {\n    return node.nodeName === \"#text\";\n}\n\nfunction diffTreeToDOM(desc: Text | HTMLElement): Node {\n    if (isTextNode(desc)) {\n        return stringAsTextNode(desc.data);\n    } else {\n        const node = document.createElement(desc.nodeName);\n        for (const [key, value] of Object.entries(desc.attributes)) {\n            node.setAttribute(key, value.value);\n        }\n        if (desc.childNodes) {\n            for (const childDesc of desc.childNodes) {\n                node.appendChild(diffTreeToDOM(childDesc as Text | HTMLElement));\n            }\n        }\n        return node;\n    }\n}\n\nfunction insertBefore(parent: Node, nextSibling: Node | undefined, child: Node): void {\n    if (nextSibling) {\n        parent.insertBefore(child, nextSibling);\n    } else {\n        parent.appendChild(child);\n    }\n}\n\nfunction isRouteOfNextSibling(route1: number[], route2: number[]): boolean {\n    // routes are arrays with indices,\n    // to be interpreted as a path in the dom tree\n\n    // ensure same parent\n    for (let i = 0; i < route1.length - 1; ++i) {\n        if (route1[i] !== route2[i]) {\n            return false;\n        }\n    }\n    // the route2 is only affected by the diff of route1\n    // inserting an element if the index at the level of the\n    // last element of route1 being larger\n    // (e.g. coming behind route1 at that level)\n    const lastD1Idx = route1.length - 1;\n    return route2[lastD1Idx]! >= route1[lastD1Idx]!;\n}\n\nfunction adjustRoutes(diff: IDiff, remainingDiffs: IDiff[]): void {\n    if (diff.action === \"removeTextElement\" || diff.action === \"removeElement\") {\n        // as removed text is not removed from the html, but marked as deleted,\n        // we need to readjust indices that assume the current node has been removed.\n        const advance = 1;\n        for (const rd of remainingDiffs) {\n            if (isRouteOfNextSibling(diff.route, rd.route)) {\n                rd.route[diff.route.length - 1] += advance;\n            }\n        }\n    }\n}\n\nfunction stringAsTextNode(string: string): Text {\n    return document.createTextNode(unescape(string));\n}\n\nfunction renderDifferenceInDOM(originalRootNode: Node, diff: IDiff, diffMathPatch: DiffMatchPatch): void {\n    const { refNode, refParentNode } = findRefNodes(originalRootNode, diff.route);\n\n    switch (diff.action) {\n        case \"replaceElement\": {\n            if (!refNode) {\n                console.warn(\"Unable to apply replaceElement operation due to missing node\");\n                return;\n            }\n            const container = document.createElement(\"span\");\n            const delNode = wrapDeletion(diffTreeToDOM(diff.oldValue as HTMLElement));\n            const insNode = wrapInsertion(diffTreeToDOM(diff.newValue as HTMLElement));\n            container.appendChild(delNode);\n            container.appendChild(insNode);\n            refNode.parentNode!.replaceChild(container, refNode);\n            break;\n        }\n        case \"removeTextElement\": {\n            if (!refNode) {\n                console.warn(\"Unable to apply removeTextElement operation due to missing node\");\n                return;\n            }\n            const delNode = wrapDeletion(stringAsTextNode(diff.value as string));\n            refNode.parentNode!.replaceChild(delNode, refNode);\n            break;\n        }\n        case \"removeElement\": {\n            if (!refNode) {\n                console.warn(\"Unable to apply removeElement operation due to missing node\");\n                return;\n            }\n            const delNode = wrapDeletion(diffTreeToDOM(diff.element as HTMLElement));\n            refNode.parentNode!.replaceChild(delNode, refNode);\n            break;\n        }\n        case \"modifyTextElement\": {\n            if (!refNode) {\n                console.warn(\"Unable to apply modifyTextElement operation due to missing node\");\n                return;\n            }\n            const textDiffs = diffMathPatch.diff_main(diff.oldValue as string, diff.newValue as string);\n            diffMathPatch.diff_cleanupSemantic(textDiffs);\n            const container = document.createElement(\"span\");\n            for (const [modifier, text] of textDiffs) {\n                let textDiffNode: Node = stringAsTextNode(text);\n                if (modifier < 0) {\n                    textDiffNode = wrapDeletion(textDiffNode);\n                } else if (modifier > 0) {\n                    textDiffNode = wrapInsertion(textDiffNode);\n                }\n                container.appendChild(textDiffNode);\n            }\n            refNode.parentNode!.replaceChild(container, refNode);\n            break;\n        }\n        case \"addElement\": {\n            if (!refParentNode) {\n                console.warn(\"Unable to apply addElement operation due to missing node\");\n                return;\n            }\n            const insNode = wrapInsertion(diffTreeToDOM(diff.element as HTMLElement));\n            insertBefore(refParentNode, refNode, insNode);\n            break;\n        }\n        case \"addTextElement\": {\n            if (!refParentNode) {\n                console.warn(\"Unable to apply addTextElement operation due to missing node\");\n                return;\n            }\n            // XXX: sometimes diffDOM says insert a newline when there shouldn't be one\n            // but we must insert the node anyway so that we don't break the route child IDs.\n            // See https://github.com/fiduswriter/diffDOM/issues/100\n            const insNode = wrapInsertion(stringAsTextNode(diff.value !== \"\\n\" ? (diff.value as string) : \"\"));\n            insertBefore(refParentNode, refNode, insNode);\n            break;\n        }\n        // e.g. when changing a the href of a link,\n        // show the link with old href as removed and with the new href as added\n        case \"removeAttribute\":\n        case \"addAttribute\":\n        case \"modifyAttribute\": {\n            if (!refNode) {\n                console.warn(`Unable to apply ${diff.action} operation due to missing node`);\n                return;\n            }\n            const delNode = wrapDeletion(refNode.cloneNode(true));\n            const updatedNode = refNode.cloneNode(true) as HTMLElement;\n            if (diff.action === \"addAttribute\" || diff.action === \"modifyAttribute\") {\n                updatedNode.setAttribute(diff.name, diff.newValue as string);\n            } else {\n                updatedNode.removeAttribute(diff.name);\n            }\n            const insNode = wrapInsertion(updatedNode);\n            const container = document.createElement(checkBlockNode(refNode) ? \"div\" : \"span\");\n            container.appendChild(delNode);\n            container.appendChild(insNode);\n            refNode.parentNode!.replaceChild(container, refNode);\n            break;\n        }\n        default:\n            // Should not happen (modifyComment, ???)\n            logger.warn(\"MessageDiffUtils::editBodyDiffToHtml: diff action not supported atm\", diff);\n    }\n}\n\n/**\n * Renders a message with the changes made in an edit shown visually.\n * @param {IContent} originalContent the content for the base message\n * @param {IContent} editContent the content for the edit message\n * @return {JSX.Element} a react element similar to what `bodyToHtml` returns\n */\nexport function editBodyDiffToHtml(originalContent: IContent, editContent: IContent): JSX.Element {\n    // wrap the body in a div, DiffDOM needs a root element\n    const originalBody = `<div>${getSanitizedHtmlBody(originalContent)}</div>`;\n    const editBody = `<div>${getSanitizedHtmlBody(editContent)}</div>`;\n    const dd = new DiffDOM();\n    // diffActions is an array of objects with at least a `action` and `route`\n    // property. `action` tells us what the diff object changes, and `route` where.\n    // `route` is a path on the DOM tree expressed as an array of indices.\n    const diffActions = dd.diff(originalBody, editBody);\n    // for diffing text fragments\n    const diffMathPatch = new DiffMatchPatch();\n    // parse the base html message as a DOM tree, to which we'll apply the differences found.\n    // fish out the div in which we wrapped the messages above with children[0].\n    const originalRootNode = new DOMParser().parseFromString(originalBody, \"text/html\").body.children[0]!;\n    for (let i = 0; i < diffActions.length; ++i) {\n        const diff = diffActions[i]!;\n        renderDifferenceInDOM(originalRootNode, diff, diffMathPatch);\n        // DiffDOM assumes in subsequent diffs route path that\n        // the action was applied (e.g. that a removeElement action removed the element).\n        // This is not the case for us. We render differences in the DOM tree, and don't apply them.\n        // So we need to adjust the routes of the remaining diffs to account for this.\n        adjustRoutes(diff, diffActions.slice(i + 1));\n    }\n    // take the html out of the modified DOM tree again\n    const safeBody = originalRootNode.innerHTML;\n    const className = classNames({\n        \"mx_EventTile_body\": true,\n        \"markdown-body\": true,\n    });\n    return <span key=\"body\" className={className} dangerouslySetInnerHTML={{ __html: safeBody }} dir=\"auto\" />;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type MatrixEvent, HTTPError, MatrixError } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../languageHandler\";\nimport ConfirmRedactDialog from \"./ConfirmRedactDialog\";\nimport ErrorDialog from \"./ErrorDialog\";\nimport BaseDialog from \"./BaseDialog\";\nimport Spinner from \"../elements/Spinner\";\n\ninterface IProps {\n    event: MatrixEvent;\n    redact: () => Promise<void>;\n    onFinished: (success?: boolean) => void;\n}\n\ninterface IState {\n    isRedacting: boolean;\n    redactionErrorCode: string | number | null;\n}\n\n/*\n * A dialog for confirming a redaction.\n * Also shows a spinner (and possible error) while the redaction is ongoing,\n * and only closes the dialog when the redaction is done or failed.\n *\n * This is done to prevent the edit history dialog racing with the redaction:\n * if this dialog closes and the MessageEditHistoryDialog is shown again,\n * it will fetch the relations again, which will race with the ongoing /redact request.\n * which will cause the edit to appear unredacted.\n *\n * To avoid this, we keep the dialog open as long as /redact is in progress.\n */\nexport default class ConfirmAndWaitRedactDialog extends React.PureComponent<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n        this.state = {\n            isRedacting: false,\n            redactionErrorCode: null,\n        };\n    }\n\n    public onParentFinished = async (proceed?: boolean): Promise<void> => {\n        if (proceed) {\n            this.setState({ isRedacting: true });\n            try {\n                await this.props.redact();\n                this.props.onFinished(true);\n            } catch (error) {\n                let code: string | number | undefined;\n                if (error instanceof MatrixError) {\n                    code = error.errcode;\n                } else if (error instanceof HTTPError) {\n                    code = error.httpStatus;\n                }\n\n                if (typeof code !== \"undefined\") {\n                    this.setState({ redactionErrorCode: code });\n                } else {\n                    this.props.onFinished(true);\n                }\n            }\n        } else {\n            this.props.onFinished(false);\n        }\n    };\n\n    public render(): React.ReactNode {\n        if (this.state.isRedacting) {\n            if (this.state.redactionErrorCode) {\n                const code = this.state.redactionErrorCode;\n                return (\n                    <ErrorDialog\n                        onFinished={this.props.onFinished}\n                        title={_t(\"common|error\")}\n                        description={_t(\"redact|error\", { code })}\n                    />\n                );\n            } else {\n                return (\n                    <BaseDialog onFinished={this.props.onFinished} hasCancel={false} title={_t(\"redact|ongoing\")}>\n                        <Spinner />\n                    </BaseDialog>\n                );\n            }\n        } else {\n            return <ConfirmRedactDialog event={this.props.event} onFinished={this.onParentFinished} />;\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, createRef } from \"react\";\nimport { type EventStatus, type IContent, type MatrixEvent, MatrixEventEvent, MsgType } from \"matrix-js-sdk/src/matrix\";\nimport classNames from \"classnames\";\n\nimport EventContentBody from \"./EventContentBody.tsx\";\nimport { editBodyDiffToHtml } from \"../../../utils/MessageDiffUtils\";\nimport { formatTime } from \"../../../DateUtils\";\nimport { _t } from \"../../../languageHandler\";\nimport Modal from \"../../../Modal\";\nimport RedactedBody from \"./RedactedBody\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport ConfirmAndWaitRedactDialog from \"../dialogs/ConfirmAndWaitRedactDialog\";\nimport ViewSource from \"../../structures/ViewSource\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\n\nfunction getReplacedContent(event: MatrixEvent): IContent {\n    const originalContent = event.getOriginalContent();\n    return originalContent[\"m.new_content\"] || originalContent;\n}\n\ninterface IProps {\n    // the message event being edited\n    mxEvent: MatrixEvent;\n    previousEdit?: MatrixEvent;\n    isBaseEvent?: boolean;\n    isTwelveHour?: boolean;\n}\n\ninterface IState {\n    canRedact: boolean;\n    sendStatus: EventStatus | null;\n}\n\nexport default class EditHistoryMessage extends React.PureComponent<IProps, IState> {\n    public static contextType = MatrixClientContext;\n    declare public context: React.ContextType<typeof MatrixClientContext>;\n\n    private content = createRef<HTMLDivElement>();\n\n    public constructor(props: IProps, context: React.ContextType<typeof MatrixClientContext>) {\n        super(props, context);\n\n        const cli = this.context;\n        const userId = cli.getSafeUserId();\n        const event = this.props.mxEvent;\n        const room = cli.getRoom(event.getRoomId());\n        event.localRedactionEvent()?.on(MatrixEventEvent.Status, this.onAssociatedStatusChanged);\n        const canRedact = room?.currentState.maySendRedactionForEvent(event, userId) ?? false;\n        this.state = { canRedact, sendStatus: event.getAssociatedStatus() };\n    }\n\n    private onAssociatedStatusChanged = (): void => {\n        this.setState({ sendStatus: this.props.mxEvent.getAssociatedStatus() });\n    };\n\n    private onRedactClick = async (): Promise<void> => {\n        const event = this.props.mxEvent;\n        const cli = this.context;\n\n        Modal.createDialog(\n            ConfirmAndWaitRedactDialog,\n            {\n                event,\n                redact: async () => {\n                    await cli.redactEvent(event.getRoomId()!, event.getId()!);\n                },\n            },\n            \"mx_Dialog_confirmredact\",\n        );\n    };\n\n    private onViewSourceClick = (): void => {\n        Modal.createDialog(\n            ViewSource,\n            {\n                mxEvent: this.props.mxEvent,\n                ignoreEdits: true,\n            },\n            \"mx_Dialog_viewsource\",\n        );\n    };\n\n    public componentWillUnmount(): void {\n        const event = this.props.mxEvent;\n        event.localRedactionEvent()?.off(MatrixEventEvent.Status, this.onAssociatedStatusChanged);\n    }\n\n    private renderActionBar(): React.ReactNode {\n        // hide the button when already redacted\n        let redactButton: JSX.Element | undefined;\n        if (!this.props.mxEvent.isRedacted() && !this.props.isBaseEvent && this.state.canRedact) {\n            redactButton = <AccessibleButton onClick={this.onRedactClick}>{_t(\"action|remove\")}</AccessibleButton>;\n        }\n\n        let viewSourceButton: JSX.Element | undefined;\n        if (SettingsStore.getValue(\"developerMode\")) {\n            viewSourceButton = (\n                <AccessibleButton onClick={this.onViewSourceClick}>{_t(\"action|view_source\")}</AccessibleButton>\n            );\n        }\n\n        if (!redactButton && !viewSourceButton) {\n            // Hide the empty MessageActionBar\n            return null;\n        } else {\n            // disabled remove button when not allowed\n            return (\n                <div className=\"mx_MessageActionBar\">\n                    {redactButton}\n                    {viewSourceButton}\n                </div>\n            );\n        }\n    }\n\n    public render(): React.ReactNode {\n        const { mxEvent } = this.props;\n        const content = getReplacedContent(mxEvent);\n        let contentContainer;\n        if (mxEvent.isRedacted()) {\n            contentContainer = <RedactedBody mxEvent={this.props.mxEvent} />;\n        } else {\n            let contentElements;\n            if (this.props.previousEdit) {\n                contentElements = editBodyDiffToHtml(getReplacedContent(this.props.previousEdit), content);\n            } else {\n                contentElements = (\n                    <EventContentBody\n                        as=\"span\"\n                        mxEvent={mxEvent}\n                        content={content}\n                        highlights={[]}\n                        stripReply\n                        renderTooltipsForAmbiguousLinks\n                        renderMentionPills\n                        renderCodeBlocks\n                        renderSpoilers\n                        linkify\n                    />\n                );\n            }\n            if (mxEvent.getContent().msgtype === MsgType.Emote) {\n                const name = mxEvent.sender ? mxEvent.sender.name : mxEvent.getSender();\n                contentContainer = (\n                    <div className=\"mx_EventTile_content\" ref={this.content}>\n                        *&nbsp;\n                        <span className=\"mx_MEmoteBody_sender\">{name}</span>\n                        &nbsp;{contentElements}\n                    </div>\n                );\n            } else {\n                contentContainer = (\n                    <div className=\"mx_EventTile_content\" ref={this.content}>\n                        {contentElements}\n                    </div>\n                );\n            }\n        }\n\n        const timestamp = formatTime(new Date(mxEvent.getTs()), this.props.isTwelveHour);\n        const isSending = [\"sending\", \"queued\", \"encrypting\"].includes(this.state.sendStatus!);\n        const classes = classNames(\"mx_EventTile\", {\n            // Note: we keep the `sending` state class for tests, not for our styles\n            mx_EventTile_sending: isSending,\n        });\n        return (\n            <li>\n                <div className={classes}>\n                    <div className=\"mx_EventTile_line\">\n                        <span className=\"mx_MessageTimestamp\">{timestamp}</span>\n                        {contentContainer}\n                        {this.renderActionBar()}\n                    </div>\n                </div>\n            </li>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { type MatrixEvent, EventType, RelationType, type MatrixClient, MatrixError } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { _t } from \"../../../languageHandler\";\nimport { wantsDateSeparator } from \"../../../DateUtils\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport BaseDialog from \"./BaseDialog\";\nimport ScrollPanel from \"../../structures/ScrollPanel\";\nimport Spinner from \"../elements/Spinner\";\nimport EditHistoryMessage from \"../messages/EditHistoryMessage\";\nimport DateSeparator from \"../messages/DateSeparator\";\n\ninterface IProps {\n    mxEvent: MatrixEvent;\n    onFinished(): void;\n}\n\ninterface IState {\n    originalEvent: MatrixEvent | null;\n    error: MatrixError | null;\n    events: MatrixEvent[];\n    nextBatch: string | null;\n    isLoading: boolean;\n    isTwelveHour: boolean;\n}\n\nexport default class MessageEditHistoryDialog extends React.PureComponent<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n        this.state = {\n            originalEvent: null,\n            error: null,\n            events: [],\n            nextBatch: null,\n            isLoading: true,\n            isTwelveHour: SettingsStore.getValue(\"showTwelveHourTimestamps\"),\n        };\n    }\n\n    private loadMoreEdits = async (backwards?: boolean): Promise<boolean> => {\n        if (backwards || (!this.state.nextBatch && !this.state.isLoading)) {\n            // bail out on backwards as we only paginate in one direction\n            return false;\n        }\n        const opts = { from: this.state.nextBatch ?? undefined };\n        const roomId = this.props.mxEvent.getRoomId()!;\n        const eventId = this.props.mxEvent.getId()!;\n        const client = MatrixClientPeg.safeGet();\n\n        const { resolve, reject, promise } = Promise.withResolvers<boolean>();\n        let result: Awaited<ReturnType<MatrixClient[\"relations\"]>>;\n\n        try {\n            result = await client.relations(roomId, eventId, RelationType.Replace, EventType.RoomMessage, opts);\n        } catch (error) {\n            // log if the server returned an error\n            if (error instanceof MatrixError && error.errcode) {\n                logger.error(\"fetching /relations failed with error\", error);\n            }\n            this.setState({ error: error as MatrixError }, () => reject(error));\n            return promise;\n        }\n\n        const newEvents = result.events;\n        this.locallyRedactEventsIfNeeded(newEvents);\n        this.setState(\n            {\n                originalEvent: this.state.originalEvent ?? result.originalEvent ?? null,\n                events: this.state.events.concat(newEvents),\n                nextBatch: result.nextBatch ?? null,\n                isLoading: false,\n            },\n            () => {\n                const hasMoreResults = !!this.state.nextBatch;\n                resolve(hasMoreResults);\n            },\n        );\n        return promise;\n    };\n\n    private locallyRedactEventsIfNeeded(newEvents: MatrixEvent[]): void {\n        const roomId = this.props.mxEvent.getRoomId();\n        const client = MatrixClientPeg.safeGet();\n        const room = client.getRoom(roomId);\n        if (!room) return;\n        const pendingEvents = room.getPendingEvents();\n        for (const e of newEvents) {\n            const pendingRedaction = pendingEvents.find((pe) => {\n                return pe.getType() === EventType.RoomRedaction && pe.getAssociatedId() === e.getId();\n            });\n            if (pendingRedaction) {\n                e.markLocallyRedacted(pendingRedaction);\n            }\n        }\n    }\n\n    public componentDidMount(): void {\n        this.loadMoreEdits();\n    }\n\n    private renderEdits(): JSX.Element[] {\n        const nodes: JSX.Element[] = [];\n        let lastEvent: MatrixEvent;\n        let allEvents = this.state.events;\n        // append original event when we've done last pagination\n        if (this.state.originalEvent && !this.state.nextBatch) {\n            allEvents = allEvents.concat(this.state.originalEvent);\n        }\n        const baseEventId = this.props.mxEvent.getId();\n        allEvents.forEach((e, i) => {\n            if (!lastEvent || wantsDateSeparator(lastEvent.getDate() || undefined, e.getDate() || undefined)) {\n                nodes.push(\n                    <li key={e.getTs() + \"~\"}>\n                        <DateSeparator roomId={e.getRoomId()!} ts={e.getTs()} />\n                    </li>,\n                );\n            }\n            const isBaseEvent = e.getId() === baseEventId;\n            nodes.push(\n                <EditHistoryMessage\n                    key={e.getId()}\n                    previousEdit={!isBaseEvent ? allEvents[i + 1] : undefined}\n                    isBaseEvent={isBaseEvent}\n                    mxEvent={e}\n                    isTwelveHour={this.state.isTwelveHour}\n                />,\n            );\n            lastEvent = e;\n        });\n        return nodes;\n    }\n\n    public render(): React.ReactNode {\n        let content;\n        if (this.state.error) {\n            const { error } = this.state;\n            if (error.errcode === \"M_UNRECOGNIZED\") {\n                content = <p className=\"mx_MessageEditHistoryDialog_error\">{_t(\"error|edit_history_unsupported\")}</p>;\n            } else if (error.errcode) {\n                // some kind of error from the homeserver\n                content = <p className=\"mx_MessageEditHistoryDialog_error\">{_t(\"error|something_went_wrong\")}</p>;\n            } else {\n                content = (\n                    <p className=\"mx_MessageEditHistoryDialog_error\">\n                        {_t(\"cannot_reach_homeserver\")}\n                        <br />\n                        {_t(\"cannot_reach_homeserver_detail\")}\n                    </p>\n                );\n            }\n        } else if (this.state.isLoading) {\n            content = <Spinner />;\n        } else {\n            content = (\n                <ScrollPanel\n                    className=\"mx_MessageEditHistoryDialog_scrollPanel\"\n                    onFillRequest={this.loadMoreEdits}\n                    stickyBottom={false}\n                    startAtBottom={false}\n                >\n                    <ul className=\"mx_MessageEditHistoryDialog_edits\">{this.renderEdits()}</ul>\n                </ScrollPanel>\n            );\n        }\n        return (\n            <BaseDialog\n                className=\"mx_MessageEditHistoryDialog\"\n                hasCancel={true}\n                onFinished={this.props.onFinished}\n                title={_t(\"message_edit_dialog_title\")}\n            >\n                {content}\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef, type KeyboardEvent } from \"react\";\nimport classNames from \"classnames\";\nimport { EventStatus, type MatrixEvent, type Room, MsgType } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type Composer as ComposerEvent } from \"@matrix-org/analytics-events/types/typescript/Composer\";\nimport {\n    type ReplacementEvent,\n    type RoomMessageEventContent,\n    type RoomMessageTextEventContent,\n} from \"matrix-js-sdk/src/types\";\n\nimport { _t } from \"../../../languageHandler\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport EditorModel from \"../../../editor/model\";\nimport { getCaretOffsetAndText } from \"../../../editor/dom\";\nimport { htmlSerializeIfNeeded, textSerialize, containsEmote, stripEmoteCommand } from \"../../../editor/serialize\";\nimport { findEditableEvent } from \"../../../utils/EventUtils\";\nimport { parseEvent } from \"../../../editor/deserialize\";\nimport { CommandPartCreator, type Part, type PartCreator, type SerializedPart } from \"../../../editor/parts\";\nimport type EditorStateTransfer from \"../../../utils/EditorStateTransfer\";\nimport BasicMessageComposer, { REGEX_EMOTICON } from \"./BasicMessageComposer\";\nimport { CommandCategories } from \"../../../slash-commands/SlashCommands\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport SendHistoryManager from \"../../../SendHistoryManager\";\nimport { type ActionPayload } from \"../../../dispatcher/payloads\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport { createRedactEventDialog } from \"../dialogs/ConfirmRedactDialog\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { withMatrixClientHOC, type MatrixClientProps } from \"../../../contexts/MatrixClientContext\";\nimport RoomContext from \"../../../contexts/RoomContext\";\nimport { ComposerType } from \"../../../dispatcher/payloads/ComposerInsertPayload\";\nimport { getSlashCommand, isSlashCommand, runSlashCommand, shouldSendAnyway } from \"../../../editor/commands\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { PosthogAnalytics } from \"../../../PosthogAnalytics\";\nimport { editorRoomKey, editorStateKey } from \"../../../Editing\";\nimport type DocumentOffset from \"../../../editor/offset\";\nimport { attachMentions, attachRelation } from \"../../../utils/messages\";\nimport { filterBoolean } from \"../../../utils/arrays\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\n\n// exported for tests\nexport function createEditContent(\n    model: EditorModel,\n    editedEvent: MatrixEvent,\n    replyToEvent?: MatrixEvent,\n): RoomMessageEventContent {\n    const isEmote = containsEmote(model);\n    if (isEmote) {\n        model = stripEmoteCommand(model);\n    }\n    const body = textSerialize(model);\n\n    const newContent: RoomMessageEventContent = {\n        msgtype: isEmote ? MsgType.Emote : MsgType.Text,\n        body: body,\n    };\n    const contentBody: RoomMessageTextEventContent & Omit<ReplacementEvent<RoomMessageEventContent>, \"m.relates_to\"> = {\n        \"msgtype\": newContent.msgtype,\n        \"body\": `* ${body}`,\n        \"m.new_content\": newContent,\n    };\n\n    const formattedBody = htmlSerializeIfNeeded(model, {\n        useMarkdown: SettingsStore.getValue(\"MessageComposerInput.useMarkdown\"),\n    });\n    if (formattedBody) {\n        newContent.format = \"org.matrix.custom.html\";\n        newContent.formatted_body = formattedBody;\n        contentBody.format = newContent.format;\n        contentBody.formatted_body = `* ${formattedBody}`;\n    }\n\n    // Build the mentions properties for both the content and new_content.\n    attachMentions(editedEvent.sender!.userId, contentBody, model, replyToEvent, editedEvent.getContent());\n    attachRelation(contentBody, { rel_type: \"m.replace\", event_id: editedEvent.getId() });\n\n    return contentBody as RoomMessageEventContent;\n}\n\ninterface IEditMessageComposerProps extends MatrixClientProps {\n    editState: EditorStateTransfer;\n    className?: string;\n}\ninterface IState {\n    saveDisabled: boolean;\n}\n\nclass EditMessageComposer extends React.Component<IEditMessageComposerProps, IState> {\n    public static contextType = RoomContext;\n    declare public context: React.ContextType<typeof RoomContext>;\n\n    private readonly editorRef = createRef<BasicMessageComposer>();\n    private dispatcherRef?: string;\n    private readonly replyToEvent?: MatrixEvent;\n    private model!: EditorModel;\n\n    public constructor(props: IEditMessageComposerProps, context: React.ContextType<typeof RoomContext>) {\n        super(props, context);\n\n        const isRestored = this.createEditorModel();\n        const ev = this.props.editState.getEvent();\n\n        this.replyToEvent = ev.replyEventId ? this.context.room?.findEventById(ev.replyEventId) : undefined;\n\n        const editContent = createEditContent(this.model, ev, this.replyToEvent);\n        this.state = {\n            saveDisabled: !isRestored || !this.isContentModified(editContent[\"m.new_content\"]!),\n        };\n    }\n\n    public componentDidMount(): void {\n        window.addEventListener(\"beforeunload\", this.saveStoredEditorState);\n        this.dispatcherRef = dis.register(this.onAction);\n    }\n\n    private getRoom(): Room {\n        if (!this.context.room) {\n            throw new Error(`Cannot render without room`);\n        }\n        return this.context.room;\n    }\n\n    private onKeyDown = (event: KeyboardEvent): void => {\n        // ignore any keypress while doing IME compositions\n        if (this.editorRef.current?.isComposing(event)) {\n            return;\n        }\n        const action = getKeyBindingsManager().getMessageComposerAction(event);\n        switch (action) {\n            case KeyBindingAction.SendMessage:\n                this.sendEdit();\n                event.stopPropagation();\n                event.preventDefault();\n                break;\n            case KeyBindingAction.CancelReplyOrEdit:\n                event.stopPropagation();\n                this.cancelEdit();\n                break;\n            case KeyBindingAction.EditPrevMessage: {\n                if (this.editorRef.current?.isModified() || !this.editorRef.current?.isCaretAtStart()) {\n                    return;\n                }\n                const previousEvent = findEditableEvent({\n                    events: this.events,\n                    isForward: false,\n                    fromEventId: this.props.editState.getEvent().getId(),\n                    matrixClient: MatrixClientPeg.safeGet(),\n                });\n                if (previousEvent) {\n                    dis.dispatch({\n                        action: Action.EditEvent,\n                        event: previousEvent,\n                        timelineRenderingType: this.context.timelineRenderingType,\n                    });\n                    event.preventDefault();\n                }\n                break;\n            }\n            case KeyBindingAction.EditNextMessage: {\n                if (this.editorRef.current?.isModified() || !this.editorRef.current?.isCaretAtEnd()) {\n                    return;\n                }\n                const nextEvent = findEditableEvent({\n                    events: this.events,\n                    isForward: true,\n                    fromEventId: this.props.editState.getEvent().getId(),\n                    matrixClient: MatrixClientPeg.safeGet(),\n                });\n                if (nextEvent) {\n                    dis.dispatch({\n                        action: Action.EditEvent,\n                        event: nextEvent,\n                        timelineRenderingType: this.context.timelineRenderingType,\n                    });\n                } else {\n                    this.cancelEdit();\n                }\n                event.preventDefault();\n                break;\n            }\n        }\n    };\n\n    private endEdit(): void {\n        localStorage.removeItem(this.editorRoomKey);\n        localStorage.removeItem(this.editorStateKey);\n\n        // close the event editing and focus composer\n        dis.dispatch({\n            action: Action.EditEvent,\n            event: null,\n            timelineRenderingType: this.context.timelineRenderingType,\n        });\n        dis.dispatch({\n            action: Action.FocusSendMessageComposer,\n            context: this.context.timelineRenderingType,\n        });\n    }\n\n    private get editorRoomKey(): string {\n        return editorRoomKey(this.props.editState.getEvent().getRoomId()!, this.context.timelineRenderingType);\n    }\n\n    private get editorStateKey(): string {\n        return editorStateKey(this.props.editState.getEvent().getId()!);\n    }\n\n    private get events(): MatrixEvent[] {\n        const liveTimelineEvents = this.context.liveTimeline?.getEvents();\n        const room = this.getRoom();\n        if (!liveTimelineEvents || !room) return [];\n        const pendingEvents = room.getPendingEvents();\n        const isInThread = Boolean(this.props.editState.getEvent().getThread());\n        return liveTimelineEvents.concat(isInThread ? [] : pendingEvents);\n    }\n\n    private cancelEdit = (): void => {\n        this.endEdit();\n    };\n\n    private get shouldSaveStoredEditorState(): boolean {\n        return localStorage.getItem(this.editorRoomKey) !== null;\n    }\n\n    private restoreStoredEditorState(partCreator: PartCreator): Part[] | undefined {\n        const json = localStorage.getItem(this.editorStateKey);\n        if (json) {\n            try {\n                const { parts: serializedParts } = JSON.parse(json);\n                const parts: Part[] = serializedParts.map((p: SerializedPart) => partCreator.deserializePart(p));\n                return parts;\n            } catch (e) {\n                logger.error(\"Error parsing editing state: \", e);\n            }\n        }\n    }\n\n    private clearPreviousEdit(): void {\n        if (localStorage.getItem(this.editorRoomKey)) {\n            localStorage.removeItem(`mx_edit_state_${localStorage.getItem(this.editorRoomKey)}`);\n        }\n    }\n\n    private saveStoredEditorState = (): void => {\n        const item = SendHistoryManager.createItem(this.model);\n        this.clearPreviousEdit();\n        localStorage.setItem(this.editorRoomKey, this.props.editState.getEvent().getId()!);\n        localStorage.setItem(this.editorStateKey, JSON.stringify(item));\n    };\n\n    private isContentModified(newContent: RoomMessageEventContent): boolean {\n        // if nothing has changed then bail\n        const oldContent = this.props.editState.getEvent().getContent<RoomMessageEventContent>();\n        if (\n            oldContent[\"msgtype\"] === newContent[\"msgtype\"] &&\n            oldContent[\"body\"] === newContent[\"body\"] &&\n            (oldContent as RoomMessageTextEventContent)[\"format\"] ===\n                (newContent as RoomMessageTextEventContent)[\"format\"] &&\n            (oldContent as RoomMessageTextEventContent)[\"formatted_body\"] ===\n                (newContent as RoomMessageTextEventContent)[\"formatted_body\"]\n        ) {\n            return false;\n        }\n        return true;\n    }\n\n    private sendEdit = async (): Promise<void> => {\n        if (this.state.saveDisabled) return;\n\n        const editedEvent = this.props.editState.getEvent();\n\n        PosthogAnalytics.instance.trackEvent<ComposerEvent>({\n            eventName: \"Composer\",\n            isEditing: true,\n            messageType: \"Text\",\n            inThread: !!editedEvent?.getThread(),\n            isReply: !!editedEvent.replyEventId,\n        });\n\n        // Replace emoticon at the end of the message\n        if (SettingsStore.getValue(\"MessageComposerInput.autoReplaceEmoji\") && this.editorRef.current) {\n            const caret = this.editorRef.current.getCaret();\n            const position = this.model.positionForOffset(caret.offset, caret.atNodeEnd);\n            this.editorRef.current.replaceEmoticon(position, REGEX_EMOTICON);\n        }\n        const editContent = createEditContent(this.model, editedEvent, this.replyToEvent);\n        const newContent = editContent[\"m.new_content\"]!;\n\n        let shouldSend = true;\n\n        if (newContent?.body === \"\") {\n            this.cancelPreviousPendingEdit();\n            createRedactEventDialog({\n                mxEvent: editedEvent,\n                onCloseDialog: () => {\n                    this.cancelEdit();\n                },\n            });\n            return;\n        }\n\n        // If content is modified then send an updated event into the room\n        if (this.isContentModified(newContent)) {\n            const roomId = editedEvent.getRoomId()!;\n            if (!containsEmote(this.model) && isSlashCommand(this.model)) {\n                const [cmd, args, commandText] = getSlashCommand(roomId, this.model);\n                if (cmd) {\n                    const threadId = editedEvent?.getThread()?.id || null;\n                    const [content, commandSuccessful] = await runSlashCommand(\n                        MatrixClientPeg.safeGet(),\n                        cmd,\n                        args,\n                        roomId,\n                        threadId,\n                    );\n                    if (!commandSuccessful) {\n                        return; // errored\n                    }\n\n                    if (cmd.category === CommandCategories.messages || cmd.category === CommandCategories.effects) {\n                        editContent[\"m.new_content\"] = content!;\n                    } else {\n                        shouldSend = false;\n                    }\n                } else {\n                    const sendAnyway = await shouldSendAnyway(commandText);\n                    // re-focus the composer after QuestionDialog is closed\n                    dis.dispatch({\n                        action: Action.FocusAComposer,\n                        context: this.context.timelineRenderingType,\n                    });\n                    // if !sendAnyway bail to let the user edit the composer and try again\n                    if (!sendAnyway) return;\n                }\n            }\n            if (shouldSend) {\n                this.cancelPreviousPendingEdit();\n\n                const event = this.props.editState.getEvent();\n                const threadId = event.threadRootId || null;\n\n                this.props.mxClient.sendMessage(roomId, threadId, editContent);\n                dis.dispatch({ action: \"message_sent\" });\n            }\n        }\n\n        this.endEdit();\n    };\n\n    private cancelPreviousPendingEdit(): void {\n        const originalEvent = this.props.editState.getEvent();\n        const previousEdit = originalEvent.replacingEvent();\n        if (\n            previousEdit &&\n            (previousEdit.status === EventStatus.QUEUED || previousEdit.status === EventStatus.NOT_SENT)\n        ) {\n            this.props.mxClient.cancelPendingEvent(previousEdit);\n        }\n    }\n\n    public componentWillUnmount(): void {\n        // store caret and serialized parts in the\n        // editorstate so it can be restored when the remote echo event tile gets rendered\n        // in case we're currently editing a pending event\n        const sel = document.getSelection()!;\n        let caret: DocumentOffset | undefined;\n        if (sel.focusNode && this.editorRef.current?.editorRef.current) {\n            caret = getCaretOffsetAndText(this.editorRef.current.editorRef.current, sel).caret;\n        }\n        const parts = this.model.serializeParts();\n        // if caret is undefined because for some reason there isn't a valid selection,\n        // then when mounting the editor again with the same editor state,\n        // it will set the cursor at the end.\n        this.props.editState.setEditorState(caret ?? null, parts);\n        window.removeEventListener(\"beforeunload\", this.saveStoredEditorState);\n        if (this.shouldSaveStoredEditorState) {\n            this.saveStoredEditorState();\n        }\n        dis.unregister(this.dispatcherRef);\n    }\n\n    private createEditorModel(): boolean {\n        const { editState } = this.props;\n        const room = this.getRoom();\n        const partCreator = new CommandPartCreator(room, this.props.mxClient);\n\n        let parts: Part[];\n        let isRestored = false;\n        if (editState.hasEditorState()) {\n            // if restoring state from a previous editor,\n            // restore serialized parts from the state\n            // (editState.hasEditorState() checks getSerializedParts is not null)\n            parts = filterBoolean<Part>(editState.getSerializedParts()!.map((p) => partCreator.deserializePart(p)));\n        } else {\n            // otherwise, either restore serialized parts from localStorage or parse the body of the event\n            const restoredParts = this.restoreStoredEditorState(partCreator);\n            parts =\n                restoredParts ||\n                parseEvent(editState.getEvent(), partCreator, {\n                    shouldEscape: SettingsStore.getValue(\"MessageComposerInput.useMarkdown\"),\n                });\n            isRestored = !!restoredParts;\n        }\n        this.model = new EditorModel(parts, partCreator);\n        this.saveStoredEditorState();\n\n        return isRestored;\n    }\n\n    private onChange = (): void => {\n        if (!this.state.saveDisabled || !this.editorRef.current?.isModified()) {\n            return;\n        }\n\n        this.setState({\n            saveDisabled: false,\n        });\n    };\n\n    private onAction = (payload: ActionPayload): void => {\n        if (!this.editorRef.current) return;\n\n        if (payload.action === Action.ComposerInsert) {\n            if (payload.timelineRenderingType !== this.context.timelineRenderingType) return;\n            if (payload.composerType !== ComposerType.Edit) return;\n\n            if (payload.userId) {\n                this.editorRef.current?.insertMention(payload.userId);\n            } else if (payload.event) {\n                this.editorRef.current?.insertQuotedMessage(payload.event);\n            } else if (payload.text) {\n                this.editorRef.current?.insertPlaintext(payload.text);\n            }\n        } else if (payload.action === Action.FocusEditMessageComposer) {\n            this.editorRef.current.focus();\n        }\n    };\n\n    public render(): React.ReactNode {\n        const room = this.getRoom();\n        if (!room) return null;\n\n        return (\n            <div className={classNames(\"mx_EditMessageComposer\", this.props.className)} onKeyDown={this.onKeyDown}>\n                <BasicMessageComposer\n                    ref={this.editorRef}\n                    model={this.model}\n                    room={room}\n                    threadId={this.props.editState?.getEvent()?.getThread()?.id}\n                    initialCaret={this.props.editState.getCaret() ?? undefined}\n                    label={_t(\"composer|edit_composer_label\")}\n                    onChange={this.onChange}\n                />\n                <div className=\"mx_EditMessageComposer_buttons\">\n                    <AccessibleButton kind=\"secondary\" onClick={this.cancelEdit}>\n                        {_t(\"action|cancel\")}\n                    </AccessibleButton>\n                    <AccessibleButton kind=\"primary\" onClick={this.sendEdit} disabled={this.state.saveDisabled}>\n                        {_t(\"action|save\")}\n                    </AccessibleButton>\n                </div>\n            </div>\n        );\n    }\n}\n\nconst EditMessageComposerWithMatrixClient = withMatrixClientHOC(EditMessageComposer);\nexport default EditMessageComposerWithMatrixClient;\n","/*\nCopyright 2024, 2025 New Vector Ltd.\nCopyright 2016-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ComponentProps, createRef, type ReactNode } from \"react\";\nimport { decode } from \"html-entities\";\nimport { type MatrixEvent, type IPreviewUrlResponse } from \"matrix-js-sdk/src/matrix\";\n\nimport { Linkify } from \"../../../HtmlUtils\";\nimport Modal from \"../../../Modal\";\nimport * as ImageUtils from \"../../../ImageUtils\";\nimport { mediaFromMxc } from \"../../../customisations/Media\";\nimport ImageView from \"../elements/ImageView\";\nimport LinkWithTooltip from \"../elements/LinkWithTooltip\";\nimport PlatformPeg from \"../../../PlatformPeg\";\n\ninterface IProps {\n    link: string;\n    preview: IPreviewUrlResponse;\n    mxEvent: MatrixEvent; // the Event associated with the preview\n    children?: ReactNode;\n    mediaVisible: boolean;\n}\n\nexport default class LinkPreviewWidget extends React.Component<IProps> {\n    private image = createRef<HTMLImageElement>();\n\n    private onImageClick = (ev: React.MouseEvent): void => {\n        const p = this.props.preview;\n        if (ev.button != 0 || ev.metaKey) return;\n        ev.preventDefault();\n\n        let src: string | null | undefined = p[\"og:image\"];\n        if (src?.startsWith(\"mxc://\")) {\n            src = mediaFromMxc(src).srcHttp;\n        }\n\n        if (!src) return;\n\n        const params: Omit<ComponentProps<typeof ImageView>, \"onFinished\"> = {\n            src: src,\n            width: p[\"og:image:width\"],\n            height: p[\"og:image:height\"],\n            name: p[\"og:title\"] || p[\"og:description\"] || this.props.link,\n            fileSize: p[\"matrix:image:size\"],\n            link: this.props.link,\n        };\n\n        if (this.image.current) {\n            const clientRect = this.image.current.getBoundingClientRect();\n\n            params.thumbnailInfo = {\n                width: clientRect.width,\n                height: clientRect.height,\n                positionX: clientRect.x,\n                positionY: clientRect.y,\n            };\n        }\n\n        Modal.createDialog(ImageView, params, \"mx_Dialog_lightbox\", undefined, true);\n    };\n\n    public render(): React.ReactNode {\n        const p = this.props.preview;\n\n        // FIXME: do we want to factor out all image displaying between this and MImageBody - especially for lightboxing?\n        let image: string | null = p[\"og:image\"] ?? null;\n        if (!this.props.mediaVisible) {\n            image = null; // Don't render a button to show the image, just hide it outright\n        }\n        const imageMaxWidth = 100;\n        const imageMaxHeight = 100;\n        if (image && image.startsWith(\"mxc://\")) {\n            // We deliberately don't want a square here, so use the source HTTP thumbnail function\n            image = mediaFromMxc(image).getThumbnailOfSourceHttp(imageMaxWidth, imageMaxHeight, \"scale\");\n        }\n\n        const thumbHeight =\n            ImageUtils.thumbHeight(p[\"og:image:width\"], p[\"og:image:height\"], imageMaxWidth, imageMaxHeight) ??\n            imageMaxHeight;\n\n        let img: JSX.Element | undefined;\n        if (image) {\n            img = (\n                <div className=\"mx_LinkPreviewWidget_image\" style={{ height: thumbHeight }}>\n                    <img\n                        ref={this.image}\n                        style={{ maxWidth: imageMaxWidth, maxHeight: imageMaxHeight }}\n                        src={image}\n                        onClick={this.onImageClick}\n                        alt=\"\"\n                    />\n                </div>\n            );\n        }\n\n        // The description includes &-encoded HTML entities, we decode those as React treats the thing as an\n        // opaque string. This does not allow any HTML to be injected into the DOM.\n        const description = decode(p[\"og:description\"] || \"\");\n\n        const title = p[\"og:title\"]?.trim() ?? \"\";\n        const anchor = (\n            <a href={this.props.link} target=\"_blank\" rel=\"noreferrer noopener\">\n                {title}\n            </a>\n        );\n        const needsTooltip = PlatformPeg.get()?.needsUrlTooltips() && this.props.link !== title;\n\n        return (\n            <div className=\"mx_LinkPreviewWidget\">\n                <div className=\"mx_LinkPreviewWidget_wrapImageCaption\">\n                    {img}\n                    <div className=\"mx_LinkPreviewWidget_caption\">\n                        <div className=\"mx_LinkPreviewWidget_title\">\n                            {needsTooltip ? (\n                                <LinkWithTooltip tooltip={new URL(this.props.link, window.location.href).toString()}>\n                                    {anchor}\n                                </LinkWithTooltip>\n                            ) : (\n                                anchor\n                            )}\n                            {p[\"og:site_name\"] && (\n                                <span className=\"mx_LinkPreviewWidget_siteName\">{\" - \" + p[\"og:site_name\"]}</span>\n                            )}\n                        </div>\n                        <div className=\"mx_LinkPreviewWidget_description\">\n                            <Linkify>{description}</Linkify>\n                        </div>\n                    </div>\n                </div>\n                {this.props.children}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015, 2016 , 2020 Copyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\n * Returns the actual height that an image of dimensions (fullWidth, fullHeight)\n * will occupy if resized to fit inside a thumbnail bounding box of size\n * (thumbWidth, thumbHeight).\n *\n * If the aspect ratio of the source image is taller than the aspect ratio of\n * the thumbnail bounding box, then we return the thumbHeight parameter unchanged.\n * Otherwise we return the thumbHeight parameter scaled down appropriately to\n * reflect the actual height the scaled thumbnail occupies.\n *\n * This is very useful for calculating how much height a thumbnail will actually\n * consume in the timeline, when performing scroll offset calculations\n * (e.g. scroll locking)\n */\nexport function thumbHeight(fullWidth: number, fullHeight: number, thumbWidth: number, thumbHeight: number): number;\nexport function thumbHeight(\n    fullWidth: number | undefined,\n    fullHeight: number | undefined,\n    thumbWidth: number,\n    thumbHeight: number,\n): null;\nexport function thumbHeight(\n    fullWidth: number | undefined,\n    fullHeight: number | undefined,\n    thumbWidth: number,\n    thumbHeight: number,\n): number | null {\n    if (!fullWidth || !fullHeight) {\n        // Cannot calculate thumbnail height for image: missing w/h in metadata. We can't even\n        // log this because it's spammy\n        return null;\n    }\n    if (fullWidth < thumbWidth && fullHeight < thumbHeight) {\n        // no scaling needs to be applied\n        return fullHeight;\n    }\n    const widthMulti = thumbWidth / fullWidth;\n    const heightMulti = thumbHeight / fullHeight;\n    if (widthMulti < heightMulti) {\n        // width is the dominant dimension so scaling will be fixed on that\n        return Math.floor(widthMulti * fullHeight);\n    } else {\n        // height is the dominant dimension so scaling will be fixed on that\n        return Math.floor(heightMulti * fullHeight);\n    }\n}\n","/*\nCopyright 2024, 2025 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useContext } from \"react\";\nimport { type MatrixEvent, MatrixError, type IPreviewUrlResponse, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport CloseIcon from \"@vector-im/compound-design-tokens/assets/web/icons/close\";\n\nimport { useStateToggle } from \"../../../hooks/useStateToggle\";\nimport LinkPreviewWidget from \"./LinkPreviewWidget\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport { _t } from \"../../../languageHandler\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { useAsyncMemo } from \"../../../hooks/useAsyncMemo\";\nimport { useMediaVisible } from \"../../../hooks/useMediaVisible\";\n\nconst INITIAL_NUM_PREVIEWS = 2;\n\ninterface IProps {\n    links: string[]; // the URLs to be previewed\n    mxEvent: MatrixEvent; // the Event associated with the preview\n    onCancelClick(): void; // called when the preview's cancel ('hide') button is clicked\n}\n\nconst LinkPreviewGroup: React.FC<IProps> = ({ links, mxEvent, onCancelClick }) => {\n    const cli = useContext(MatrixClientContext);\n    const [expanded, toggleExpanded] = useStateToggle();\n    const [mediaVisible] = useMediaVisible(mxEvent);\n\n    const ts = mxEvent.getTs();\n    const previews = useAsyncMemo<[string, IPreviewUrlResponse][]>(\n        async () => {\n            return fetchPreviews(cli, links, ts);\n        },\n        [links, ts],\n        [],\n    );\n\n    const showPreviews = expanded ? previews : previews.slice(0, INITIAL_NUM_PREVIEWS);\n\n    let toggleButton: JSX.Element | undefined;\n    if (previews.length > INITIAL_NUM_PREVIEWS) {\n        toggleButton = (\n            <AccessibleButton onClick={toggleExpanded}>\n                {expanded\n                    ? _t(\"action|collapse\")\n                    : _t(\"timeline|url_preview|show_n_more\", { count: previews.length - showPreviews.length })}\n            </AccessibleButton>\n        );\n    }\n\n    return (\n        <div className=\"mx_LinkPreviewGroup\">\n            {showPreviews.map(([link, preview], i) => (\n                <LinkPreviewWidget\n                    mediaVisible={mediaVisible}\n                    key={link}\n                    link={link}\n                    preview={preview}\n                    mxEvent={mxEvent}\n                >\n                    {i === 0 ? (\n                        <AccessibleButton\n                            className=\"mx_LinkPreviewGroup_hide\"\n                            onClick={onCancelClick}\n                            aria-label={_t(\"timeline|url_preview|close\")}\n                        >\n                            <CloseIcon width=\"20px\" height=\"20px\" />\n                        </AccessibleButton>\n                    ) : undefined}\n                </LinkPreviewWidget>\n            ))}\n            {toggleButton}\n        </div>\n    );\n};\n\nconst fetchPreviews = (cli: MatrixClient, links: string[], ts: number): Promise<[string, IPreviewUrlResponse][]> => {\n    return Promise.all<[string, IPreviewUrlResponse] | void>(\n        links.map(async (link): Promise<[string, IPreviewUrlResponse] | undefined> => {\n            try {\n                const preview = await cli.getUrlPreview(link, ts);\n                // Ensure at least one of the rendered fields is truthy\n                if (\n                    preview?.[\"og:image\"]?.startsWith(\"mxc://\") ||\n                    !!preview?.[\"og:description\"] ||\n                    !!preview?.[\"og:title\"]\n                ) {\n                    return [link, preview];\n                }\n            } catch (error) {\n                if (error instanceof MatrixError && error.httpStatus === 404) {\n                    // Quieten 404 Not found errors, not all URLs can have a preview generated\n                    logger.debug(\"Failed to get URL preview: \", error);\n                } else {\n                    logger.error(\"Failed to get URL preview: \", error);\n                }\n            }\n        }),\n    ).then((a) => a.filter(Boolean)) as Promise<[string, IPreviewUrlResponse][]>;\n};\n\nexport default LinkPreviewGroup;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, createRef, type SyntheticEvent, type MouseEvent } from \"react\";\nimport { MsgType } from \"matrix-js-sdk/src/matrix\";\n\nimport EventContentBody from \"./EventContentBody.tsx\";\nimport { formatDate } from \"../../../DateUtils\";\nimport Modal from \"../../../Modal\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { _t } from \"../../../languageHandler\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { IntegrationManagers } from \"../../../integrations/IntegrationManagers\";\nimport { isPermalinkHost, tryTransformPermalinkToLocalHref } from \"../../../utils/permalinks/Permalinks\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport QuestionDialog from \"../dialogs/QuestionDialog\";\nimport MessageEditHistoryDialog from \"../dialogs/MessageEditHistoryDialog\";\nimport EditMessageComposer from \"../rooms/EditMessageComposer\";\nimport LinkPreviewGroup from \"../rooms/LinkPreviewGroup\";\nimport { type IBodyProps } from \"./IBodyProps\";\nimport RoomContext from \"../../../contexts/RoomContext\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport { options as linkifyOpts } from \"../../../linkify-matrix\";\nimport { getParentEventId } from \"../../../utils/Reply\";\nimport { EditWysiwygComposer } from \"../rooms/wysiwyg_composer\";\nimport { type IEventTileOps } from \"../rooms/EventTile\";\n\ninterface IState {\n    // the URLs (if any) to be previewed with a LinkPreviewWidget inside this TextualBody.\n    links: string[];\n\n    // track whether the preview widget is hidden\n    widgetHidden: boolean;\n}\n\nexport default class TextualBody extends React.Component<IBodyProps, IState> {\n    private readonly contentRef = createRef<HTMLDivElement>();\n\n    public static contextType = RoomContext;\n    declare public context: React.ContextType<typeof RoomContext>;\n\n    public state = {\n        links: [],\n        widgetHidden: false,\n    };\n\n    public componentDidMount(): void {\n        if (!this.props.editState) {\n            this.applyFormatting();\n        }\n    }\n\n    private applyFormatting(): void {\n        this.calculateUrlPreview();\n    }\n\n    public componentDidUpdate(prevProps: Readonly<IBodyProps>): void {\n        if (!this.props.editState) {\n            const stoppedEditing = prevProps.editState && !this.props.editState;\n            const messageWasEdited = prevProps.replacingEventId !== this.props.replacingEventId;\n            const urlPreviewChanged = prevProps.showUrlPreview !== this.props.showUrlPreview;\n            if (messageWasEdited || stoppedEditing || urlPreviewChanged) {\n                this.applyFormatting();\n            }\n        }\n    }\n\n    public shouldComponentUpdate(nextProps: Readonly<IBodyProps>, nextState: Readonly<IState>): boolean {\n        //console.info(\"shouldComponentUpdate: ShowUrlPreview for %s is %s\", this.props.mxEvent.getId(), this.props.showUrlPreview);\n\n        // exploit that events are immutable :)\n        return (\n            nextProps.mxEvent.getId() !== this.props.mxEvent.getId() ||\n            nextProps.highlights !== this.props.highlights ||\n            nextProps.replacingEventId !== this.props.replacingEventId ||\n            nextProps.highlightLink !== this.props.highlightLink ||\n            nextProps.showUrlPreview !== this.props.showUrlPreview ||\n            nextProps.editState !== this.props.editState ||\n            nextState.links !== this.state.links ||\n            nextState.widgetHidden !== this.state.widgetHidden ||\n            nextProps.isSeeingThroughMessageHiddenForModeration !== this.props.isSeeingThroughMessageHiddenForModeration\n        );\n    }\n\n    private calculateUrlPreview(): void {\n        //console.info(\"calculateUrlPreview: ShowUrlPreview for %s is %s\", this.props.mxEvent.getId(), this.props.showUrlPreview);\n\n        if (this.props.showUrlPreview && this.contentRef.current) {\n            // pass only the first child which is the event tile otherwise this recurses on edited events\n            let links = this.findLinks([this.contentRef.current]);\n            if (links.length) {\n                // de-duplicate the links using a set here maintains the order\n                links = Array.from(new Set(links));\n                this.setState({ links });\n\n                // lazy-load the hidden state of the preview widget from localstorage\n                if (window.localStorage) {\n                    const hidden = !!window.localStorage.getItem(\"hide_preview_\" + this.props.mxEvent.getId());\n                    this.setState({ widgetHidden: hidden });\n                }\n            } else if (this.state.links.length) {\n                this.setState({ links: [] });\n            }\n        }\n    }\n\n    private findLinks(nodes: ArrayLike<Element>): string[] {\n        let links: string[] = [];\n\n        for (let i = 0; i < nodes.length; i++) {\n            const node = nodes[i];\n            if (node.tagName === \"A\" && node.getAttribute(\"href\")) {\n                if (this.isLinkPreviewable(node)) {\n                    links.push(node.getAttribute(\"href\")!);\n                }\n            } else if (node.tagName === \"PRE\" || node.tagName === \"CODE\" || node.tagName === \"BLOCKQUOTE\") {\n                continue;\n            } else if (node.children && node.children.length) {\n                links = links.concat(this.findLinks(node.children));\n            }\n        }\n        return links;\n    }\n\n    private isLinkPreviewable(node: Element): boolean {\n        // don't try to preview relative links\n        const href = node.getAttribute(\"href\") ?? \"\";\n        if (!href.startsWith(\"http://\") && !href.startsWith(\"https://\")) {\n            return false;\n        }\n\n        const url = node.getAttribute(\"href\");\n        const host = url?.match(/^https?:\\/\\/(.*?)(\\/|$)/)?.[1];\n\n        // never preview permalinks (if anything we should give a smart\n        // preview of the room/user they point to: nobody needs to be reminded\n        // what the matrix.to site looks like).\n        if (!host || isPermalinkHost(host)) return false;\n\n        // as a random heuristic to avoid highlighting things like \"foo.pl\"\n        // we require the linked text to either include a / (either from http://\n        // or from a full foo.bar/baz style schemeless URL) - or be a markdown-style\n        // link, in which case we check the target text differs from the link value.\n        // TODO: make this configurable?\n        if (node.textContent?.includes(\"/\")) {\n            return true;\n        }\n\n        if (node.textContent?.toLowerCase().trim().startsWith(host.toLowerCase())) {\n            // it's a \"foo.pl\" style link\n            return false;\n        } else {\n            // it's a [foo bar](http://foo.com) style link\n            return true;\n        }\n    }\n\n    private onCancelClick = (): void => {\n        this.setState({ widgetHidden: true });\n        // FIXME: persist this somewhere smarter than local storage\n        if (global.localStorage) {\n            global.localStorage.setItem(\"hide_preview_\" + this.props.mxEvent.getId(), \"1\");\n        }\n        this.forceUpdate();\n    };\n\n    private onEmoteSenderClick = (): void => {\n        const mxEvent = this.props.mxEvent;\n        dis.dispatch({\n            action: Action.ComposerInsert,\n            userId: mxEvent.getSender(),\n            timelineRenderingType: this.context.timelineRenderingType,\n        });\n    };\n\n    /**\n     * This acts as a fallback in-app navigation handler for any body links that\n     * were ignored as part of linkification because they were already links\n     * to start with (e.g. pills, links in the content).\n     */\n    private onBodyLinkClick = (e: MouseEvent): void => {\n        let target: HTMLLinkElement | null = e.target as HTMLLinkElement;\n        // links processed by linkifyjs have their own handler so don't handle those here\n        if (target.classList.contains(linkifyOpts.className as string)) return;\n        if (target.nodeName !== \"A\") {\n            // Jump to parent as the `<a>` may contain children, e.g. an anchor wrapping an inline code section\n            target = target.closest<HTMLLinkElement>(\"a\");\n        }\n        if (!target) return;\n\n        const localHref = tryTransformPermalinkToLocalHref(target.href);\n        if (localHref !== target.href) {\n            // it could be converted to a localHref -> therefore handle locally\n            e.preventDefault();\n            window.location.hash = localHref;\n        }\n    };\n\n    public getEventTileOps = (): IEventTileOps => ({\n        isWidgetHidden: () => {\n            return this.state.widgetHidden;\n        },\n\n        unhideWidget: () => {\n            this.setState({ widgetHidden: false });\n            if (global.localStorage) {\n                global.localStorage.removeItem(\"hide_preview_\" + this.props.mxEvent.getId());\n            }\n        },\n    });\n\n    private onStarterLinkClick = (starterLink: string, ev: SyntheticEvent): void => {\n        ev.preventDefault();\n        // We need to add on our scalar token to the starter link, but we may not have one!\n        // In addition, we can't fetch one on click and then go to it immediately as that\n        // is then treated as a popup!\n        // We can get around this by fetching one now and showing a \"confirmation dialog\" (hurr hurr)\n        // which requires the user to click through and THEN we can open the link in a new tab because\n        // the window.open command occurs in the same stack frame as the onClick callback.\n\n        const managers = IntegrationManagers.sharedInstance();\n        if (!managers.hasManager()) {\n            managers.openNoManagerDialog();\n            return;\n        }\n\n        // Go fetch a scalar token\n        const integrationManager = managers.getPrimaryManager();\n        const scalarClient = integrationManager?.getScalarClient();\n        scalarClient?.connect().then(() => {\n            const completeUrl = scalarClient.getStarterLink(starterLink);\n            const integrationsUrl = integrationManager!.uiUrl;\n            const { finished } = Modal.createDialog(QuestionDialog, {\n                title: _t(\"timeline|scalar_starter_link|dialog_title\"),\n                description: (\n                    <div>\n                        {_t(\"timeline|scalar_starter_link|dialog_description\", { integrationsUrl: integrationsUrl })}\n                    </div>\n                ),\n                button: _t(\"action|continue\"),\n            });\n\n            finished.then(([confirmed]) => {\n                if (!confirmed) {\n                    return;\n                }\n                const width = window.screen.width > 1024 ? 1024 : window.screen.width;\n                const height = window.screen.height > 800 ? 800 : window.screen.height;\n                const left = (window.screen.width - width) / 2;\n                const top = (window.screen.height - height) / 2;\n                const features = `height=${height}, width=${width}, top=${top}, left=${left},`;\n                const wnd = window.open(completeUrl, \"_blank\", features)!;\n                wnd.opener = null;\n            });\n        });\n    };\n\n    private openHistoryDialog = async (): Promise<void> => {\n        Modal.createDialog(MessageEditHistoryDialog, { mxEvent: this.props.mxEvent });\n    };\n\n    private renderEditedMarker(): JSX.Element {\n        const date = this.props.mxEvent.replacingEventDate();\n        const dateString = date && formatDate(date);\n\n        return (\n            <AccessibleButton\n                className=\"mx_EventTile_edited\"\n                onClick={this.openHistoryDialog}\n                aria-label={_t(\"timeline|edits|tooltip_label\", { date: dateString })}\n                title={_t(\"timeline|edits|tooltip_title\", { date: dateString })}\n                caption={_t(\"timeline|edits|tooltip_sub\")}\n            >\n                <span>{`(${_t(\"common|edited\")})`}</span>\n            </AccessibleButton>\n        );\n    }\n\n    /**\n     * Render a marker informing the user that, while they can see the message,\n     * it is hidden for other users.\n     */\n    private renderPendingModerationMarker(): JSX.Element {\n        let text;\n        const visibility = this.props.mxEvent.messageVisibility();\n        switch (visibility.visible) {\n            case true:\n                throw new Error(\"renderPendingModerationMarker should only be applied to hidden messages\");\n            case false:\n                if (visibility.reason) {\n                    text = _t(\"timeline|pending_moderation_reason\", { reason: visibility.reason });\n                } else {\n                    text = _t(\"timeline|pending_moderation\");\n                }\n                break;\n        }\n        return <span className=\"mx_EventTile_pendingModeration\">{`(${text})`}</span>;\n    }\n\n    public render(): React.ReactNode {\n        if (this.props.editState) {\n            const isWysiwygComposerEnabled = SettingsStore.getValue(\"feature_wysiwyg_composer\");\n            return isWysiwygComposerEnabled ? (\n                <EditWysiwygComposer editorStateTransfer={this.props.editState} className=\"mx_EventTile_content\" />\n            ) : (\n                <EditMessageComposer editState={this.props.editState} className=\"mx_EventTile_content\" />\n            );\n        }\n        const mxEvent = this.props.mxEvent;\n        const content = mxEvent.getContent();\n        const isNotice = content.msgtype === MsgType.Notice;\n        const isEmote = content.msgtype === MsgType.Emote;\n        const isCaption = [MsgType.Image, MsgType.File, MsgType.Audio, MsgType.Video].includes(\n            content.msgtype as MsgType,\n        );\n\n        const willHaveWrapper =\n            this.props.replacingEventId || this.props.isSeeingThroughMessageHiddenForModeration || isEmote;\n        // only strip reply if this is the original replying event, edits thereafter do not have the fallback\n        const stripReply = !mxEvent.replacingEvent() && !!getParentEventId(mxEvent);\n        let body = (\n            <EventContentBody\n                as={willHaveWrapper ? \"span\" : \"div\"}\n                includeDir={false}\n                mxEvent={mxEvent}\n                content={content}\n                stripReply={stripReply}\n                linkify\n                highlights={this.props.highlights}\n                ref={this.contentRef}\n                renderTooltipsForAmbiguousLinks\n                renderKeywordPills\n                renderMentionPills\n                renderCodeBlocks\n                renderSpoilers\n            />\n        );\n\n        if (this.props.replacingEventId) {\n            body = (\n                <div dir=\"auto\" className=\"mx_EventTile_annotated\">\n                    {body}\n                    {this.renderEditedMarker()}\n                </div>\n            );\n        }\n        if (this.props.isSeeingThroughMessageHiddenForModeration) {\n            body = (\n                <div dir=\"auto\" className=\"mx_EventTile_annotated\">\n                    {body}\n                    {this.renderPendingModerationMarker()}\n                </div>\n            );\n        }\n\n        if (this.props.highlightLink) {\n            body = <a href={this.props.highlightLink}>{body}</a>;\n        } else if (content.data && typeof content.data[\"org.matrix.neb.starter_link\"] === \"string\") {\n            body = (\n                <AccessibleButton\n                    kind=\"link_inline\"\n                    onClick={this.onStarterLinkClick.bind(this, content.data[\"org.matrix.neb.starter_link\"])}\n                >\n                    {body}\n                </AccessibleButton>\n            );\n        }\n\n        let widgets;\n        if (this.state.links.length && !this.state.widgetHidden && this.props.showUrlPreview) {\n            widgets = (\n                <LinkPreviewGroup\n                    links={this.state.links}\n                    mxEvent={this.props.mxEvent}\n                    onCancelClick={this.onCancelClick}\n                />\n            );\n        }\n\n        if (isEmote) {\n            return (\n                <div\n                    id={this.props.id}\n                    className=\"mx_MEmoteBody mx_EventTile_content\"\n                    onClick={this.onBodyLinkClick}\n                    dir=\"auto\"\n                >\n                    *&nbsp;\n                    <span className=\"mx_MEmoteBody_sender\" onClick={this.onEmoteSenderClick}>\n                        {mxEvent.sender ? mxEvent.sender.name : mxEvent.getSender()}\n                    </span>\n                    &nbsp;\n                    {body}\n                    {widgets}\n                </div>\n            );\n        }\n        if (isNotice) {\n            return (\n                <div id={this.props.id} className=\"mx_MNoticeBody mx_EventTile_content\" onClick={this.onBodyLinkClick}>\n                    {body}\n                    {widgets}\n                </div>\n            );\n        }\n        if (isCaption) {\n            return (\n                <div id={this.props.id} className=\"mx_MTextBody mx_EventTile_caption\" onClick={this.onBodyLinkClick}>\n                    {body}\n                    {widgets}\n                </div>\n            );\n        }\n        return (\n            <div id={this.props.id} className=\"mx_MTextBody mx_EventTile_content\" onClick={this.onBodyLinkClick}>\n                {body}\n                {widgets}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport MAudioBody from \"./MAudioBody\";\nimport MVoiceMessageBody from \"./MVoiceMessageBody\";\nimport { type IBodyProps } from \"./IBodyProps\";\nimport { isVoiceMessage } from \"../../../utils/EventUtils\";\n\nexport default class MVoiceOrAudioBody extends React.PureComponent<IBodyProps> {\n    public render(): React.ReactNode {\n        if (!this.props.forExport && isVoiceMessage(this.props.mxEvent)) {\n            return <MVoiceMessageBody {...this.props} />;\n        } else {\n            return <MAudioBody {...this.props} />;\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode } from \"react\";\nimport { decode } from \"blurhash\";\nimport { type MediaEventContent } from \"matrix-js-sdk/src/types\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { _t } from \"../../../languageHandler\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport InlineSpinner from \"../elements/InlineSpinner\";\nimport { mediaFromContent } from \"../../../customisations/Media\";\nimport { BLURHASH_FIELD } from \"../../../utils/image-media\";\nimport { type IBodyProps } from \"./IBodyProps\";\nimport MFileBody from \"./MFileBody\";\nimport { type ImageSize, suggestedSize as suggestedVideoSize } from \"../../../settings/enums/ImageSize\";\nimport RoomContext, { TimelineRenderingType } from \"../../../contexts/RoomContext\";\nimport MediaProcessingError from \"./shared/MediaProcessingError\";\nimport { HiddenMediaPlaceholder } from \"./HiddenMediaPlaceholder\";\nimport { useMediaVisible } from \"../../../hooks/useMediaVisible\";\n\ninterface IState {\n    decryptedUrl: string | null;\n    decryptedThumbnailUrl: string | null;\n    decryptedBlob: Blob | null;\n    error?: any;\n    fetchingData: boolean;\n    posterLoading: boolean;\n    blurhashUrl: string | null;\n}\n\ninterface IProps extends IBodyProps {\n    /**\n     * Should the media be behind a preview.\n     */\n    mediaVisible: boolean;\n    /**\n     * Set the visibility of the media event.\n     * @param visible Should the event be visible.\n     */\n    setMediaVisible: (visible: boolean) => void;\n}\n\nclass MVideoBodyInner extends React.PureComponent<IProps, IState> {\n    public static contextType = RoomContext;\n    declare public context: React.ContextType<typeof RoomContext>;\n\n    private videoRef = React.createRef<HTMLVideoElement>();\n    private sizeWatcher?: string;\n\n    public state = {\n        fetchingData: false,\n        decryptedUrl: null,\n        decryptedThumbnailUrl: null,\n        decryptedBlob: null,\n        error: null,\n        posterLoading: false,\n        blurhashUrl: null,\n    };\n\n    private onClick = (): void => {\n        this.props.setMediaVisible(true);\n    };\n\n    private getContentUrl(): string | undefined {\n        const content = this.props.mxEvent.getContent<MediaEventContent>();\n        // During export, the content url will point to the MSC, which will later point to a local url\n        if (this.props.forExport) return content.file?.url ?? content.url;\n        const media = mediaFromContent(content);\n        if (media.isEncrypted) {\n            return this.state.decryptedUrl ?? undefined;\n        } else {\n            return media.srcHttp ?? undefined;\n        }\n    }\n\n    private hasContentUrl(): boolean {\n        const url = this.getContentUrl();\n        return !!url && !url.startsWith(\"data:\");\n    }\n\n    private getThumbUrl(): string | null {\n        // there's no need of thumbnail when the content is local\n        if (this.props.forExport) return null;\n\n        const content = this.props.mxEvent.getContent<MediaEventContent>();\n        const media = mediaFromContent(content);\n\n        if (media.isEncrypted && this.state.decryptedThumbnailUrl) {\n            return this.state.decryptedThumbnailUrl;\n        } else if (this.state.posterLoading) {\n            return this.state.blurhashUrl;\n        } else if (media.hasThumbnail) {\n            return media.thumbnailHttp;\n        } else {\n            return null;\n        }\n    }\n\n    private loadBlurhash(): void {\n        const info = this.props.mxEvent.getContent()?.info;\n        if (!info[BLURHASH_FIELD]) return;\n\n        const canvas = document.createElement(\"canvas\");\n\n        const { w: width, h: height } = suggestedVideoSize(SettingsStore.getValue(\"Images.size\") as ImageSize, {\n            w: info.w,\n            h: info.h,\n        });\n\n        canvas.width = width;\n        canvas.height = height;\n\n        const pixels = decode(info[BLURHASH_FIELD], width, height);\n        const ctx = canvas.getContext(\"2d\")!;\n        const imgData = ctx.createImageData(width, height);\n        imgData.data.set(pixels);\n        ctx.putImageData(imgData, 0, 0);\n\n        this.setState({\n            blurhashUrl: canvas.toDataURL(),\n            posterLoading: true,\n        });\n\n        const content = this.props.mxEvent.getContent<MediaEventContent>();\n        const media = mediaFromContent(content);\n        if (media.hasThumbnail) {\n            const image = new Image();\n            image.onload = () => {\n                this.setState({ posterLoading: false });\n            };\n            image.src = media.thumbnailHttp!;\n        }\n    }\n\n    private async downloadVideo(): Promise<void> {\n        try {\n            this.loadBlurhash();\n        } catch (e) {\n            logger.error(\"Failed to load blurhash\", e);\n        }\n\n        if (this.props.mediaEventHelper?.media.isEncrypted && this.state.decryptedUrl === null) {\n            try {\n                const autoplay = SettingsStore.getValue(\"autoplayVideo\") as boolean;\n                const thumbnailUrl = await this.props.mediaEventHelper.thumbnailUrl.value;\n                if (autoplay) {\n                    logger.log(\"Preloading video\");\n                    this.setState({\n                        decryptedUrl: await this.props.mediaEventHelper.sourceUrl.value,\n                        decryptedThumbnailUrl: thumbnailUrl,\n                        decryptedBlob: await this.props.mediaEventHelper.sourceBlob.value,\n                    });\n                } else {\n                    logger.log(\"NOT preloading video\");\n                    const content = this.props.mxEvent.getContent<MediaEventContent>();\n\n                    let mimetype = content?.info?.mimetype;\n\n                    // clobber quicktime muxed files to be considered MP4 so browsers\n                    // are willing to play them\n                    if (mimetype == \"video/quicktime\") {\n                        mimetype = \"video/mp4\";\n                    }\n\n                    this.setState({\n                        // For Chrome and Electron, we need to set some non-empty `src` to\n                        // enable the play button. Firefox does not seem to care either\n                        // way, so it's fine to do for all browsers.\n                        decryptedUrl: `data:${mimetype},`,\n                        decryptedThumbnailUrl: thumbnailUrl || `data:${mimetype},`,\n                        decryptedBlob: null,\n                    });\n                }\n            } catch (err) {\n                logger.warn(\"Unable to decrypt attachment: \", err);\n                // Set a placeholder image when we can't decrypt the image.\n                this.setState({\n                    error: err,\n                });\n            }\n        }\n    }\n\n    public async componentDidMount(): Promise<void> {\n        this.sizeWatcher = SettingsStore.watchSetting(\"Images.size\", null, () => {\n            this.forceUpdate(); // we don't really have a reliable thing to update, so just update the whole thing\n        });\n\n        // Do not attempt to load the media if we do not want to show previews here.\n        if (this.props.mediaVisible) {\n            await this.downloadVideo();\n        }\n    }\n\n    public async componentDidUpdate(prevProps: Readonly<IProps>): Promise<void> {\n        if (!prevProps.mediaVisible && this.props.mediaVisible) {\n            await this.downloadVideo();\n        }\n    }\n\n    public componentWillUnmount(): void {\n        SettingsStore.unwatchSetting(this.sizeWatcher);\n    }\n\n    private videoOnPlay = async (): Promise<void> => {\n        if (this.hasContentUrl() || this.state.fetchingData || this.state.error) {\n            // We have the file, we are fetching the file, or there is an error.\n            return;\n        }\n        this.setState({\n            // To stop subsequent download attempts\n            fetchingData: true,\n        });\n        if (!this.props.mediaEventHelper!.media.isEncrypted) {\n            this.setState({\n                error: \"No file given in content\",\n            });\n            return;\n        }\n        this.setState(\n            {\n                decryptedUrl: await this.props.mediaEventHelper!.sourceUrl.value,\n                decryptedBlob: await this.props.mediaEventHelper!.sourceBlob.value,\n                fetchingData: false,\n            },\n            () => {\n                if (!this.videoRef.current) return;\n                this.videoRef.current.play();\n            },\n        );\n    };\n\n    protected get showFileBody(): boolean {\n        return (\n            this.context.timelineRenderingType !== TimelineRenderingType.Room &&\n            this.context.timelineRenderingType !== TimelineRenderingType.Pinned &&\n            this.context.timelineRenderingType !== TimelineRenderingType.Search\n        );\n    }\n\n    private getFileBody = (): ReactNode => {\n        if (this.props.forExport) return null;\n        return this.showFileBody && <MFileBody {...this.props} showGenericPlaceholder={false} />;\n    };\n\n    public render(): React.ReactNode {\n        const content = this.props.mxEvent.getContent();\n        const autoplay = !this.props.inhibitInteraction && SettingsStore.getValue(\"autoplayVideo\");\n\n        let aspectRatio;\n        if (content.info?.w && content.info?.h) {\n            aspectRatio = `${content.info.w}/${content.info.h}`;\n        }\n        const { w: maxWidth, h: maxHeight } = suggestedVideoSize(SettingsStore.getValue(\"Images.size\") as ImageSize, {\n            w: content.info?.w,\n            h: content.info?.h,\n        });\n\n        // HACK: This div fills out space while the video loads, to prevent scroll jumps\n        const spaceFiller = <div style={{ width: maxWidth, height: maxHeight }} />;\n\n        if (this.state.error !== null) {\n            return (\n                <MediaProcessingError className=\"mx_MVideoBody\">\n                    {_t(\"timeline|m.video|error_decrypting\")}\n                </MediaProcessingError>\n            );\n        }\n\n        // Users may not even want to show a poster, so instead show a preview button.\n        if (!this.props.mediaVisible) {\n            return (\n                <span className=\"mx_MVideoBody\">\n                    <div\n                        className=\"mx_MVideoBody_container\"\n                        style={{ width: maxWidth, height: maxHeight, aspectRatio }}\n                    >\n                        <HiddenMediaPlaceholder onClick={this.onClick}>\n                            {_t(\"timeline|m.video|show_video\")}\n                        </HiddenMediaPlaceholder>\n                    </div>\n                </span>\n            );\n        }\n\n        // Important: If we aren't autoplaying and we haven't decrypted it yet, show a video with a poster.\n        if (!this.props.forExport && content.file !== undefined && this.state.decryptedUrl === null && autoplay) {\n            // Need to decrypt the attachment\n            // The attachment is decrypted in componentDidMount.\n            // For now show a spinner.\n            return (\n                <span className=\"mx_MVideoBody\">\n                    <div className=\"mx_MVideoBody_container\" style={{ maxWidth, maxHeight, aspectRatio }}>\n                        <InlineSpinner />\n                    </div>\n                    {spaceFiller}\n                </span>\n            );\n        }\n\n        const contentUrl = this.getContentUrl();\n        const thumbUrl = this.getThumbUrl();\n        let poster: string | undefined;\n        let preload = \"metadata\";\n        if (content.info && thumbUrl) {\n            poster = thumbUrl;\n            preload = \"none\";\n        }\n\n        const fileBody = this.getFileBody();\n        return (\n            <span className=\"mx_MVideoBody\">\n                <div className=\"mx_MVideoBody_container\" style={{ maxWidth, maxHeight, aspectRatio }}>\n                    <video\n                        className=\"mx_MVideoBody\"\n                        ref={this.videoRef}\n                        src={contentUrl}\n                        title={content.body}\n                        controls={!this.props.inhibitInteraction}\n                        // Disable downloading as it doesn't work with e2ee video,\n                        // users should use the dedicated Download button in the Message Action Bar\n                        controlsList=\"nodownload\"\n                        // The video uses a cross-origin request.\n                        // Firefox explicitly bypasses services workers for crossorigin\n                        // video elements without crossorigin attribute.\n                        crossOrigin=\"anonymous\"\n                        preload={preload}\n                        muted={autoplay}\n                        autoPlay={autoplay}\n                        poster={poster}\n                        onPlay={this.videoOnPlay}\n                    />\n                    {spaceFiller}\n                </div>\n                {fileBody}\n            </span>\n        );\n    }\n}\n\n// Wrap MVideoBody component so we can use a hook here.\nconst MVideoBody: React.FC<IBodyProps> = (props) => {\n    const [mediaVisible, setVisible] = useMediaVisible(props.mxEvent);\n    return <MVideoBodyInner mediaVisible={mediaVisible} setMediaVisible={setVisible} {...props} />;\n};\n\nexport default MVideoBody;\n","/*\nCopyright 2018-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ComponentProps, type ReactNode } from \"react\";\nimport { type Tooltip } from \"@vector-im/compound-web\";\nimport { type MediaEventContent } from \"matrix-js-sdk/src/types\";\n\nimport { MImageBodyInner } from \"./MImageBody\";\nimport { BLURHASH_FIELD } from \"../../../utils/image-media\";\nimport IconsShowStickersSvg from \"../../../../res/img/icons-show-stickers.svg\";\nimport { type IBodyProps } from \"./IBodyProps\";\nimport { useMediaVisible } from \"../../../hooks/useMediaVisible\";\n\nclass MStickerBodyInner extends MImageBodyInner {\n    // Mostly empty to prevent default behaviour of MImageBody\n    protected onClick = (ev: React.MouseEvent): void => {\n        ev.preventDefault();\n        if (!this.props.mediaVisible) {\n            this.props.setMediaVisible(true);\n        }\n    };\n\n    // MStickerBody doesn't need a wrapping `<a href=...>`, but it does need extra padding\n    // which is added by mx_MStickerBody_wrapper\n    protected wrapImage(contentUrl: string, children: React.ReactNode): JSX.Element {\n        let onClick: React.MouseEventHandler | undefined;\n        if (!this.props.mediaVisible) {\n            onClick = this.onClick;\n        }\n        return (\n            <div className=\"mx_MStickerBody_wrapper\" onClick={onClick}>\n                {\" \"}\n                {children}{\" \"}\n            </div>\n        );\n    }\n\n    // Placeholder to show in place of the sticker image if img onLoad hasn't fired yet.\n    protected getPlaceholder(width: number, height: number): ReactNode {\n        if (this.props.mxEvent.getContent().info?.[BLURHASH_FIELD]) return super.getPlaceholder(width, height);\n        return (\n            <img\n                aria-hidden\n                alt=\"\"\n                className=\"mx_MStickerBody_placeholder\"\n                src={IconsShowStickersSvg}\n                width=\"80\"\n                height=\"80\"\n                onMouseEnter={this.onImageEnter}\n                onMouseLeave={this.onImageLeave}\n            />\n        );\n    }\n\n    // Tooltip to show on mouse over\n    protected getTooltipProps(): ComponentProps<typeof Tooltip> | null {\n        const content = this.props.mxEvent && this.props.mxEvent.getContent();\n\n        if (!content?.body || !content.info?.w) return null;\n\n        return {\n            placement: \"right\",\n            description: content.body,\n        };\n    }\n\n    // Don't show \"Download this_file.png ...\"\n    protected getFileBody(): ReactNode {\n        return null;\n    }\n\n    protected getBanner(content: MediaEventContent): ReactNode {\n        return null; // we don't need a banner, we have a tooltip\n    }\n}\n\nconst MStickerBody: React.FC<IBodyProps> = (props) => {\n    const [mediaVisible, setVisible] = useMediaVisible(props.mxEvent);\n    return <MStickerBodyInner mediaVisible={mediaVisible} setMediaVisible={setVisible} {...props} />;\n};\n\nexport default MStickerBody;\n","var _path, _path2;\nfunction _extends() { return _extends = Object.assign ? Object.assign.bind() : function (n) { for (var e = 1; e < arguments.length; e++) { var t = arguments[e]; for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]); } return n; }, _extends.apply(null, arguments); }\nimport * as React from \"react\";\nimport { forwardRef } from \"react\";\nvar SvgIconsShowStickers = function SvgIconsShowStickers(props, ref) {\n  return /*#__PURE__*/React.createElement(\"svg\", _extends({\n    xmlns: \"http://www.w3.org/2000/svg\",\n    xmlSpace: \"preserve\",\n    viewBox: \"0 0 500 500\",\n    role: \"presentation\",\n    \"aria-hidden\": true,\n    ref: ref\n  }, props), _path || (_path = /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"#76CFA6\",\n    d: \"M250 500c138.571 0 250-111.43 250-250C500 111.429 388.571 0 250 0S0 111.429 0 250c0 138.57 111.429 250 250 250\",\n    opacity: 0.15\n  })), _path2 || (_path2 = /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"none\",\n    stroke: \"#76CFA6\",\n    strokeMiterlimit: 10,\n    strokeWidth: 12,\n    d: \"M249 430c-98.996 0-180-81.003-180-180 0-98.998 81.005-180 180-180 98.994 0 180 81.001 180 180 0 98.997-81.005 180-180 180zm72.8-200.8c17.685 0 31.201-13.518 31.201-31.2s-13.519-31.2-31.201-31.2-31.2 13.518-31.2 31.2 13.518 31.2 31.2 31.2zm-145.6 0c17.682 0 31.2-13.518 31.2-31.2s-13.519-31.2-31.2-31.2c-17.683 0-31.201 13.518-31.201 31.2s13.519 31.2 31.201 31.2zM249 364.4c48.883 0 89.436-30.164 106.081-72.801H142.919C159.564 334.236 200.117 364.4 249 364.4z\"\n  })));\n};\nvar ForwardRef = /*#__PURE__*/forwardRef(SvgIconsShowStickers);\nexport { ForwardRef as Icon };\nexport default \"img/icons-show-stickers.f790079.svg\";","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type MatrixEvent, ClientEvent, type ClientEventHandlerMap } from \"matrix-js-sdk/src/matrix\";\nimport { secureRandomString } from \"matrix-js-sdk/src/randomstring\";\nimport { Tooltip } from \"@vector-im/compound-web\";\n\nimport { _t } from \"../../../languageHandler\";\nimport Modal from \"../../../Modal\";\nimport {\n    locationEventGeoUri,\n    getLocationShareErrorMessage,\n    LocationShareError,\n    isSelfLocation,\n} from \"../../../utils/location\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { SmartMarker, Map, LocationViewDialog } from \"../location\";\nimport { type IBodyProps } from \"./IBodyProps\";\nimport { createReconnectedListener } from \"../../../utils/connection\";\n\ninterface IState {\n    error?: Error;\n}\n\nexport default class MLocationBody extends React.Component<IBodyProps, IState> {\n    public static contextType = MatrixClientContext;\n    declare public context: React.ContextType<typeof MatrixClientContext>;\n\n    private unmounted = false;\n    private mapId: string;\n    private reconnectedListener: ClientEventHandlerMap[ClientEvent.Sync];\n\n    public constructor(props: IBodyProps) {\n        super(props);\n\n        // multiple instances of same map might be in document\n        // eg thread and main timeline, reply\n        const idSuffix = `${props.mxEvent.getId()}_${secureRandomString(8)}`;\n        this.mapId = `mx_MLocationBody_${idSuffix}`;\n\n        this.reconnectedListener = createReconnectedListener(this.clearError);\n\n        this.state = {};\n    }\n\n    private onClick = (): void => {\n        Modal.createDialog(\n            LocationViewDialog,\n            {\n                matrixClient: this.context,\n                mxEvent: this.props.mxEvent,\n            },\n            \"mx_LocationViewDialog_wrapper\",\n            false, // isPriority\n            true, // isStatic\n        );\n    };\n\n    private clearError = (): void => {\n        this.context.off(ClientEvent.Sync, this.reconnectedListener);\n        this.setState({ error: undefined });\n    };\n\n    private onError = (error: Error): void => {\n        if (this.unmounted) return;\n        this.setState({ error });\n        // Unregister first in case we already had it registered\n        this.context.off(ClientEvent.Sync, this.reconnectedListener);\n        this.context.on(ClientEvent.Sync, this.reconnectedListener);\n    };\n\n    public componentDidMount(): void {\n        this.unmounted = false;\n    }\n\n    public componentWillUnmount(): void {\n        this.unmounted = true;\n        this.context.off(ClientEvent.Sync, this.reconnectedListener);\n    }\n\n    public render(): React.ReactElement<HTMLDivElement> {\n        return this.state.error ? (\n            <LocationBodyFallbackContent error={this.state.error} event={this.props.mxEvent} />\n        ) : (\n            <LocationBodyContent\n                mxEvent={this.props.mxEvent}\n                mapId={this.mapId}\n                onError={this.onError}\n                tooltip={_t(\"location_sharing|expand_map\")}\n                onClick={this.onClick}\n            />\n        );\n    }\n}\n\nexport const LocationBodyFallbackContent: React.FC<{ event: MatrixEvent; error: Error }> = ({ error, event }) => {\n    const errorType = error?.message as LocationShareError;\n    const message = `${_t(\"location_sharing|failed_load_map\")}: ${getLocationShareErrorMessage(errorType)}`;\n\n    const locationFallback = isSelfLocation(event.getContent())\n        ? _t(\"timeline|m.location|self_location\") + event.getContent()?.body\n        : _t(\"timeline|m.location|location\") + event.getContent()?.body;\n\n    return (\n        <div className=\"mx_EventTile_body mx_MLocationBody\">\n            <span className={errorType !== LocationShareError.MapStyleUrlNotConfigured ? \"mx_EventTile_tileError\" : \"\"}>\n                {message}\n            </span>\n            <br />\n            {locationFallback}\n        </div>\n    );\n};\n\ninterface LocationBodyContentProps {\n    mxEvent: MatrixEvent;\n    mapId: string;\n    tooltip: string;\n    onError: (error: Error) => void;\n    onClick?: () => void;\n}\nexport const LocationBodyContent: React.FC<LocationBodyContentProps> = ({\n    mxEvent,\n    mapId,\n    tooltip,\n    onError,\n    onClick,\n}) => {\n    // only pass member to marker when should render avatar marker\n    const markerRoomMember = isSelfLocation(mxEvent.getContent()) ? mxEvent.sender : undefined;\n    const geoUri = locationEventGeoUri(mxEvent);\n\n    const mapElement = (\n        <Map id={mapId} centerGeoUri={geoUri} onClick={onClick} onError={onError} className=\"mx_MLocationBody_map\">\n            {({ map }) => (\n                <SmartMarker\n                    map={map}\n                    id={`${mapId}-marker`}\n                    geoUri={geoUri}\n                    roomMember={markerRoomMember ?? undefined}\n                />\n            )}\n        </Map>\n    );\n\n    return (\n        <div className=\"mx_MLocationBody\">\n            <Tooltip label={tooltip}>\n                <div className=\"mx_MLocationBody_map\">{mapElement}</div>\n            </Tooltip>\n        </div>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\nimport AccessibleButton, { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport { type IBodyProps } from \"./IBodyProps\";\n\nexport default class MjolnirBody extends React.Component<IBodyProps> {\n    private onAllowClick = (e: ButtonEvent): void => {\n        e.preventDefault();\n        e.stopPropagation();\n\n        const key = `mx_mjolnir_render_${this.props.mxEvent.getRoomId()}__${this.props.mxEvent.getId()}`;\n        localStorage.setItem(key, \"true\");\n        this.props.onMessageAllowed?.();\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <div className=\"mx_MjolnirBody\">\n                <i>\n                    {_t(\n                        \"timeline|mjolnir|message_hidden\",\n                        {},\n                        {\n                            a: (sub) => (\n                                <AccessibleButton kind=\"link_inline\" onClick={this.onAllowClick}>\n                                    {sub}\n                                </AccessibleButton>\n                            ),\n                        },\n                    )}\n                </i>\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// Exports beacon components which touch maplibre-gs wrapped in React Suspense to enable code splitting\n\nimport React, { type JSX, type ComponentProps, lazy, Suspense } from \"react\";\n\nimport Spinner from \"../elements/Spinner\";\n\nconst BeaconViewDialogComponent = lazy(() => import(\"./BeaconViewDialog\"));\n\nexport function BeaconViewDialog(props: ComponentProps<typeof BeaconViewDialogComponent>): JSX.Element {\n    return (\n        <Suspense fallback={<Spinner />}>\n            <BeaconViewDialogComponent {...props} />\n        </Suspense>\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useCallback, useContext, useEffect, useState } from \"react\";\nimport {\n    type Beacon,\n    BeaconEvent,\n    type MatrixEvent,\n    MatrixEventEvent,\n    type MatrixClient,\n    RelationType,\n    type IRedactOpts,\n    type ContentHelpers,\n    M_BEACON,\n} from \"matrix-js-sdk/src/matrix\";\nimport { secureRandomString } from \"matrix-js-sdk/src/randomstring\";\nimport classNames from \"classnames\";\n\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { useEventEmitterState } from \"../../../hooks/useEventEmitter\";\nimport { _t } from \"../../../languageHandler\";\nimport Modal from \"../../../Modal\";\nimport { isBeaconWaitingToStart, useBeacon } from \"../../../utils/beacon\";\nimport { isSelfLocation, LocationShareError } from \"../../../utils/location\";\nimport { BeaconDisplayStatus, getBeaconDisplayStatus } from \"../beacon/displayStatus\";\nimport BeaconStatus from \"../beacon/BeaconStatus\";\nimport OwnBeaconStatus from \"../beacon/OwnBeaconStatus\";\nimport { Map, SmartMarker } from \"../location\";\nimport { MapError } from \"../location/MapError\";\nimport MapFallback from \"../location/MapFallback\";\nimport { type GetRelationsForEvent } from \"../rooms/EventTile\";\nimport { BeaconViewDialog } from \"../beacon\";\nimport { type IBodyProps } from \"./IBodyProps\";\n\nconst useBeaconState = (\n    beaconInfoEvent: MatrixEvent,\n): {\n    beacon?: Beacon;\n    description?: string;\n    latestLocationState?: ContentHelpers.BeaconLocationState;\n    isLive?: boolean;\n    waitingToStart?: boolean;\n} => {\n    const beacon = useBeacon(beaconInfoEvent);\n\n    const isLive = useEventEmitterState(beacon, BeaconEvent.LivenessChange, () => beacon?.isLive);\n\n    const latestLocationState = useEventEmitterState(\n        beacon,\n        BeaconEvent.LocationUpdate,\n        () => beacon?.latestLocationState,\n    );\n\n    if (!beacon) {\n        return {};\n    }\n\n    // a beacon's starting timestamp can be in the future\n    // (either from small deviations in system clock times, or on purpose from another client)\n    // a beacon is only live between its start timestamp and expiry\n    // detect when a beacon is waiting to become live\n    // and display a loading state\n    const waitingToStart = !!beacon && isBeaconWaitingToStart(beacon);\n    const { description } = beacon.beaconInfo;\n\n    return {\n        beacon,\n        description,\n        isLive,\n        waitingToStart,\n        latestLocationState,\n    };\n};\n\n// multiple instances of same map might be in document\n// eg thread and main timeline, reply\n// maplibregl needs a unique id to attach the map instance to\nconst useUniqueId = (eventId: string): string => {\n    const [id, setId] = useState(`${eventId}_${secureRandomString(8)}`);\n\n    useEffect(() => {\n        setId(`${eventId}_${secureRandomString(8)}`);\n    }, [eventId]);\n\n    return id;\n};\n\n// remove related beacon locations on beacon redaction\nconst useHandleBeaconRedaction = (\n    event: MatrixEvent,\n    matrixClient: MatrixClient,\n    getRelationsForEvent?: GetRelationsForEvent,\n): void => {\n    const onBeforeBeaconInfoRedaction = useCallback(\n        (_event: MatrixEvent, redactionEvent: MatrixEvent) => {\n            const relations = getRelationsForEvent\n                ? getRelationsForEvent(event.getId()!, RelationType.Reference, M_BEACON.name)\n                : undefined;\n\n            relations?.getRelations()?.forEach((locationEvent) => {\n                matrixClient.redactEvent(\n                    locationEvent.getRoomId()!,\n                    locationEvent.getId()!,\n                    undefined,\n                    redactionEvent.getContent<IRedactOpts>(),\n                );\n            });\n        },\n        [event, matrixClient, getRelationsForEvent],\n    );\n\n    useEffect(() => {\n        event.addListener(MatrixEventEvent.BeforeRedaction, onBeforeBeaconInfoRedaction);\n        return () => {\n            event.removeListener(MatrixEventEvent.BeforeRedaction, onBeforeBeaconInfoRedaction);\n        };\n    }, [event, onBeforeBeaconInfoRedaction]);\n};\n\nconst MBeaconBody = ({ mxEvent, getRelationsForEvent, ref }: IBodyProps): JSX.Element => {\n    const { beacon, isLive, latestLocationState, waitingToStart } = useBeaconState(mxEvent);\n    const mapId = useUniqueId(mxEvent.getId()!);\n\n    const matrixClient = useContext(MatrixClientContext);\n    const [error, setError] = useState<Error>();\n    const isMapDisplayError =\n        error?.message === LocationShareError.MapStyleUrlNotConfigured ||\n        error?.message === LocationShareError.MapStyleUrlNotReachable;\n    const displayStatus = getBeaconDisplayStatus(\n        !!isLive,\n        latestLocationState,\n        // if we are unable to display maps because it is not configured for the server\n        // don't display an error\n        isMapDisplayError ? undefined : error,\n        waitingToStart,\n    );\n    const markerRoomMember = isSelfLocation(mxEvent.getContent()) ? mxEvent.sender : undefined;\n    const isOwnBeacon = beacon?.beaconInfoOwner === matrixClient.getUserId();\n\n    useHandleBeaconRedaction(mxEvent, matrixClient, getRelationsForEvent);\n\n    const onClick = (): void => {\n        if (displayStatus !== BeaconDisplayStatus.Active) {\n            return;\n        }\n        Modal.createDialog(\n            BeaconViewDialog,\n            {\n                roomId: mxEvent.getRoomId()!,\n                matrixClient,\n                initialFocusedBeacon: beacon,\n            },\n            \"mx_BeaconViewDialog_wrapper\",\n            false, // isPriority\n            true, // isStatic\n        );\n    };\n\n    let map: JSX.Element;\n    if (displayStatus === BeaconDisplayStatus.Active && !isMapDisplayError && latestLocationState?.uri) {\n        map = (\n            <Map\n                id={mapId}\n                centerGeoUri={latestLocationState.uri}\n                onError={setError}\n                onClick={onClick}\n                className=\"mx_MBeaconBody_map\"\n            >\n                {({ map }) => (\n                    <SmartMarker\n                        map={map}\n                        id={`${mapId}-marker`}\n                        geoUri={latestLocationState.uri!}\n                        roomMember={markerRoomMember ?? undefined}\n                        useMemberColor\n                    />\n                )}\n            </Map>\n        );\n    } else if (isMapDisplayError) {\n        map = (\n            <MapError\n                error={error.message as LocationShareError}\n                onClick={onClick}\n                className={classNames(\n                    \"mx_MBeaconBody_mapError\",\n                    // set interactive class when maximised map can be opened\n                    { mx_MBeaconBody_mapErrorInteractive: displayStatus === BeaconDisplayStatus.Active },\n                )}\n                isMinimised\n            />\n        );\n    } else {\n        map = (\n            <MapFallback\n                isLoading={displayStatus === BeaconDisplayStatus.Loading}\n                className=\"mx_MBeaconBody_map mx_MBeaconBody_mapFallback\"\n            />\n        );\n    }\n\n    return (\n        <div className=\"mx_MBeaconBody\" ref={ref}>\n            {map}\n            {isOwnBeacon ? (\n                <OwnBeaconStatus\n                    className=\"mx_MBeaconBody_chin\"\n                    beacon={beacon}\n                    displayStatus={displayStatus}\n                    withIcon\n                />\n            ) : (\n                <BeaconStatus\n                    className=\"mx_MBeaconBody_chin\"\n                    beacon={beacon}\n                    displayStatus={displayStatus}\n                    label={_t(\"timeline|m.beacon_info|view_live_location\")}\n                    withIcon\n                />\n            )}\n        </div>\n    );\n};\n\nexport default MBeaconBody;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport mime from \"mime\";\nimport React, { type JSX, createRef, useContext, useEffect } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport {\n    EventType,\n    MsgType,\n    MatrixEventEvent,\n    M_BEACON_INFO,\n    M_LOCATION,\n    M_POLL_START,\n    type IContent,\n} from \"matrix-js-sdk/src/matrix\";\nimport { useCreateAutoDisposedViewModel, DecryptionFailureBodyView } from \"@element-hq/web-shared-components\";\n\nimport { LocalDeviceVerificationStateContext } from \"../../../contexts/LocalDeviceVerificationStateContext\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { Mjolnir } from \"../../../mjolnir/Mjolnir\";\nimport RedactedBody from \"./RedactedBody\";\nimport UnknownBody from \"./UnknownBody\";\nimport { type IMediaBody } from \"./IMediaBody\";\nimport { MediaEventHelper } from \"../../../utils/MediaEventHelper\";\nimport { type IBodyProps } from \"./IBodyProps\";\nimport TextualBody from \"./TextualBody\";\nimport MImageBody from \"./MImageBody\";\nimport MFileBody from \"./MFileBody\";\nimport MVoiceOrAudioBody from \"./MVoiceOrAudioBody\";\nimport MVideoBody from \"./MVideoBody\";\nimport MStickerBody from \"./MStickerBody\";\nimport MPollBody from \"./MPollBody\";\nimport MLocationBody from \"./MLocationBody\";\nimport MjolnirBody from \"./MjolnirBody\";\nimport MBeaconBody from \"./MBeaconBody\";\nimport { type GetRelationsForEvent, type IEventTileOps } from \"../rooms/EventTile\";\nimport { DecryptionFailureBodyViewModel } from \"../../../viewmodels/message-body/DecryptionFailureBodyViewModel\";\n\n// onMessageAllowed is handled internally\ninterface IProps extends Omit<IBodyProps, \"onMessageAllowed\" | \"mediaEventHelper\"> {\n    /* overrides for the msgtype-specific components, used by ReplyTile to override file rendering */\n    overrideBodyTypes?: Record<string, React.ComponentType<IBodyProps>>;\n    overrideEventTypes?: Record<string, React.ComponentType<IBodyProps>>;\n\n    // helper function to access relations for this event\n    getRelationsForEvent?: GetRelationsForEvent;\n\n    isSeeingThroughMessageHiddenForModeration?: boolean;\n\n    /**\n     * Optional ID for the root element.\n     */\n    id?: string;\n}\n\nexport interface IOperableEventTile {\n    getEventTileOps(): IEventTileOps | null;\n}\n\nconst baseBodyTypes = new Map<string, React.ComponentType<IBodyProps>>([\n    [MsgType.Text, TextualBody],\n    [MsgType.Notice, TextualBody],\n    [MsgType.Emote, TextualBody],\n    [MsgType.Image, MImageBody],\n    [MsgType.File, MFileBody],\n    [MsgType.Audio, MVoiceOrAudioBody],\n    [MsgType.Video, MVideoBody],\n]);\nconst baseEvTypes = new Map<string, React.ComponentType<IBodyProps>>([\n    [EventType.Sticker, MStickerBody],\n    [M_POLL_START.name, MPollBody],\n    [M_POLL_START.altName, MPollBody],\n    [M_BEACON_INFO.name, MBeaconBody],\n    [M_BEACON_INFO.altName, MBeaconBody],\n]);\n\nexport default class MessageEvent extends React.Component<IProps> implements IMediaBody, IOperableEventTile {\n    private body = createRef<React.Component | IOperableEventTile>();\n    private mediaHelper?: MediaEventHelper;\n    private bodyTypes = new Map<string, React.ComponentType<IBodyProps>>(baseBodyTypes.entries());\n    private evTypes = new Map<string, React.ComponentType<IBodyProps>>(baseEvTypes.entries());\n\n    public constructor(props: IProps) {\n        super(props);\n\n        if (MediaEventHelper.isEligible(this.props.mxEvent)) {\n            this.mediaHelper = new MediaEventHelper(this.props.mxEvent);\n        }\n\n        this.updateComponentMaps();\n    }\n\n    public componentDidMount(): void {\n        this.props.mxEvent.addListener(MatrixEventEvent.Decrypted, this.onDecrypted);\n    }\n\n    public componentWillUnmount(): void {\n        this.props.mxEvent.removeListener(MatrixEventEvent.Decrypted, this.onDecrypted);\n        this.mediaHelper?.destroy();\n    }\n\n    public componentDidUpdate(prevProps: Readonly<IProps>): void {\n        if (this.props.mxEvent !== prevProps.mxEvent && MediaEventHelper.isEligible(this.props.mxEvent)) {\n            this.mediaHelper?.destroy();\n            this.mediaHelper = new MediaEventHelper(this.props.mxEvent);\n        }\n\n        this.updateComponentMaps();\n    }\n\n    private updateComponentMaps(): void {\n        this.bodyTypes = new Map<string, React.ComponentType<IBodyProps>>(baseBodyTypes.entries());\n        for (const [bodyType, bodyComponent] of Object.entries(this.props.overrideBodyTypes ?? {})) {\n            this.bodyTypes.set(bodyType, bodyComponent);\n        }\n\n        this.evTypes = new Map<string, React.ComponentType<IBodyProps>>(baseEvTypes.entries());\n        for (const [evType, evComponent] of Object.entries(this.props.overrideEventTypes ?? {})) {\n            this.evTypes.set(evType, evComponent);\n        }\n    }\n\n    public getEventTileOps = (): IEventTileOps | null => {\n        return (this.body.current as IOperableEventTile)?.getEventTileOps?.() || null;\n    };\n\n    public getMediaHelper(): MediaEventHelper | undefined {\n        return this.mediaHelper;\n    }\n\n    private onDecrypted = (): void => {\n        // Recheck MediaEventHelper eligibility as it can change when the event gets decrypted\n        if (MediaEventHelper.isEligible(this.props.mxEvent)) {\n            this.mediaHelper?.destroy();\n            this.mediaHelper = new MediaEventHelper(this.props.mxEvent);\n        }\n    };\n\n    private onTileUpdate = (): void => {\n        this.forceUpdate();\n    };\n\n    /**\n     *  Validates that the filename extension and advertised mimetype\n     *  of the supplied image/file message content match and are actuallly video/image content.\n     *  For image/video messages with a thumbnail it also validates the mimetype is an image.\n     * @param content The mxEvent content of the message\n     * @returns A boolean indicating whether the validation passed\n     */\n    private validateImageOrVideoMimetype = (content: IContent): boolean => {\n        // As per the spec if filename is not present the body represents the filename\n        const filename = content.filename ?? content.body;\n        if (!filename) {\n            logger.log(\"Failed to validate image/video content, filename null\");\n            return false;\n        }\n        // Check mimetype of the thumbnail\n        if (!this.validateThumbnailMimetype(content)) {\n            logger.log(\"Failed to validate file/image thumbnail\");\n            return false;\n        }\n\n        // if there is no mimetype from the extesion or the mimetype is not image/video validation fails\n        const typeFromExtension = mime.getType(filename) ?? undefined;\n        const extensionMajorMimetype = this.parseMajorMimetype(typeFromExtension);\n        if (!typeFromExtension || !this.validateAllowedMimetype(typeFromExtension, [\"image\", \"video\"])) {\n            logger.log(\"Failed to validate image/video content, invalid or missing extension\");\n            return false;\n        }\n\n        // if the content mimetype is set check it is an image/video and that it matches the extesion mimetype otherwise validation fails\n        const contentMimetype = content.info?.mimetype;\n        if (contentMimetype) {\n            const contentMajorMimetype = this.parseMajorMimetype(contentMimetype);\n            if (\n                !this.validateAllowedMimetype(contentMimetype, [\"image\", \"video\"]) ||\n                extensionMajorMimetype !== contentMajorMimetype\n            ) {\n                logger.log(\"Failed to validate image/video content, invalid or missing mimetype\");\n                return false;\n            }\n        }\n        return true;\n    };\n\n    /**\n     *  Validates that the advertised mimetype of the sticker content\n     *  is an image.\n     *  For stickers with a thumbnail it also validates the mimetype is an image.\n     * @param content The mxEvent content of the message\n     * @returns A boolean indicating whether the validation passed\n     */\n    private validateStickerMimetype = (content: IContent): boolean => {\n        // Validate mimetype of the thumbnail\n        const thumbnailResult = this.validateThumbnailMimetype(content);\n        if (!thumbnailResult) {\n            logger.log(\"Failed to validate sticker thumbnail\");\n            return false;\n        }\n        // Validate mimetype of the content info is valid if it is set\n        const contentMimetype = content.info?.mimetype;\n        if (contentMimetype && !this.validateAllowedMimetype(contentMimetype, [\"image\"])) {\n            logger.log(\"Failed to validate image/video content, invalid or missing mimetype/extensions\");\n            return false;\n        }\n        return true;\n    };\n\n    /**\n     *  For image/video messages or stickers that have a thumnail mimetype specified,\n     *  validates that the major mimetime is image.\n     * @param content The mxEvent content of the message\n     * @returns A boolean indicating whether the validation passed\n     */\n    private validateThumbnailMimetype = (content: IContent): boolean => {\n        const thumbnailMimetype = content.info?.thumbnail_info?.mimetype;\n        return !thumbnailMimetype || this.validateAllowedMimetype(thumbnailMimetype, [\"image\"]);\n    };\n\n    /**\n     * Validates that the major part of a mimetime from an allowed list.\n     * @param mimetype The mimetype to validate\n     * @param allowedMajorMimeTypes The list of allowed major mimetimes\n     * @returns A boolean indicating whether the validation passed\n     */\n    private validateAllowedMimetype = (mimetype: string, allowedMajorMimeTypes: string[]): boolean => {\n        const majorMimetype = this.parseMajorMimetype(mimetype);\n        return !!majorMimetype && allowedMajorMimeTypes.includes(majorMimetype);\n    };\n\n    /**\n     * Parses and returns the the major part of a mimetype(before the \"/\").\n     * @param mimetype As optional mimetype string to parse\n     * @returns The major part of the mimetype string or undefined\n     */\n    private parseMajorMimetype(mimetype?: string): string | undefined {\n        return mimetype?.split(\"/\")[0];\n    }\n\n    public render(): React.ReactNode {\n        const content = this.props.mxEvent.getContent();\n        const type = this.props.mxEvent.getType();\n        const msgtype = content.msgtype;\n        let BodyType: React.ComponentType<IBodyProps> = RedactedBody;\n        if (!this.props.mxEvent.isRedacted()) {\n            // only resolve BodyType if event is not redacted\n            if (this.props.mxEvent.isDecryptionFailure()) {\n                BodyType = DecryptionFailureBodyWrapper;\n            } else if (type && this.evTypes.has(type)) {\n                BodyType = this.evTypes.get(type)!;\n            } else if (msgtype && this.bodyTypes.has(msgtype)) {\n                BodyType = this.bodyTypes.get(msgtype)!;\n            } else if (content.url) {\n                // Fallback to MFileBody if there's a content URL\n                BodyType = this.bodyTypes.get(MsgType.File)!;\n            } else {\n                // Fallback to UnknownBody otherwise if not redacted\n                BodyType = UnknownBody;\n            }\n\n            if (\n                ((BodyType === MImageBody || BodyType == MVideoBody) && !this.validateImageOrVideoMimetype(content)) ||\n                (BodyType === MStickerBody && !this.validateStickerMimetype(content))\n            ) {\n                BodyType = this.bodyTypes.get(MsgType.File)!;\n            }\n\n            // TODO: move to eventTypes when location sharing spec stabilises\n            if (M_LOCATION.matches(type) || (type === EventType.RoomMessage && msgtype === MsgType.Location)) {\n                BodyType = MLocationBody;\n            }\n        }\n\n        if (SettingsStore.getValue(\"feature_mjolnir\")) {\n            const key = `mx_mjolnir_render_${this.props.mxEvent.getRoomId()}__${this.props.mxEvent.getId()}`;\n            const allowRender = localStorage.getItem(key) === \"true\";\n\n            if (!allowRender) {\n                const userDomain = this.props.mxEvent.getSender()?.split(\":\").slice(1).join(\":\");\n                const userBanned = Mjolnir.sharedInstance().isUserBanned(this.props.mxEvent.getSender()!);\n                const serverBanned = userDomain && Mjolnir.sharedInstance().isServerBanned(userDomain);\n\n                if (userBanned || serverBanned) {\n                    BodyType = MjolnirBody;\n                }\n            }\n        }\n\n        const hasCaption =\n            [MsgType.Image, MsgType.File, MsgType.Audio, MsgType.Video].includes(msgtype as MsgType) &&\n            content.filename &&\n            content.filename !== content.body;\n        const bodyProps: IBodyProps = {\n            ref: this.body,\n            mxEvent: this.props.mxEvent,\n            highlights: this.props.highlights,\n            highlightLink: this.props.highlightLink,\n            showUrlPreview: this.props.showUrlPreview,\n            forExport: this.props.forExport,\n            maxImageHeight: this.props.maxImageHeight,\n            replacingEventId: this.props.replacingEventId,\n            editState: this.props.editState,\n            onMessageAllowed: this.onTileUpdate,\n            permalinkCreator: this.props.permalinkCreator,\n            mediaEventHelper: this.mediaHelper,\n            getRelationsForEvent: this.props.getRelationsForEvent,\n            isSeeingThroughMessageHiddenForModeration: this.props.isSeeingThroughMessageHiddenForModeration,\n            inhibitInteraction: this.props.inhibitInteraction,\n            id: this.props.id,\n        };\n        if (hasCaption) {\n            return <CaptionBody {...bodyProps} WrappedBodyType={BodyType} />;\n        }\n\n        return BodyType ? <BodyType {...bodyProps} /> : null;\n    }\n}\n\nconst CaptionBody: React.FunctionComponent<IBodyProps & { WrappedBodyType: React.ComponentType<IBodyProps> }> = ({\n    WrappedBodyType,\n    ...props\n}) => (\n    <div className=\"mx_EventTile_content\">\n        <WrappedBodyType {...props} />\n        <TextualBody {...{ ...props, ref: undefined }} />\n    </div>\n);\n\n/**\n * Bridge decryption-failure events into the view model using current local verification state.\n * This wrapper can be removed after MessageEvent has been changed to a function component.\n */\nfunction DecryptionFailureBodyWrapper({ mxEvent, ref }: IBodyProps): JSX.Element {\n    const verificationState = useContext(LocalDeviceVerificationStateContext);\n    const vm = useCreateAutoDisposedViewModel(\n        () =>\n            new DecryptionFailureBodyViewModel({\n                decryptionFailureCode: mxEvent.decryptionFailureReason,\n                verificationState,\n            }),\n    );\n    useEffect(() => {\n        vm.setVerificationState(verificationState);\n    }, [verificationState, vm]);\n    return <DecryptionFailureBodyView vm={vm} ref={ref} />;\n}\n","var _path;\nfunction _extends() { return _extends = Object.assign ? Object.assign.bind() : function (n) { for (var e = 1; e < arguments.length; e++) { var t = arguments[e]; for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]); } return n; }, _extends.apply(null, arguments); }\nimport * as React from \"react\";\nimport { forwardRef } from \"react\";\nvar SvgSensor = function SvgSensor(props, ref) {\n  return /*#__PURE__*/React.createElement(\"svg\", _extends({\n    xmlns: \"http://www.w3.org/2000/svg\",\n    fill: \"none\",\n    viewBox: \"0 0 12 12\",\n    role: \"presentation\",\n    \"aria-hidden\": true,\n    ref: ref\n  }, props), _path || (_path = /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"currentColor\",\n    d: \"M2.638 9.363a4.7 4.7 0 0 1-1.033-1.507 4.6 4.6 0 0 1-.374-1.848q0-.998.372-1.859a5 5 0 0 1 1.022-1.524l.588.587a4.1 4.1 0 0 0-.838 1.258 3.8 3.8 0 0 0-.306 1.525q0 .81.306 1.527t.85 1.253zM3.9 8.1a3.2 3.2 0 0 1-.633-.944 2.8 2.8 0 0 1-.236-1.15q0-.626.235-1.16A3.2 3.2 0 0 1 3.9 3.9l.588.587a2.3 2.3 0 0 0-.453.682q-.165.386-.166.833 0 .448.166.832.165.384.453.679zm2.097-1.081q-.422 0-.719-.3a1 1 0 0 1-.297-.722q0-.422.3-.719a1 1 0 0 1 .722-.297q.422 0 .719.3t.297.722-.3.719a1 1 0 0 1-.722.297m2.09 1.069-.574-.575a2.14 2.14 0 0 0 .618-1.515 2.1 2.1 0 0 0-.618-1.51L8.1 3.9q.4.412.634.947.235.534.235 1.161 0 .615-.236 1.15a2.9 2.9 0 0 1-.645.93m1.276 1.275-.588-.588a3.84 3.84 0 0 0 1.156-2.77q0-.824-.31-1.533a4.3 4.3 0 0 0-.833-1.26l.587-.587q.65.663 1.022 1.524a4.6 4.6 0 0 1 .372 1.859q0 .986-.374 1.848a4.7 4.7 0 0 1-1.032 1.507\"\n  })));\n};\nvar ForwardRef = /*#__PURE__*/forwardRef(SvgSensor);\nexport { ForwardRef as Icon };\nexport default \"img/sensor.8f9c469.svg\";","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode } from \"react\";\nimport { Tooltip } from \"@vector-im/compound-web\";\n\nimport { formatFullDate, formatTime, formatFullTime, formatRelativeTime } from \"../../../DateUtils\";\nimport { _t } from \"../../../languageHandler\";\nimport { Icon as LateIcon } from \"../../../../res/img/sensor.svg\";\n\ninterface IProps {\n    ts: number;\n    /**\n     * If specified will render both the sent-at and received-at timestamps in the tooltip\n     */\n    receivedTs?: number;\n    showTwelveHour?: boolean;\n    showFullDate?: boolean;\n    showSeconds?: boolean;\n    showRelative?: boolean;\n\n    /**\n     * If set to true then no tooltip will be shown\n     */\n    inhibitTooltip?: boolean;\n\n    /**\n     * If specified, will be rendered as an anchor bearing the href, a `span` element will be used otherwise\n     */\n    href?: string;\n    /**\n     * Optional onClick handler to attach to the DOM element\n     */\n    onClick?: React.MouseEventHandler<HTMLElement>;\n    /**\n     * Optional onContextMenu handler to attach to the DOM element\n     */\n    onContextMenu?: React.MouseEventHandler<HTMLElement>;\n}\n\nexport default class MessageTimestamp extends React.Component<IProps> {\n    public render(): React.ReactNode {\n        const date = new Date(this.props.ts);\n        let timestamp: string;\n        if (this.props.showRelative) {\n            timestamp = formatRelativeTime(date, this.props.showTwelveHour);\n        } else if (this.props.showFullDate) {\n            timestamp = formatFullDate(date, this.props.showTwelveHour, this.props.showSeconds);\n        } else if (this.props.showSeconds) {\n            timestamp = formatFullTime(date, this.props.showTwelveHour);\n        } else {\n            timestamp = formatTime(date, this.props.showTwelveHour);\n        }\n\n        let label = formatFullDate(date, this.props.showTwelveHour);\n        let caption: string | undefined;\n        let icon: ReactNode | undefined;\n        if (this.props.receivedTs !== undefined) {\n            label = _t(\"timeline|message_timestamp_sent_at\", { dateTime: label });\n            const receivedDate = new Date(this.props.receivedTs);\n            caption = _t(\"timeline|message_timestamp_received_at\", {\n                dateTime: formatFullDate(receivedDate, this.props.showTwelveHour),\n            });\n            icon = <LateIcon className=\"mx_MessageTimestamp_lateIcon\" width=\"16\" height=\"16\" />;\n        }\n\n        let content;\n        if (this.props.href) {\n            content = (\n                <a\n                    href={this.props.href}\n                    onClick={this.props.onClick}\n                    onContextMenu={this.props.onContextMenu}\n                    className=\"mx_MessageTimestamp\"\n                    aria-live=\"off\"\n                >\n                    {icon}\n                    {timestamp}\n                </a>\n            );\n        } else {\n            content = (\n                <span\n                    onClick={this.props.onClick}\n                    onContextMenu={this.props.onContextMenu}\n                    className=\"mx_MessageTimestamp\"\n                    aria-hidden={true}\n                    aria-live=\"off\"\n                    tabIndex={this.props.onClick || !this.props.inhibitTooltip ? 0 : undefined}\n                >\n                    {icon}\n                    {timestamp}\n                </span>\n            );\n        }\n\n        if (this.props.inhibitTooltip) return content;\n\n        return (\n            <Tooltip description={label} caption={caption}>\n                {content}\n            </Tooltip>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useContext, type JSX } from \"react\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { DeleteIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { formatFullDate } from \"../../../DateUtils\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { type IBodyProps } from \"./IBodyProps\";\n\nconst RedactedBody = ({ mxEvent, ref }: IBodyProps): JSX.Element => {\n    const cli: MatrixClient = useContext(MatrixClientContext);\n    let text = _t(\"timeline|self_redaction\");\n    const unsigned = mxEvent.getUnsigned();\n    const redactedBecauseUserId = unsigned && unsigned.redacted_because && unsigned.redacted_because.sender;\n    if (redactedBecauseUserId && redactedBecauseUserId !== mxEvent.getSender()) {\n        const room = cli.getRoom(mxEvent.getRoomId());\n        const sender = room && room.getMember(redactedBecauseUserId);\n        text = _t(\"timeline|redaction\", { name: sender ? sender.name : redactedBecauseUserId });\n    }\n\n    const showTwelveHour = SettingsStore.getValue(\"showTwelveHourTimestamps\");\n    const fullDate = unsigned.redacted_because\n        ? formatFullDate(new Date(unsigned.redacted_because.origin_server_ts), showTwelveHour)\n        : undefined;\n    const titleText = fullDate ? _t(\"timeline|redacted|tooltip\", { date: fullDate }) : undefined;\n\n    return (\n        <span className=\"mx_RedactedBody\" ref={ref} title={titleText}>\n            <DeleteIcon />\n            {text}\n        </span>\n    );\n};\n\nexport default RedactedBody;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { FileErrorIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\ninterface Props {\n    className?: string;\n    Icon?: typeof FileErrorIcon;\n    children: React.ReactNode;\n}\n\nconst MediaProcessingError: React.FC<Props> = ({ className, children, Icon = FileErrorIcon }) => (\n    <span className={className}>\n        <Icon className=\"mx_MediaProcessingError_Icon\" width=\"16\" height=\"16\" />\n        {children}\n    </span>\n);\n\nexport default MediaProcessingError;\n","var _path;\nfunction _extends() { return _extends = Object.assign ? Object.assign.bind() : function (n) { for (var e = 1; e < arguments.length; e++) { var t = arguments[e]; for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]); } return n; }, _extends.apply(null, arguments); }\nimport * as React from \"react\";\nimport { forwardRef } from \"react\";\nvar SvgTrophy = function SvgTrophy(props, ref) {\n  return /*#__PURE__*/React.createElement(\"svg\", _extends({\n    xmlns: \"http://www.w3.org/2000/svg\",\n    fill: \"none\",\n    viewBox: \"0 0 12 12\",\n    role: \"presentation\",\n    \"aria-hidden\": true,\n    ref: ref\n  }, props), _path || (_path = /*#__PURE__*/React.createElement(\"path\", {\n    fill: \"currentColor\",\n    d: \"M10.667 1.333H9.333V.667C9.333.3 9.033 0 8.667 0H3.333c-.366 0-.666.3-.666.667v.666H1.333C.6 1.333 0 1.933 0 2.667v.666c0 1.7 1.28 3.087 2.927 3.294A3.34 3.34 0 0 0 5.333 8.6v2.067h-2c-.366 0-.666.3-.666.666s.3.667.666.667h5.334c.366 0 .666-.3.666-.667 0-.366-.3-.666-.666-.666h-2V8.6a3.34 3.34 0 0 0 2.406-1.973C10.72 6.42 12 5.033 12 3.333v-.666c0-.734-.6-1.334-1.333-1.334m-9.334 2v-.666h1.334v2.546a2.01 2.01 0 0 1-1.334-1.88m9.334 0c0 .867-.56 1.6-1.334 1.88V2.667h1.334z\"\n  })));\n};\nvar ForwardRef = /*#__PURE__*/forwardRef(SvgTrophy);\nexport { ForwardRef as Icon };\nexport default \"img/element-icons/trophy.1ab5e03.svg\";","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode } from \"react\";\nimport classNames from \"classnames\";\nimport { type PollAnswerSubevent } from \"matrix-js-sdk/src/extensible_events_v1/PollStartEvent\";\nimport { CheckIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { Icon as TrophyIcon } from \"../../../../res/img/element-icons/trophy.svg\";\nimport StyledRadioButton from \"../elements/StyledRadioButton\";\n\ntype PollOptionContentProps = {\n    answer: PollAnswerSubevent;\n    voteCount: number;\n    displayVoteCount?: boolean;\n    isWinner?: boolean;\n};\nconst PollOptionContent: React.FC<PollOptionContentProps> = ({ isWinner, answer, voteCount, displayVoteCount }) => {\n    const votesText = displayVoteCount ? _t(\"timeline|m.poll|count_of_votes\", { count: voteCount }) : \"\";\n    return (\n        <div className=\"mx_PollOption_content\">\n            <div className=\"mx_PollOption_optionText\">{answer.text}</div>\n            <div className=\"mx_PollOption_optionVoteCount\">\n                {isWinner && <TrophyIcon className=\"mx_PollOption_winnerIcon\" />}\n                {votesText}\n            </div>\n        </div>\n    );\n};\n\ninterface PollOptionProps extends PollOptionContentProps {\n    pollId: string;\n    totalVoteCount: number;\n    optionNumber: number;\n    isEnded?: boolean;\n    isChecked?: boolean;\n    onOptionSelected?: (id: string) => void;\n    children?: ReactNode;\n}\n\nconst ActivePollOption: React.FC<Omit<PollOptionProps, \"totalVoteCount\"> & { children: ReactNode }> = ({\n    pollId,\n    isChecked,\n    isEnded,\n    optionNumber,\n    isWinner,\n    voteCount,\n    displayVoteCount,\n    children,\n    answer,\n    onOptionSelected,\n}) => {\n    let ariaLabel: string;\n\n    if (displayVoteCount && isWinner) {\n        ariaLabel = _t(\"poll|option_label_winning_with_total\", {\n            number: optionNumber,\n            answer: answer.text,\n            count: voteCount,\n        });\n    } else if (displayVoteCount) {\n        ariaLabel = _t(\"poll|option_label_with_total\", {\n            number: optionNumber,\n            answer: answer.text,\n            count: voteCount,\n        });\n    } else {\n        ariaLabel = _t(\"poll|option_label\", {\n            number: optionNumber,\n            answer: answer.text,\n        });\n    }\n\n    return (\n        <StyledRadioButton\n            className=\"mx_PollOption_live-option\"\n            name={`poll_answer_select-${pollId}`}\n            value={answer.id}\n            checked={isChecked}\n            disabled={isEnded}\n            aria-label={ariaLabel}\n            onChange={() => onOptionSelected?.(answer.id)}\n            icon={isChecked ? <CheckIcon /> : undefined}\n        >\n            <div aria-hidden=\"true\">{children}</div>\n        </StyledRadioButton>\n    );\n};\n\nexport const PollOption: React.FC<PollOptionProps> = ({\n    pollId,\n    answer,\n    voteCount,\n    totalVoteCount,\n    optionNumber,\n    displayVoteCount,\n    isEnded,\n    isChecked,\n    onOptionSelected,\n}) => {\n    const cls = classNames({\n        mx_PollOption: true,\n        mx_PollOption_checked: isChecked,\n        mx_PollOption_ended: isEnded,\n    });\n    const isWinner = isEnded && isChecked;\n    const answerPercent = totalVoteCount === 0 ? 0 : Math.round((100.0 * voteCount) / totalVoteCount);\n    return (\n        <div data-testid={`pollOption-${answer.id}`} className={cls} onClick={() => onOptionSelected?.(answer.id)}>\n            <ActivePollOption\n                pollId={pollId}\n                answer={answer}\n                optionNumber={optionNumber}\n                isChecked={isChecked}\n                isEnded={isEnded}\n                isWinner={isWinner}\n                voteCount={voteCount}\n                displayVoteCount={displayVoteCount}\n                onOptionSelected={onOptionSelected}\n            >\n                <PollOptionContent\n                    isWinner={isWinner}\n                    answer={answer}\n                    voteCount={voteCount}\n                    displayVoteCount={displayVoteCount}\n                />\n            </ActivePollOption>\n            <div className=\"mx_PollOption_popularityBackground\">\n                <div className=\"mx_PollOption_popularityAmount\" style={{ width: `${answerPercent}%` }} />\n            </div>\n        </div>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type FieldsetHTMLAttributes, type ReactNode } from \"react\";\n\nexport type FilterTab<T> = {\n    label: string | ReactNode;\n    id: T;\n};\ntype FilterTabGroupProps<T extends string = string> = FieldsetHTMLAttributes<any> & {\n    // group name used for radio buttons\n    name: string;\n    onFilterChange: (id: T) => void;\n    // active tab's id\n    value: T;\n    // tabs to display\n    tabs: FilterTab<T>[];\n};\n\n/**\n * React component which styles a set of content filters as tabs\n *\n * This is used in displays which show a list of content items, and the user can select between one of several\n * filters for those items. For example, in the Poll History dialog, the user can select between \"Active\" and \"Ended\"\n * polls.\n *\n * Type `T` is used for the `value` attribute for the buttons in the radio group.\n */\nexport const FilterTabGroup = <T extends string = string>({\n    name,\n    value,\n    tabs,\n    onFilterChange,\n    ...rest\n}: FilterTabGroupProps<T>): JSX.Element => (\n    <fieldset {...rest} className=\"mx_FilterTabGroup\">\n        {tabs.map(({ label, id }) => (\n            <label data-testid={`filter-tab-${name}-${id}`} key={id}>\n                <input type=\"radio\" name={name} value={id} onChange={() => onFilterChange(id)} checked={value === id} />\n                <span>{label}</span>\n            </label>\n        ))}\n    </fieldset>\n);\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type PollStartEvent } from \"matrix-js-sdk/src/extensible_events_v1/PollStartEvent\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { Tooltip } from \"@vector-im/compound-web\";\nimport { PollsIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { formatLocalDateShort } from \"../../../../DateUtils\";\nimport { _t } from \"../../../../languageHandler\";\n\ninterface Props {\n    event: MatrixEvent;\n    onClick: () => void;\n}\n\nexport const PollListItem: React.FC<Props> = ({ event, onClick }) => {\n    const pollEvent = event.unstableExtensibleEvent as unknown as PollStartEvent;\n    if (!pollEvent) {\n        return null;\n    }\n    const formattedDate = formatLocalDateShort(event.getTs());\n    return (\n        <li data-testid={`pollListItem-${event.getId()!}`} className=\"mx_PollListItem\" onClick={onClick}>\n            <Tooltip label={_t(\"right_panel|poll|view_poll\")} placement=\"top\" isTriggerInteractive={false}>\n                <div className=\"mx_PollListItem_content\">\n                    <span>{formattedDate}</span>\n                    <PollsIcon className=\"mx_PollListItem_icon\" />\n                    <span className=\"mx_PollListItem_question\">{pollEvent.question.text}</span>\n                </div>\n            </Tooltip>\n        </li>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useEffect, useState } from \"react\";\nimport { type PollAnswerSubevent } from \"matrix-js-sdk/src/extensible_events_v1/PollStartEvent\";\nimport { type MatrixEvent, type Poll, PollEvent, type Relations } from \"matrix-js-sdk/src/matrix\";\nimport { Tooltip } from \"@vector-im/compound-web\";\nimport { PollsEndIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport { formatLocalDateShort } from \"../../../../DateUtils\";\nimport { allVotes, collectUserVotes, countVotes } from \"../../messages/MPollBody\";\nimport { PollOption } from \"../../polls/PollOption\";\nimport { Caption } from \"../../typography/Caption\";\n\ninterface Props {\n    event: MatrixEvent;\n    poll: Poll;\n    onClick: () => void;\n}\n\ntype EndedPollState = {\n    winningAnswers: {\n        answer: PollAnswerSubevent;\n        voteCount: number;\n        optionNumber: number;\n    }[];\n    totalVoteCount: number;\n};\nconst getWinningAnswers = (poll: Poll, responseRelations: Relations): EndedPollState => {\n    const userVotes = collectUserVotes(allVotes(responseRelations));\n    const votes = countVotes(userVotes, poll.pollEvent);\n    const totalVoteCount = [...votes.values()].reduce((sum, vote) => sum + vote, 0);\n    const winCount = Math.max(...votes.values());\n\n    return {\n        totalVoteCount,\n        winningAnswers: poll.pollEvent.answers\n            .map((answer, index) => ({ answerIndex: index, answer })) // keep track of original answer index\n            .filter(({ answer }) => votes.get(answer.id) === winCount)\n            .map(({ answer, answerIndex }) => ({\n                answer,\n                voteCount: votes.get(answer.id) || 0,\n                optionNumber: answerIndex + 1,\n            })),\n    };\n};\n\n/**\n * Get deduplicated and validated poll responses\n * Will use cached responses from Poll instance when existing\n * Updates on changes to Poll responses (paging relations or from sync)\n * Returns winning answers and total vote count\n */\nconst usePollVotes = (poll: Poll): Partial<EndedPollState> => {\n    const [results, setResults] = useState({ totalVoteCount: 0 });\n\n    useEffect(() => {\n        const getResponses = async (): Promise<void> => {\n            const responseRelations = await poll.getResponses();\n            setResults(getWinningAnswers(poll, responseRelations));\n        };\n        const onPollResponses = (responseRelations: Relations): void =>\n            setResults(getWinningAnswers(poll, responseRelations));\n        poll.on(PollEvent.Responses, onPollResponses);\n\n        getResponses();\n\n        return () => {\n            poll.off(PollEvent.Responses, onPollResponses);\n        };\n    }, [poll]);\n\n    return results;\n};\n\n/**\n * Render an ended poll with the winning answer and vote count\n * @param event - the poll start MatrixEvent\n * @param poll - Poll instance\n */\nexport const PollListItemEnded: React.FC<Props> = ({ event, poll, onClick }) => {\n    const pollEvent = poll.pollEvent;\n    const { winningAnswers, totalVoteCount } = usePollVotes(poll);\n    if (!pollEvent) {\n        return null;\n    }\n    const formattedDate = formatLocalDateShort(event.getTs());\n\n    return (\n        <li data-testid={`pollListItem-${event.getId()!}`} className=\"mx_PollListItemEnded\" onClick={onClick}>\n            <Tooltip label={_t(\"right_panel|poll|view_poll\")} placement=\"top\" isTriggerInteractive={false}>\n                <div className=\"mx_PollListItemEnded_content\">\n                    <div className=\"mx_PollListItemEnded_title\">\n                        <PollsEndIcon className=\"mx_PollListItemEnded_icon\" />\n                        <span className=\"mx_PollListItemEnded_question\">{pollEvent.question.text}</span>\n                        <Caption>{formattedDate}</Caption>\n                    </div>\n                    {!!winningAnswers?.length && (\n                        <div className=\"mx_PollListItemEnded_answers\">\n                            {winningAnswers?.map(({ answer, voteCount, optionNumber }) => (\n                                <PollOption\n                                    key={answer.id}\n                                    answer={answer}\n                                    voteCount={voteCount}\n                                    totalVoteCount={totalVoteCount!}\n                                    pollId={poll.pollId}\n                                    optionNumber={optionNumber}\n                                    displayVoteCount\n                                    isChecked\n                                    isEnded\n                                />\n                            ))}\n                        </div>\n                    )}\n                    <div className=\"mx_PollListItemEnded_voteCount\">\n                        <Caption>{_t(\"right_panel|poll|final_result\", { count: totalVoteCount })}</Caption>\n                    </div>\n                </div>\n            </Tooltip>\n        </li>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport classNames from \"classnames\";\nimport { type MatrixEvent, type Poll } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport { FilterTabGroup } from \"../../elements/FilterTabGroup\";\nimport InlineSpinner from \"../../elements/InlineSpinner\";\nimport { type PollHistoryFilter } from \"./types\";\nimport { PollListItem } from \"./PollListItem\";\nimport { PollListItemEnded } from \"./PollListItemEnded\";\nimport AccessibleButton from \"../../elements/AccessibleButton\";\n\nconst LoadingPolls: React.FC<{ noResultsYet?: boolean }> = ({ noResultsYet }) => (\n    <div\n        className={classNames(\"mx_PollHistoryList_loading\", {\n            mx_PollHistoryList_noResultsYet: noResultsYet,\n        })}\n    >\n        <InlineSpinner />\n        {_t(\"right_panel|poll|loading\")}\n    </div>\n);\n\nconst LoadMorePolls: React.FC<{ loadMorePolls?: () => void; isLoading?: boolean }> = ({ isLoading, loadMorePolls }) =>\n    loadMorePolls ? (\n        <AccessibleButton\n            className=\"mx_PollHistoryList_loadMorePolls\"\n            kind=\"link_inline\"\n            onClick={() => loadMorePolls()}\n        >\n            {_t(\"right_panel|poll|load_more\")}\n            {isLoading && <InlineSpinner />}\n        </AccessibleButton>\n    ) : null;\n\nconst ONE_DAY_MS = 60000 * 60 * 24;\nconst getNoResultsMessage = (\n    filter: PollHistoryFilter,\n    oldestEventTimestamp?: number,\n    loadMorePolls?: () => void,\n): string => {\n    if (!loadMorePolls) {\n        return filter === \"ACTIVE\" ? _t(\"right_panel|poll|empty_active\") : _t(\"right_panel|poll|empty_past\");\n    }\n\n    // we don't know how much history has been fetched\n    if (!oldestEventTimestamp) {\n        return filter === \"ACTIVE\"\n            ? _t(\"right_panel|poll|empty_active_load_more\")\n            : _t(\"right_panel|poll|empty_past_load_more\");\n    }\n\n    const fetchedHistoryDaysCount = Math.ceil((Date.now() - oldestEventTimestamp) / ONE_DAY_MS);\n    return filter === \"ACTIVE\"\n        ? _t(\"right_panel|poll|empty_active_load_more_n_days\", { count: fetchedHistoryDaysCount })\n        : _t(\"right_panel|poll|empty_past_load_more_n_days\", {\n              count: fetchedHistoryDaysCount,\n          });\n};\n\nconst NoResults: React.FC<{\n    filter: PollHistoryFilter;\n    oldestFetchedEventTimestamp?: number;\n    loadMorePolls?: () => void;\n    isLoading?: boolean;\n}> = ({ filter, isLoading, oldestFetchedEventTimestamp, loadMorePolls }) => {\n    // we can't page the timeline anymore\n    // just use plain loader\n    if (!loadMorePolls && isLoading) {\n        return <LoadingPolls noResultsYet />;\n    }\n\n    return (\n        <span className=\"mx_PollHistoryList_noResults\">\n            {getNoResultsMessage(filter, oldestFetchedEventTimestamp, loadMorePolls)}\n\n            {!!loadMorePolls && <LoadMorePolls loadMorePolls={loadMorePolls} isLoading={isLoading} />}\n        </span>\n    );\n};\n\ntype PollHistoryListProps = {\n    pollStartEvents: MatrixEvent[];\n    polls: Map<string, Poll>;\n    filter: PollHistoryFilter;\n    /**\n     * server ts of the oldest fetched poll\n     * ignoring filter\n     * used to render no results in last x days message\n     * undefined when no polls are found\n     */\n    oldestFetchedEventTimestamp?: number;\n    onFilterChange: (filter: PollHistoryFilter) => void;\n    onItemClick: (pollId: string) => void;\n    loadMorePolls?: () => void;\n    isLoading?: boolean;\n};\nexport const PollHistoryList: React.FC<PollHistoryListProps> = ({\n    pollStartEvents,\n    polls,\n    filter,\n    isLoading,\n    oldestFetchedEventTimestamp,\n    onFilterChange,\n    loadMorePolls,\n    onItemClick,\n}) => {\n    return (\n        <div className=\"mx_PollHistoryList\">\n            <FilterTabGroup<PollHistoryFilter>\n                name=\"PollHistory_filter\"\n                value={filter}\n                onFilterChange={onFilterChange}\n                tabs={[\n                    { id: \"ACTIVE\", label: _t(\"right_panel|poll|active_heading\") },\n                    { id: \"ENDED\", label: _t(\"right_panel|poll|past_heading\") },\n                ]}\n            />\n            {!!pollStartEvents.length && (\n                <ol className={classNames(\"mx_PollHistoryList_list\", `mx_PollHistoryList_list_${filter}`)}>\n                    {pollStartEvents.map((pollStartEvent) =>\n                        filter === \"ACTIVE\" ? (\n                            <PollListItem\n                                key={pollStartEvent.getId()!}\n                                event={pollStartEvent}\n                                onClick={() => onItemClick(pollStartEvent.getId()!)}\n                            />\n                        ) : (\n                            <PollListItemEnded\n                                key={pollStartEvent.getId()!}\n                                event={pollStartEvent}\n                                poll={polls.get(pollStartEvent.getId()!)!}\n                                onClick={() => onItemClick(pollStartEvent.getId()!)}\n                            />\n                        ),\n                    )}\n                    {isLoading && !loadMorePolls && <LoadingPolls />}\n                    {!!loadMorePolls && <LoadMorePolls loadMorePolls={loadMorePolls} isLoading={isLoading} />}\n                </ol>\n            )}\n            {!pollStartEvents.length && (\n                <NoResults\n                    oldestFetchedEventTimestamp={oldestFetchedEventTimestamp}\n                    isLoading={isLoading}\n                    filter={filter}\n                    loadMorePolls={loadMorePolls}\n                />\n            )}\n        </div>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport LeftCaretIcon from \"@vector-im/compound-design-tokens/assets/web/icons/chevron-left\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport AccessibleButton from \"../../elements/AccessibleButton\";\nimport { type PollHistoryFilter } from \"./types\";\n\ninterface Props {\n    filter: PollHistoryFilter;\n    onNavigateBack: () => void;\n}\n\nexport const PollDetailHeader: React.FC<Props> = ({ filter, onNavigateBack }) => {\n    return (\n        <AccessibleButton kind=\"content_inline\" onClick={onNavigateBack} className=\"mx_PollDetailHeader\">\n            <LeftCaretIcon className=\"mx_PollDetailHeader_icon\" />\n            {filter === \"ACTIVE\" ? _t(\"right_panel|poll|active_heading\") : _t(\"right_panel|poll|past_heading\")}\n        </AccessibleButton>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type Poll } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport dispatcher from \"../../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../../dispatcher/actions\";\nimport { type ViewRoomPayload } from \"../../../../dispatcher/payloads/ViewRoomPayload\";\nimport { type RoomPermalinkCreator } from \"../../../../utils/permalinks/Permalinks\";\nimport { type MediaEventHelper } from \"../../../../utils/MediaEventHelper\";\nimport AccessibleButton, { type ButtonEvent } from \"../../elements/AccessibleButton\";\nimport MPollBody from \"../../messages/MPollBody\";\n\ninterface Props {\n    poll: Poll;\n    requestModalClose: () => void;\n    permalinkCreator: RoomPermalinkCreator;\n}\n\n/**\n * Content of PollHistory when a specific poll is selected\n */\nexport const PollDetail: React.FC<Props> = ({ poll, permalinkCreator, requestModalClose }) => {\n    // link to end event for ended polls\n    const eventIdToLinkTo = poll.isEnded ? poll.endEventId! : poll.pollId;\n    const linkToTimeline = permalinkCreator.forEvent(eventIdToLinkTo);\n\n    const onLinkClick = (e: ButtonEvent): void => {\n        if ((e as React.MouseEvent).ctrlKey || (e as React.MouseEvent).metaKey) {\n            // native behavior for link on ctrl/cmd + click\n            return;\n        }\n        // otherwise handle navigation in the app\n        e.preventDefault();\n        dispatcher.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            event_id: eventIdToLinkTo,\n            highlighted: true,\n            room_id: poll.roomId,\n            metricsTrigger: undefined, // room doesn't change\n        });\n\n        requestModalClose();\n    };\n    return (\n        <>\n            <MPollBody\n                mxEvent={poll.rootEvent}\n                permalinkCreator={permalinkCreator}\n                // MPollBody doesn't use this\n                // and MessageEvent only defines it for eligible events\n                // should be fixed on IBodyProps types\n                // cheat to fulfil the type here\n                mediaEventHelper={{} as unknown as MediaEventHelper}\n            />\n            <br />\n            <div>\n                <AccessibleButton\n                    kind=\"link_inline\"\n                    element=\"a\"\n                    href={linkToTimeline}\n                    onClick={onLinkClick}\n                    rel=\"noreferrer noopener\"\n                >\n                    {_t(\"right_panel|poll|view_in_timeline\")}\n                </AccessibleButton>\n            </div>\n        </>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useEffect, useState } from \"react\";\nimport { type Poll, PollEvent, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { useEventEmitterState } from \"../../../../hooks/useEventEmitter\";\n\n/**\n * Get poll instances from a room\n * Updates to include new polls\n * @param roomId - id of room to retrieve polls for\n * @param matrixClient - client\n * @returns {Map<string, Poll>} - Map of Poll instances\n */\nexport const usePolls = (\n    roomId: string,\n    matrixClient: MatrixClient,\n): {\n    polls: Map<string, Poll>;\n} => {\n    const room = matrixClient.getRoom(roomId);\n\n    if (!room) {\n        throw new Error(\"Cannot find room\");\n    }\n\n    // copy room.polls map so changes can be detected\n    const polls = useEventEmitterState(room, PollEvent.New, () => new Map<string, Poll>(room.polls));\n\n    return { polls };\n};\n\n/**\n * Get all poll instances from a room\n * Fetch their responses (using cached poll responses)\n * Updates on:\n * - new polls added to room\n * - new responses added to polls\n * - changes to poll ended state\n * @param roomId - id of room to retrieve polls for\n * @param matrixClient - client\n * @returns {Map<string, Poll>} - Map of Poll instances\n */\nexport const usePollsWithRelations = (\n    roomId: string,\n    matrixClient: MatrixClient,\n): {\n    polls: Map<string, Poll>;\n} => {\n    const { polls } = usePolls(roomId, matrixClient);\n    const [pollsWithRelations, setPollsWithRelations] = useState<Map<string, Poll>>(polls);\n\n    useEffect(() => {\n        const onPollUpdate = async (): Promise<void> => {\n            // trigger rerender by creating a new poll map\n            setPollsWithRelations(new Map(polls));\n        };\n        if (polls) {\n            for (const poll of polls.values()) {\n                // listen to changes in responses and end state\n                poll.on(PollEvent.End, onPollUpdate);\n                poll.on(PollEvent.Responses, onPollUpdate);\n                // trigger request to get all responses\n                // if they are not already in cache\n                poll.getResponses();\n            }\n            setPollsWithRelations(polls);\n        }\n        // unsubscribe\n        return () => {\n            if (polls) {\n                for (const poll of polls.values()) {\n                    poll.off(PollEvent.End, onPollUpdate);\n                    poll.off(PollEvent.Responses, onPollUpdate);\n                }\n            }\n        };\n    }, [polls, setPollsWithRelations]);\n\n    return { polls: pollsWithRelations };\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useCallback, useEffect, useState } from \"react\";\nimport {\n    M_POLL_START,\n    type MatrixClient,\n    Direction,\n    EventTimeline,\n    type EventTimelineSet,\n    type Room,\n    Filter,\n    type IFilterDefinition,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nconst getOldestEventTimestamp = (timelineSet?: EventTimelineSet): number | undefined => {\n    if (!timelineSet) {\n        return;\n    }\n\n    const liveTimeline = timelineSet?.getLiveTimeline();\n    const events = liveTimeline.getEvents();\n    return events[0]?.getTs();\n};\n\n/**\n * Page backwards in timeline history\n * @param timelineSet - timelineset to page\n * @param matrixClient - client\n * @param canPageBackward - whether the timeline has more pages\n * @param oldestEventTimestamp - server ts of the oldest encountered event\n */\nconst pagePollHistory = async (\n    timelineSet: EventTimelineSet,\n    matrixClient: MatrixClient,\n): Promise<{\n    oldestEventTimestamp?: number;\n    canPageBackward: boolean;\n}> => {\n    if (!timelineSet) {\n        return { canPageBackward: false };\n    }\n\n    const liveTimeline = timelineSet.getLiveTimeline();\n\n    await matrixClient.paginateEventTimeline(liveTimeline, {\n        backwards: true,\n    });\n\n    return {\n        oldestEventTimestamp: getOldestEventTimestamp(timelineSet),\n        canPageBackward: !!liveTimeline.getPaginationToken(EventTimeline.BACKWARDS),\n    };\n};\n\n/**\n * Page timeline backwards until either:\n * - event older than timestamp is encountered\n * - end of timeline is reached\n * @param timelineSet - timeline set to page\n * @param matrixClient - client\n * @param timestamp - epoch timestamp to page until\n * @param canPageBackward - whether the timeline has more pages\n * @param oldestEventTimestamp - server ts of the oldest encountered event\n */\nconst fetchHistoryUntilTimestamp = async (\n    timelineSet: EventTimelineSet | undefined,\n    matrixClient: MatrixClient,\n    timestamp: number,\n    canPageBackward: boolean,\n    oldestEventTimestamp?: number,\n): Promise<void> => {\n    if (!timelineSet || !canPageBackward || (oldestEventTimestamp && oldestEventTimestamp < timestamp)) {\n        return;\n    }\n    const result = await pagePollHistory(timelineSet, matrixClient);\n\n    return fetchHistoryUntilTimestamp(\n        timelineSet,\n        matrixClient,\n        timestamp,\n        result.canPageBackward,\n        result.oldestEventTimestamp,\n    );\n};\n\nconst ONE_DAY_MS = 60000 * 60 * 24;\n/**\n * Fetches timeline history for given number of days in past\n * @param timelineSet - timelineset to page\n * @param matrixClient - client\n * @param historyPeriodDays - number of days of history to fetch, from current day\n * @returns isLoading - true while fetching\n * @returns oldestEventTimestamp - timestamp of oldest encountered poll, undefined when no polls found in timeline so far\n * @returns loadMorePolls - function to page timeline backwards, undefined when timeline cannot be paged backwards\n * @returns loadTimelineHistory - loads timeline history for the given history period\n */\nconst useTimelineHistory = (\n    timelineSet: EventTimelineSet | undefined,\n    matrixClient: MatrixClient,\n    historyPeriodDays: number,\n): {\n    isLoading: boolean;\n    oldestEventTimestamp?: number;\n    loadTimelineHistory: () => Promise<void>;\n    loadMorePolls?: () => Promise<void>;\n} => {\n    const [isLoading, setIsLoading] = useState(true);\n    const [oldestEventTimestamp, setOldestEventTimestamp] = useState<number | undefined>(undefined);\n    const [canPageBackward, setCanPageBackward] = useState(false);\n\n    const loadTimelineHistory = useCallback(async () => {\n        const endOfHistoryPeriodTimestamp = Date.now() - ONE_DAY_MS * historyPeriodDays;\n        setIsLoading(true);\n        try {\n            const liveTimeline = timelineSet?.getLiveTimeline();\n            const canPageBackward = !!liveTimeline?.getPaginationToken(Direction.Backward);\n            const oldestEventTimestamp = getOldestEventTimestamp(timelineSet);\n\n            await fetchHistoryUntilTimestamp(\n                timelineSet,\n                matrixClient,\n                endOfHistoryPeriodTimestamp,\n                canPageBackward,\n                oldestEventTimestamp,\n            );\n\n            setCanPageBackward(!!timelineSet?.getLiveTimeline()?.getPaginationToken(EventTimeline.BACKWARDS));\n            setOldestEventTimestamp(getOldestEventTimestamp(timelineSet));\n        } catch (error) {\n            logger.error(\"Failed to fetch room polls history\", error);\n        } finally {\n            setIsLoading(false);\n        }\n    }, [historyPeriodDays, timelineSet, matrixClient]);\n\n    const loadMorePolls = useCallback(async () => {\n        if (!timelineSet) {\n            return;\n        }\n        setIsLoading(true);\n        try {\n            const result = await pagePollHistory(timelineSet, matrixClient);\n\n            setCanPageBackward(result.canPageBackward);\n            setOldestEventTimestamp(result.oldestEventTimestamp);\n        } catch (error) {\n            logger.error(\"Failed to fetch room polls history\", error);\n        } finally {\n            setIsLoading(false);\n        }\n    }, [timelineSet, matrixClient]);\n\n    return {\n        isLoading,\n        oldestEventTimestamp,\n        loadTimelineHistory,\n        loadMorePolls: canPageBackward ? loadMorePolls : undefined,\n    };\n};\n\nconst filterDefinition: IFilterDefinition = {\n    room: {\n        timeline: {\n            types: [M_POLL_START.name, M_POLL_START.altName],\n        },\n    },\n};\n\n/**\n * Fetches poll start events in the last N days of room history\n * @param room - room to fetch history for\n * @param matrixClient - client\n * @param historyPeriodDays - number of days of history to fetch, from current day\n * @returns isLoading - true while fetching history\n * @returns oldestEventTimestamp - timestamp of oldest encountered poll, undefined when no polls found in timeline so far\n * @returns loadMorePolls - function to page timeline backwards, undefined when timeline cannot be paged backwards\n */\nexport const useFetchPastPolls = (\n    room: Room,\n    matrixClient: MatrixClient,\n    historyPeriodDays = 30,\n): {\n    isLoading: boolean;\n    oldestEventTimestamp?: number;\n    loadMorePolls?: () => Promise<void>;\n} => {\n    const [timelineSet, setTimelineSet] = useState<EventTimelineSet | undefined>(undefined);\n\n    useEffect(() => {\n        const filter = new Filter(matrixClient.getSafeUserId());\n        filter.setDefinition(filterDefinition);\n        const getFilteredTimelineSet = async (): Promise<void> => {\n            const filterId = await matrixClient.getOrCreateFilter(`POLL_HISTORY_FILTER_${room.roomId}}`, filter);\n            filter.filterId = filterId;\n            const timelineSet = room.getOrCreateFilteredTimelineSet(filter);\n            setTimelineSet(timelineSet);\n        };\n\n        getFilteredTimelineSet();\n    }, [room, matrixClient]);\n\n    const { isLoading, oldestEventTimestamp, loadMorePolls, loadTimelineHistory } = useTimelineHistory(\n        timelineSet,\n        matrixClient,\n        historyPeriodDays,\n    );\n\n    useEffect(() => {\n        loadTimelineHistory();\n    }, [loadTimelineHistory]);\n\n    return { isLoading, oldestEventTimestamp, loadMorePolls };\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useState } from \"react\";\nimport { type MatrixClient, type MatrixEvent, type Poll, type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport { PollHistoryList } from \"./PollHistoryList\";\nimport { type PollHistoryFilter } from \"./types\";\nimport { PollDetailHeader } from \"./PollDetailHeader\";\nimport { PollDetail } from \"./PollDetail\";\nimport { type RoomPermalinkCreator } from \"../../../../utils/permalinks/Permalinks\";\nimport { usePollsWithRelations } from \"./usePollHistory\";\nimport { useFetchPastPolls } from \"./fetchPastPolls\";\nimport Heading from \"../../typography/Heading\";\n\ntype PollHistoryProps = {\n    room: Room;\n    matrixClient: MatrixClient;\n    permalinkCreator: RoomPermalinkCreator;\n    onFinished(): void;\n};\n\nconst sortEventsByLatest = (left: MatrixEvent, right: MatrixEvent): number => right.getTs() - left.getTs();\nconst filterPolls =\n    (filter: PollHistoryFilter) =>\n    (poll: Poll): boolean =>\n        // exclude polls while they are still loading\n        // to avoid jitter in list\n        !poll.isFetchingResponses && (filter === \"ACTIVE\") !== poll.isEnded;\n\nconst filterAndSortPolls = (polls: Map<string, Poll>, filter: PollHistoryFilter): MatrixEvent[] => {\n    return [...polls.values()]\n        .filter(filterPolls(filter))\n        .map((poll) => poll.rootEvent)\n        .sort(sortEventsByLatest);\n};\n\nexport const PollHistory: React.FC<PollHistoryProps> = ({ room, matrixClient, permalinkCreator, onFinished }) => {\n    const { polls } = usePollsWithRelations(room.roomId, matrixClient);\n    const { isLoading, loadMorePolls, oldestEventTimestamp } = useFetchPastPolls(room, matrixClient);\n    const [filter, setFilter] = useState<PollHistoryFilter>(\"ACTIVE\");\n    const [focusedPollId, setFocusedPollId] = useState<string | null>(null);\n\n    const pollStartEvents = filterAndSortPolls(polls, filter);\n    const isLoadingPollResponses = [...polls.values()].some((poll) => poll.isFetchingResponses);\n\n    const focusedPoll = focusedPollId ? polls.get(focusedPollId) : undefined;\n    const title = focusedPoll ? (\n        <PollDetailHeader filter={filter} onNavigateBack={() => setFocusedPollId(null)} />\n    ) : (\n        _t(\"right_panel|polls_button\")\n    );\n\n    return (\n        <div className=\"mx_PollHistory_content\">\n            {/* @TODO this probably needs some style */}\n            <Heading className=\"mx_PollHistory_header\" size=\"2\">\n                {title}\n            </Heading>\n            {focusedPoll ? (\n                <PollDetail poll={focusedPoll} permalinkCreator={permalinkCreator} requestModalClose={onFinished} />\n            ) : (\n                <PollHistoryList\n                    onItemClick={setFocusedPollId}\n                    pollStartEvents={pollStartEvents}\n                    isLoading={isLoading || isLoadingPollResponses}\n                    oldestFetchedEventTimestamp={oldestEventTimestamp}\n                    polls={polls}\n                    filter={filter}\n                    onFilterChange={setFilter}\n                    loadMorePolls={loadMorePolls}\n                />\n            )}\n        </div>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode, type KeyboardEvent, type Ref, type MouseEvent } from \"react\";\nimport classNames from \"classnames\";\nimport { IconButton, Text } from \"@vector-im/compound-web\";\nimport CloseIcon from \"@vector-im/compound-design-tokens/assets/web/icons/close\";\nimport ChevronLeftIcon from \"@vector-im/compound-design-tokens/assets/web/icons/chevron-left\";\n\nimport AutoHideScrollbar from \"../../structures/AutoHideScrollbar\";\nimport { _t } from \"../../../languageHandler\";\nimport RightPanelStore from \"../../../stores/right-panel/RightPanelStore\";\nimport { backLabelForPhase } from \"../../../stores/right-panel/RightPanelStorePhases\";\nimport { CardContext } from \"./context\";\n\ninterface IProps {\n    header?: ReactNode | null;\n    hideHeaderButtons?: boolean;\n    footer?: ReactNode;\n    className?: string;\n    id?: string;\n    role?: \"tabpanel\";\n    ariaLabelledBy?: string;\n    withoutScrollContainer?: boolean;\n    closeLabel?: string;\n    onClose?(ev: MouseEvent<HTMLButtonElement>): void;\n    onBack?(ev: MouseEvent<HTMLButtonElement>): void;\n    onKeyDown?(ev: KeyboardEvent): void;\n    cardState?: any;\n    ref?: Ref<HTMLDivElement>;\n    // Ref for the 'close' button the card\n    closeButtonRef?: Ref<HTMLButtonElement>;\n    children: ReactNode;\n}\n\nfunction closeRightPanel(ev: MouseEvent<HTMLButtonElement>): void {\n    ev.preventDefault();\n    ev.stopPropagation();\n    RightPanelStore.instance.popCard();\n}\n\nconst BaseCard: React.FC<IProps> = ({\n    closeLabel,\n    onClose,\n    onBack,\n    className,\n    id,\n    ariaLabelledBy,\n    role,\n    hideHeaderButtons,\n    header,\n    footer,\n    withoutScrollContainer,\n    children,\n    onKeyDown,\n    closeButtonRef,\n    ref,\n}: IProps) => {\n    let backButton;\n    const cardHistory = RightPanelStore.instance.roomPhaseHistory;\n    if (cardHistory.length > 1 && !hideHeaderButtons) {\n        const prevCard = cardHistory[cardHistory.length - 2];\n        const onBackClick = (ev: MouseEvent<HTMLButtonElement>): void => {\n            onBack?.(ev);\n            RightPanelStore.instance.popCard();\n        };\n        const label = backLabelForPhase(prevCard.phase) ?? _t(\"action|back\");\n        backButton = (\n            <IconButton\n                size=\"28px\"\n                data-testid=\"base-card-back-button\"\n                onClick={onBackClick}\n                tooltip={label}\n                kind=\"secondary\"\n            >\n                <ChevronLeftIcon />\n            </IconButton>\n        );\n    }\n\n    let closeButton;\n    if (!hideHeaderButtons) {\n        closeButton = (\n            <IconButton\n                size=\"28px\"\n                data-testid=\"base-card-close-button\"\n                onClick={onClose ?? closeRightPanel}\n                ref={closeButtonRef}\n                tooltip={closeLabel ?? _t(\"action|close\")}\n                kind=\"secondary\"\n            >\n                <CloseIcon />\n            </IconButton>\n        );\n    }\n\n    if (!withoutScrollContainer) {\n        children = <AutoHideScrollbar>{children}</AutoHideScrollbar>;\n    }\n\n    const shouldRenderHeader = header || !hideHeaderButtons;\n\n    return (\n        <CardContext.Provider value={{ isCard: true }}>\n            <div\n                id={id}\n                aria-labelledby={ariaLabelledBy}\n                role={role}\n                className={classNames(\"mx_BaseCard\", className)}\n                ref={ref}\n                onKeyDown={onKeyDown}\n            >\n                {shouldRenderHeader && (\n                    <div className=\"mx_BaseCard_header\">\n                        {backButton}\n                        {typeof header === \"string\" ? (\n                            <div className=\"mx_BaseCard_header_title\">\n                                <Text\n                                    size=\"md\"\n                                    weight=\"medium\"\n                                    className=\"mx_BaseCard_header_title_heading\"\n                                    role=\"heading\"\n                                >\n                                    {header}\n                                </Text>\n                            </div>\n                        ) : (\n                            (header ?? <div className=\"mx_BaseCard_header_spacer\" />)\n                        )}\n                        {closeButton}\n                    </div>\n                )}\n                {children}\n                {footer && <div className=\"mx_BaseCard_footer\">{footer}</div>}\n            </div>\n        </CardContext.Provider>\n    );\n};\n\nexport default BaseCard;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { type RoomMember, type User } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../languageHandler\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport Spinner from \"../elements/Spinner\";\n\nexport const PendingActionSpinner: React.FC<{ text: string }> = ({ text }) => {\n    return (\n        <div className=\"mx_EncryptionInfo_spinner\">\n            <Spinner />\n            {text}\n        </div>\n    );\n};\n\ninterface IProps {\n    waitingForOtherParty: boolean;\n    waitingForNetwork: boolean;\n    member: RoomMember | User;\n    onStartVerification: () => Promise<void>;\n    isRoomEncrypted: boolean;\n    inDialog: boolean;\n    isSelfVerification: boolean;\n}\n\nconst EncryptionInfo: React.FC<IProps> = ({\n    waitingForOtherParty,\n    waitingForNetwork,\n    member,\n    onStartVerification,\n    isRoomEncrypted,\n    inDialog,\n    isSelfVerification,\n}: IProps) => {\n    let content: JSX.Element;\n    if (waitingForOtherParty && isSelfVerification) {\n        content = <div>{_t(\"encryption|verification|once_accepted_can_continue\")}</div>;\n    } else if (waitingForOtherParty || waitingForNetwork) {\n        let text: string;\n        if (waitingForOtherParty) {\n            text = _t(\"encryption|verification|waiting_for_user_accept\", {\n                displayName: (member as User).displayName || (member as RoomMember).name || member.userId,\n            });\n        } else {\n            text = _t(\"encryption|verification|accepting\");\n        }\n        content = <PendingActionSpinner text={text} />;\n    } else {\n        content = (\n            <AccessibleButton\n                kind=\"primary\"\n                className=\"mx_UserInfo_wideButton mx_UserInfo_startVerification\"\n                onClick={onStartVerification}\n            >\n                {_t(\"encryption|verification|start_button\")}\n            </AccessibleButton>\n        );\n    }\n\n    let description: JSX.Element;\n    if (isRoomEncrypted) {\n        description = (\n            <div>\n                <p>{_t(\"user_info|room_encrypted\")}</p>\n                <p>{_t(\"user_info|room_encrypted_detail\")}</p>\n            </div>\n        );\n    } else {\n        description = (\n            <div>\n                <p>{_t(\"user_info|room_unencrypted\")}</p>\n                <p>{_t(\"user_info|room_unencrypted_detail\")}</p>\n            </div>\n        );\n    }\n\n    if (inDialog) {\n        return content;\n    }\n\n    return (\n        <React.Fragment>\n            <div data-testid=\"encryption-info-description\" className=\"mx_UserInfo_container\">\n                <h3>{_t(\"settings|security|encryption_section\")}</h3>\n                {description}\n            </div>\n            <div className=\"mx_UserInfo_container\">\n                <h3>{_t(\"user_info|verify_button\")}</h3>\n                <div>\n                    <p>{_t(\"user_info|verify_explainer\")}</p>\n                    <p>{_t(\"encryption|verification|in_person\")}</p>\n                    {content}\n                </div>\n            </div>\n        </React.Fragment>\n    );\n};\n\nexport default EncryptionInfo;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport QRCode from \"../QRCode\";\n\ninterface IProps {\n    /** The data for the QR code. If `undefined`, a spinner is shown. */\n    qrCodeBytes: undefined | Uint8ClampedArray;\n}\n\nexport default class VerificationQRCode extends React.PureComponent<IProps> {\n    public render(): React.ReactNode {\n        return (\n            <QRCode\n                data={this.props.qrCodeBytes === undefined ? null : [{ data: this.props.qrCodeBytes, mode: \"byte\" }]}\n                className=\"mx_VerificationQRCode\"\n                width={196}\n            />\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport {\n    type ShowQrCodeCallbacks,\n    type ShowSasCallbacks,\n    VerificationPhase as Phase,\n    type VerificationRequest,\n    VerificationRequestEvent,\n    VerifierEvent,\n} from \"matrix-js-sdk/src/crypto-api\";\nimport { type Device, type RoomMember, type User } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { VerificationMethod } from \"matrix-js-sdk/src/types\";\n\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport VerificationQRCode from \"../elements/crypto/VerificationQRCode\";\nimport { _t } from \"../../../languageHandler\";\nimport SdkConfig from \"../../../SdkConfig\";\nimport E2EIcon from \"../rooms/E2EIcon\";\nimport Spinner from \"../elements/Spinner\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport VerificationShowSas from \"../verification/VerificationShowSas\";\nimport { getDeviceCryptoInfo } from \"../../../utils/crypto/deviceInfo\";\nimport { E2EStatus } from \"../../../utils/ShieldUtils\";\n\ninterface IProps {\n    layout: string;\n    request: VerificationRequest;\n    member: RoomMember | User;\n    phase?: Phase;\n    onClose: () => void;\n    isRoomEncrypted: boolean;\n    inDialog: boolean;\n}\n\ninterface IState {\n    /**\n     * The data for the QR code to display.\n     *\n     * We attempt to calculate this once the verification request transitions into the \"Ready\" phase. If the other\n     * side cannot scan QR codes, it will remain `undefined`.\n     */\n    qrCodeBytes: Uint8ClampedArray | undefined;\n\n    sasEvent: ShowSasCallbacks | null;\n    emojiButtonClicked?: boolean;\n    reciprocateButtonClicked?: boolean;\n    reciprocateQREvent: ShowQrCodeCallbacks | null;\n\n    /**\n     * Details of the other device involved in the transaction.\n     *\n     * `undefined` if there is not (yet) another device in the transaction, or if we do not know about it.\n     */\n    otherDeviceDetails?: Device;\n}\n\nexport default class VerificationPanel extends React.PureComponent<IProps, IState> {\n    private hasVerifier: boolean;\n\n    /** have we yet tried to check the other device's info */\n    private haveCheckedDevice = false;\n\n    /** have we yet tried to get the QR code */\n    private haveFetchedQRCode = false;\n\n    public constructor(props: IProps) {\n        super(props);\n        this.state = { qrCodeBytes: undefined, sasEvent: null, reciprocateQREvent: null };\n        this.hasVerifier = false;\n    }\n\n    private renderQRPhase(): JSX.Element {\n        const { member, request } = this.props;\n        const showSAS: boolean = request.otherPartySupportsMethod(VerificationMethod.Sas);\n        const showQR: boolean = request.otherPartySupportsMethod(VerificationMethod.ScanQrCode);\n        const brand = SdkConfig.get().brand;\n\n        const noCommonMethodError: JSX.Element | null =\n            !showSAS && !showQR ? <p>{_t(\"encryption|verification|no_support_qr_emoji\", { brand })}</p> : null;\n\n        if (this.props.layout === \"dialog\") {\n            // HACK: This is a terrible idea.\n            let qrBlockDialog: JSX.Element | undefined;\n            let sasBlockDialog: JSX.Element | undefined;\n            if (showQR) {\n                qrBlockDialog = (\n                    <div className=\"mx_VerificationPanel_QRPhase_startOption\">\n                        <p>{_t(\"encryption|verification|qr_prompt\")}</p>\n                        <VerificationQRCode qrCodeBytes={this.state.qrCodeBytes} />\n                    </div>\n                );\n            }\n            if (showSAS) {\n                sasBlockDialog = (\n                    <div className=\"mx_VerificationPanel_QRPhase_startOption\">\n                        <p>{_t(\"encryption|verification|sas_prompt\")}</p>\n                        <span className=\"mx_VerificationPanel_QRPhase_helpText\">\n                            {_t(\"encryption|verification|sas_description\")}\n                        </span>\n                        <AccessibleButton\n                            disabled={this.state.emojiButtonClicked}\n                            onClick={this.startSAS}\n                            kind=\"primary\"\n                        >\n                            {_t(\"action|start\")}\n                        </AccessibleButton>\n                    </div>\n                );\n            }\n            const or =\n                qrBlockDialog && sasBlockDialog ? (\n                    <div className=\"mx_VerificationPanel_QRPhase_betweenText\">\n                        {_t(\"encryption|verification|qr_or_sas\", {\n                            emojiCompare: \"\",\n                            qrCode: \"\",\n                        })}\n                    </div>\n                ) : null;\n            return (\n                <div>\n                    {_t(\"encryption|verification|verify_by_completing_one_of\")}\n                    <div className=\"mx_VerificationPanel_QRPhase_startOptions\">\n                        {qrBlockDialog}\n                        {or}\n                        {sasBlockDialog}\n                        {noCommonMethodError}\n                    </div>\n                </div>\n            );\n        }\n\n        let qrBlock: JSX.Element | undefined;\n        if (showQR) {\n            qrBlock = (\n                <div className=\"mx_UserInfo_container\">\n                    <h3>{_t(\"encryption|verification|scan_qr\")}</h3>\n                    <p>\n                        {_t(\"encryption|verification|scan_qr_explainer\", {\n                            displayName: (member as User).displayName || (member as RoomMember).name || member.userId,\n                        })}\n                    </p>\n\n                    <div className=\"mx_VerificationPanel_qrCode\">\n                        <VerificationQRCode qrCodeBytes={this.state.qrCodeBytes} />\n                    </div>\n                </div>\n            );\n        }\n\n        let sasBlock: JSX.Element | undefined;\n        if (showSAS) {\n            const disabled = this.state.emojiButtonClicked;\n            const sasLabel = showQR\n                ? _t(\"encryption|verification|verify_emoji_prompt_qr\")\n                : _t(\"encryption|verification|verify_emoji_prompt\");\n\n            // Note: mx_VerificationPanel_verifyByEmojiButton is for the end-to-end tests\n            sasBlock = (\n                <div className=\"mx_UserInfo_container\">\n                    <h3>{_t(\"encryption|verification|verify_emoji\")}</h3>\n                    <p>{sasLabel}</p>\n                    <AccessibleButton\n                        disabled={disabled}\n                        kind=\"primary\"\n                        className=\"mx_UserInfo_wideButton mx_VerificationPanel_verifyByEmojiButton\"\n                        onClick={this.startSAS}\n                    >\n                        {_t(\"encryption|verification|verify_emoji\")}\n                    </AccessibleButton>\n                </div>\n            );\n        }\n\n        const noCommonMethodBlock = noCommonMethodError ? (\n            <div className=\"mx_UserInfo_container\">{noCommonMethodError}</div>\n        ) : null;\n\n        // TODO: add way to open camera to scan a QR code\n        return (\n            <React.Fragment>\n                {qrBlock}\n                {sasBlock}\n                {noCommonMethodBlock}\n            </React.Fragment>\n        );\n    }\n\n    private onReciprocateYesClick = (): void => {\n        if (!this.state.reciprocateQREvent) return;\n        this.setState({ reciprocateButtonClicked: true });\n        this.state.reciprocateQREvent?.confirm();\n    };\n\n    private onReciprocateNoClick = (): void => {\n        if (!this.state.reciprocateQREvent) return;\n        this.setState({ reciprocateButtonClicked: true });\n        this.state.reciprocateQREvent?.cancel();\n    };\n\n    /**\n     * Get details of the other device involved in the verification, if we haven't before, and store in the state.\n     */\n    private async maybeGetOtherDevice(): Promise<void> {\n        if (this.haveCheckedDevice) return;\n\n        const client = MatrixClientPeg.safeGet();\n        const deviceId = this.props.request?.otherDeviceId;\n        const userId = client.getUserId();\n        if (!deviceId || !userId) {\n            return;\n        }\n        this.haveCheckedDevice = true;\n        this.setState({ otherDeviceDetails: await getDeviceCryptoInfo(client, userId, deviceId) });\n    }\n\n    private renderQRReciprocatePhase(): JSX.Element {\n        const { member, request } = this.props;\n        const description = request.isSelfVerification\n            ? _t(\"encryption|verification|qr_reciprocate_check_again_device\")\n            : _t(\"encryption|verification|qr_reciprocate_same_shield_user\", {\n                  displayName: (member as User).displayName || (member as RoomMember).name || member.userId,\n              });\n        let body: JSX.Element;\n        if (this.state.reciprocateQREvent) {\n            // Element Web doesn't support scanning yet, so assume here we're the client being scanned.\n            body = (\n                <React.Fragment>\n                    <p>{description}</p>\n                    <E2EIcon isUser={true} status={E2EStatus.Verified} size={128} hideTooltip={true} />\n                    <div className=\"mx_VerificationPanel_reciprocateButtons\">\n                        <AccessibleButton\n                            kind=\"primary\"\n                            disabled={this.state.reciprocateButtonClicked}\n                            onClick={this.onReciprocateYesClick}\n                        >\n                            {_t(\"encryption|verification|qr_reciprocate_yes\")}\n                        </AccessibleButton>\n                        <AccessibleButton\n                            disabled={this.state.reciprocateButtonClicked}\n                            onClick={this.onReciprocateNoClick}\n                        >\n                            {_t(\"encryption|verification|qr_reciprocate_no\")}\n                        </AccessibleButton>\n                    </div>\n                </React.Fragment>\n            );\n        } else {\n            body = (\n                <p>\n                    <Spinner />\n                </p>\n            );\n        }\n        return <div className=\"mx_UserInfo_container mx_VerificationPanel_reciprocate_section\">{body}</div>;\n    }\n\n    private renderVerifiedPhase(): JSX.Element {\n        const { member, request } = this.props;\n\n        let text: string | undefined;\n        if (!request.isSelfVerification) {\n            if (this.props.isRoomEncrypted) {\n                text = _t(\"encryption|verification|prompt_encrypted\");\n            } else {\n                text = _t(\"encryption|verification|prompt_unencrypted\");\n            }\n        }\n\n        let description: string;\n        if (request.isSelfVerification) {\n            description = _t(\"encryption|verification|now_you_can\");\n        } else {\n            description = _t(\"encryption|verification|successful_user\", {\n                displayName: (member as User).displayName || (member as RoomMember).name || member.userId,\n            });\n        }\n\n        return (\n            <div className=\"mx_UserInfo_container mx_VerificationPanel_verified_section\">\n                <p>{description}</p>\n                <E2EIcon isUser={true} status={E2EStatus.Verified} size={128} hideTooltip={true} />\n                {text ? <p>{text}</p> : null}\n                <AccessibleButton kind=\"primary\" className=\"mx_UserInfo_wideButton\" onClick={this.props.onClose}>\n                    {_t(\"action|got_it\")}\n                </AccessibleButton>\n            </div>\n        );\n    }\n\n    private renderCancelledPhase(): JSX.Element {\n        return (\n            <div className=\"mx_UserInfo_container\">\n                <p>{_t(\"encryption|verification|cancelled_verification\")}</p>\n\n                <AccessibleButton kind=\"primary\" className=\"mx_UserInfo_wideButton\" onClick={this.props.onClose}>\n                    {_t(\"action|got_it\")}\n                </AccessibleButton>\n            </div>\n        );\n    }\n\n    public render(): React.ReactNode {\n        const { member, phase, request } = this.props;\n\n        const displayName = (member as User).displayName || (member as RoomMember).name || member.userId;\n\n        switch (phase) {\n            case Phase.Ready:\n                return this.renderQRPhase();\n            case Phase.Started:\n                switch (request.chosenMethod) {\n                    case VerificationMethod.Reciprocate:\n                        return this.renderQRReciprocatePhase();\n                    case VerificationMethod.Sas: {\n                        const emojis = this.state.sasEvent ? (\n                            <VerificationShowSas\n                                displayName={displayName}\n                                otherDeviceDetails={this.state.otherDeviceDetails}\n                                sas={this.state.sasEvent.sas}\n                                onCancel={this.onSasMismatchesClick}\n                                onDone={this.onSasMatchesClick}\n                                inDialog={this.props.inDialog}\n                                isSelf={request.isSelfVerification}\n                            />\n                        ) : (\n                            <Spinner />\n                        );\n                        return <div className=\"mx_UserInfo_container\">{emojis}</div>;\n                    }\n                    default:\n                        return null;\n                }\n            case Phase.Done:\n                return this.renderVerifiedPhase();\n            case Phase.Cancelled:\n                return this.renderCancelledPhase();\n        }\n        logger.error(\"VerificationPanel unhandled phase:\", phase);\n        return null;\n    }\n\n    private startSAS = async (): Promise<void> => {\n        this.setState({ emojiButtonClicked: true });\n        await this.props.request.startVerification(VerificationMethod.Sas);\n    };\n\n    private onSasMatchesClick = (): void => {\n        this.state.sasEvent?.confirm();\n    };\n\n    private onSasMismatchesClick = (): void => {\n        this.state.sasEvent?.mismatch();\n    };\n\n    private updateVerifierState = (): void => {\n        // this method is only called once we know there is a verifier.\n        const verifier = this.props.request.verifier!;\n        const sasEvent = verifier.getShowSasCallbacks();\n        const reciprocateQREvent = verifier.getReciprocateQrCodeCallbacks();\n        verifier.off(VerifierEvent.ShowSas, this.updateVerifierState);\n        verifier.off(VerifierEvent.ShowReciprocateQr, this.updateVerifierState);\n        this.setState({ sasEvent, reciprocateQREvent });\n    };\n\n    private onRequestChange = async (): Promise<void> => {\n        const { request } = this.props;\n\n        // if we have a device ID and did not have one before, fetch the device's details\n        this.maybeGetOtherDevice();\n\n        // if we have had a reply from the other side (ie, the phase is \"ready\") and we have not\n        // yet done so, fetch the QR code\n        if (request.phase === Phase.Ready && !this.haveFetchedQRCode) {\n            this.haveFetchedQRCode = true;\n            request.generateQRCode().then(\n                (buf) => {\n                    this.setState({ qrCodeBytes: buf });\n                },\n                (error) => {\n                    console.error(\"Error generating QR code:\", error);\n                },\n            );\n        }\n\n        const hadVerifier = this.hasVerifier;\n        this.hasVerifier = !!request.verifier;\n        if (!hadVerifier && this.hasVerifier) {\n            request.verifier?.on(VerifierEvent.ShowSas, this.updateVerifierState);\n            request.verifier?.on(VerifierEvent.ShowReciprocateQr, this.updateVerifierState);\n            try {\n                // on the requester side, this is also awaited in startSAS,\n                // but that's ok as verify should return the same promise.\n                await request.verifier?.verify();\n            } catch (err) {\n                logger.error(\"error verify\", err);\n            }\n        }\n    };\n\n    public componentDidMount(): void {\n        const { request } = this.props;\n        request.on(VerificationRequestEvent.Change, this.onRequestChange);\n        if (request.verifier) {\n            const sasEvent = request.verifier.getShowSasCallbacks();\n            const reciprocateQREvent = request.verifier.getReciprocateQrCodeCallbacks();\n            this.setState({ sasEvent, reciprocateQREvent });\n        }\n        this.onRequestChange();\n    }\n\n    public componentWillUnmount(): void {\n        const { request } = this.props;\n        if (request.verifier) {\n            request.verifier.off(VerifierEvent.ShowSas, this.updateVerifierState);\n            request.verifier.off(VerifierEvent.ShowReciprocateQr, this.updateVerifierState);\n        }\n        request.off(VerificationRequestEvent.Change, this.onRequestChange);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useCallback, useEffect, useRef, useState } from \"react\";\nimport { VerificationPhase, type VerificationRequest, VerificationRequestEvent } from \"matrix-js-sdk/src/crypto-api\";\nimport { type RoomMember, type User } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n// ErrorDialog needs path to the image, not the image node\n// eslint-disable-next-line no-restricted-imports\nimport ErrorSolidIcon from \"@vector-im/compound-design-tokens/icons/error-solid.svg\";\n\nimport EncryptionInfo from \"./EncryptionInfo\";\nimport VerificationPanel from \"./VerificationPanel\";\nimport { ensureDMExists } from \"../../../createRoom\";\nimport { useTypedEventEmitter } from \"../../../hooks/useEventEmitter\";\nimport Modal from \"../../../Modal\";\nimport { _t } from \"../../../languageHandler\";\nimport { RightPanelPhases } from \"../../../stores/right-panel/RightPanelStorePhases\";\nimport RightPanelStore from \"../../../stores/right-panel/RightPanelStore\";\nimport ErrorDialog from \"../dialogs/ErrorDialog\";\nimport { useMatrixClientContext } from \"../../../contexts/MatrixClientContext\";\n\n// cancellation codes which constitute a key mismatch\nconst MISMATCHES = [\"m.key_mismatch\", \"m.user_error\", \"m.mismatched_sas\"];\n\ninterface IProps {\n    member: RoomMember | User;\n    onClose: () => void;\n    verificationRequest?: VerificationRequest;\n    verificationRequestPromise?: Promise<VerificationRequest>;\n    layout: string;\n    isRoomEncrypted: boolean;\n}\n\nconst EncryptionPanel: React.FC<IProps> = (props: IProps) => {\n    const cli = useMatrixClientContext();\n    const { verificationRequest, verificationRequestPromise, member, onClose, layout, isRoomEncrypted } = props;\n    const [request, setRequest] = useState(verificationRequest);\n    // state to show a spinner immediately after clicking \"start verification\",\n    // before we have a request\n    const [isRequesting, setRequesting] = useState(false);\n    const [phase, doSetPhase] = useState(request?.phase);\n    const setPhase = (phase: VerificationPhase | undefined): void => {\n        logger.debug(`EncryptionPanel: phase now ${phase === undefined ? phase : VerificationPhase[phase]}`);\n        doSetPhase(phase);\n    };\n\n    useEffect(() => {\n        setRequest(verificationRequest);\n        if (verificationRequest) {\n            setRequesting(false);\n            setPhase(verificationRequest.phase);\n        }\n    }, [verificationRequest]);\n\n    useEffect(() => {\n        async function awaitPromise(): Promise<void> {\n            setRequesting(true);\n            const requestFromPromise = await verificationRequestPromise;\n            setRequesting(false);\n            setRequest(requestFromPromise);\n            setPhase(requestFromPromise?.phase);\n        }\n        if (verificationRequestPromise) {\n            awaitPromise();\n        }\n    }, [verificationRequestPromise]);\n    // Use a ref to track whether we are already showing the mismatch modal as state may not update fast enough\n    // if two change events are fired in quick succession like can happen with rust crypto.\n    const isShowingMismatchModal = useRef(false);\n    const changeHandler = useCallback(() => {\n        // handle transitions -> cancelled for mismatches which fire a modal instead of showing a card\n        if (\n            !isShowingMismatchModal.current &&\n            request?.phase === VerificationPhase.Cancelled &&\n            MISMATCHES.includes(request.cancellationCode ?? \"\")\n        ) {\n            isShowingMismatchModal.current = true;\n            Modal.createDialog(ErrorDialog, {\n                headerImage: ErrorSolidIcon,\n                title: _t(\"encryption|messages_not_secure|title\"),\n                description: (\n                    <div>\n                        {_t(\"encryption|messages_not_secure|heading\")}\n                        <ul>\n                            <li>{_t(\"encryption|messages_not_secure|cause_1\")}</li>\n                            <li>{_t(\"encryption|messages_not_secure|cause_2\")}</li>\n                            <li>{_t(\"encryption|messages_not_secure|cause_3\")}</li>\n                            <li>{_t(\"encryption|messages_not_secure|cause_4\")}</li>\n                        </ul>\n                    </div>\n                ),\n                onFinished: onClose,\n            });\n            return; // don't update phase here as we will be transitioning away from this view shortly\n        }\n\n        if (request) {\n            setPhase(request.phase);\n        }\n    }, [onClose, request]);\n\n    useTypedEventEmitter(request, VerificationRequestEvent.Change, changeHandler);\n\n    const onStartVerification = useCallback(async (): Promise<void> => {\n        setRequesting(true);\n        let verificationRequest_: VerificationRequest;\n        try {\n            const roomId = await ensureDMExists(cli, member.userId);\n            if (!roomId) {\n                throw new Error(\"Unable to create Room for verification\");\n            }\n            verificationRequest_ = await cli.getCrypto()!.requestVerificationDM(member.userId, roomId);\n        } catch (e) {\n            console.error(\"Error starting verification\", e);\n            setRequesting(false);\n\n            Modal.createDialog(ErrorDialog, {\n                headerImage: ErrorSolidIcon,\n                title: _t(\"encryption|verification|error_starting_title\"),\n                description: _t(\"encryption|verification|error_starting_description\"),\n            });\n            return;\n        }\n        setRequest(verificationRequest_);\n        setPhase(verificationRequest_.phase);\n        // Notify the RightPanelStore about this\n        if (RightPanelStore.instance.currentCard.phase != RightPanelPhases.EncryptionPanel) {\n            RightPanelStore.instance.pushCard({\n                phase: RightPanelPhases.EncryptionPanel,\n                state: { member, verificationRequest: verificationRequest_ },\n            });\n        }\n        if (!RightPanelStore.instance.isOpen) RightPanelStore.instance.togglePanel(null);\n    }, [cli, member]);\n\n    const requested: boolean =\n        (!request && isRequesting) ||\n        (!!request &&\n            (phase === VerificationPhase.Requested || phase === VerificationPhase.Unsent || phase === undefined));\n    const isSelfVerification = request ? request.isSelfVerification : member.userId === cli.getUserId();\n\n    if (!request || requested) {\n        const initiatedByMe = (!request && isRequesting) || (!!request && request.initiatedByMe);\n        return (\n            <EncryptionInfo\n                isRoomEncrypted={isRoomEncrypted}\n                onStartVerification={onStartVerification}\n                member={member}\n                isSelfVerification={isSelfVerification}\n                waitingForOtherParty={requested && initiatedByMe}\n                waitingForNetwork={requested && !initiatedByMe}\n                inDialog={layout === \"dialog\"}\n            />\n        );\n    } else {\n        return (\n            <VerificationPanel\n                isRoomEncrypted={isRoomEncrypted}\n                layout={layout}\n                onClose={onClose}\n                member={member}\n                request={request}\n                key={request.transactionId}\n                inDialog={layout === \"dialog\"}\n                phase={phase}\n            />\n        );\n    }\n};\n\nexport default EncryptionPanel;\n","/*\nCopyright 2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\nimport { useEffect, useState } from \"react\";\nimport {\n    type MatrixClient,\n    MatrixError,\n    ProfileKeyMSC4175Timezone,\n    ProfileKeyTimezone,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { getTwelveHourOptions } from \"../DateUtils.ts\";\nimport { useSettingValue } from \"./useSettings.ts\";\n\nconst log = logger.getChild(\"useUserTimezone\");\n\n/**\n * Fetch a user's delclared timezone through their profile, and return\n * a friendly string of the current time for that user. This will keep\n * in sync with the current time, and will be refreshed once a minute.\n *\n * @param cli The Matrix Client instance.\n * @param userId The userID to fetch the timezone for.\n * @returns A timezone name and friendly string for the user's timezone, or\n *          null if the user has no timezone or the timezone was not recognised\n *          by the browser.\n */\nexport const useUserTimezone = (cli: MatrixClient, userId: string): { timezone: string; friendly: string } | null => {\n    const [timezone, setTimezone] = useState<string>();\n    const [updateInterval, setUpdateInterval] = useState<ReturnType<typeof setTimeout>>();\n    const [friendly, setFriendly] = useState<string>();\n    const [supported, setSupported] = useState<boolean>();\n    const showTwelveHour = useSettingValue(\"showTwelveHourTimestamps\");\n\n    useEffect(() => {\n        if (!cli || supported !== undefined) {\n            return;\n        }\n        cli.doesServerSupportExtendedProfiles()\n            .then(setSupported)\n            .catch((ex) => {\n                console.warn(\"Unable to determine if extended profiles are supported\", ex);\n            });\n    }, [supported, cli]);\n\n    useEffect(() => {\n        return () => {\n            if (updateInterval) {\n                clearInterval(updateInterval);\n            }\n        };\n    }, [updateInterval]);\n\n    useEffect(() => {\n        if (supported !== true) {\n            return;\n        }\n        (async () => {\n            log.debug(\"Trying to fetch TZ for\", userId);\n            try {\n                const userProfile = await cli.getExtendedProfile(userId);\n                // In a future spec release, remove support for legacy key.\n                const tz = userProfile[ProfileKeyTimezone] ?? userProfile[ProfileKeyMSC4175Timezone];\n                if (typeof tz !== \"string\") {\n                    // Definitely not a tz.\n                    throw Error(\"Timezone value was not a string\");\n                }\n                // This will validate the timezone for us.\n                // eslint-disable-next-line new-cap\n                Intl.DateTimeFormat(undefined, { timeZone: tz });\n\n                const updateTime = (): void => {\n                    const currentTime = new Date();\n                    const friendly = currentTime.toLocaleString(undefined, {\n                        ...getTwelveHourOptions(showTwelveHour),\n                        timeZone: tz,\n                        hour: \"2-digit\",\n                        minute: \"2-digit\",\n                        timeZoneName: \"shortOffset\",\n                    });\n                    setTimezone(tz);\n                    setFriendly(friendly);\n                    setUpdateInterval(setTimeout(updateTime, (60 - currentTime.getSeconds()) * 1000));\n                };\n                updateTime();\n            } catch (ex) {\n                setTimezone(undefined);\n                setFriendly(undefined);\n                setUpdateInterval(undefined);\n                if (ex instanceof MatrixError && ex.errcode === \"M_NOT_FOUND\") {\n                    // No timezone set, ignore.\n                    return;\n                }\n                log.warn(`Could not render current timezone for ${userId}`, ex);\n            }\n        })();\n    }, [supported, userId, cli, showTwelveHour]);\n\n    if (!timezone || !friendly) {\n        return null;\n    }\n\n    return {\n        friendly,\n        timezone,\n    };\n};\n","/*\nCopyright 2025 New Vector Ltd.\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { RoomMember, type User } from \"matrix-js-sdk/src/matrix\";\nimport { useCallback, useContext } from \"react\";\n\nimport { mediaFromMxc } from \"../../../../customisations/Media\";\nimport Modal from \"../../../../Modal\";\nimport ImageView from \"../../../views/elements/ImageView\";\nimport SdkConfig from \"../../../../SdkConfig\";\nimport MatrixClientContext from \"../../../../contexts/MatrixClientContext\";\nimport { type Member } from \"../../../views/right_panel/UserInfo\";\nimport { useUserTimezone } from \"../../../../hooks/useUserTimezone\";\nimport UserIdentifierCustomisations from \"../../../../customisations/UserIdentifier\";\n\nexport interface PresenceInfo {\n    lastActiveAgo: number | undefined;\n    currentlyActive: boolean | undefined;\n    state: string | undefined;\n}\n\nexport interface TimezoneInfo {\n    timezone: string;\n    friendly: string;\n}\n\nexport interface UserInfoHeaderState {\n    /**\n     * callback function when selected user avatar is clicked in user info\n     */\n    onMemberAvatarClick: () => void;\n    /**\n     * Object containing information about the precense of the selected user\n     */\n    precenseInfo: PresenceInfo;\n    /**\n     * Boolean that show or hide the precense information\n     */\n    showPresence: boolean;\n    /**\n     *  Timezone object\n     */\n    timezoneInfo: TimezoneInfo | null;\n    /**\n     * Displayed identifier for the selected user\n     */\n    userIdentifier: string | null;\n}\ninterface UserInfoHeaderViewModelProps {\n    member: Member;\n    roomId?: string;\n}\n\n/**\n * View model for the userInfoHeaderView\n * props\n * @see {@link UserInfoHeaderState} for more information about what this view model returns.\n */\nexport function useUserfoHeaderViewModel({ member, roomId }: UserInfoHeaderViewModelProps): UserInfoHeaderState {\n    const cli = useContext(MatrixClientContext);\n\n    let showPresence = true;\n\n    const precenseInfo: PresenceInfo = {\n        lastActiveAgo: undefined,\n        currentlyActive: undefined,\n        state: undefined,\n    };\n\n    const enablePresenceByHsUrl = SdkConfig.get(\"enable_presence_by_hs_url\");\n\n    const timezoneInfo = useUserTimezone(cli, member.userId);\n\n    const userIdentifier = UserIdentifierCustomisations.getDisplayUserIdentifier?.(member.userId, {\n        roomId,\n        withDisplayName: true,\n    });\n\n    const onMemberAvatarClick = useCallback(() => {\n        const avatarUrl = (member as RoomMember).getMxcAvatarUrl\n            ? (member as RoomMember).getMxcAvatarUrl()\n            : (member as User).avatarUrl;\n\n        const httpUrl = mediaFromMxc(avatarUrl).srcHttp;\n        if (!httpUrl) return;\n\n        const params = {\n            src: httpUrl,\n            name: (member as RoomMember).name || (member as User).displayName,\n        };\n\n        Modal.createDialog(ImageView, params, \"mx_Dialog_lightbox\", undefined, true);\n    }, [member]);\n\n    if (member instanceof RoomMember && member.user) {\n        precenseInfo.state = member.user.presence;\n        precenseInfo.lastActiveAgo = member.user.lastActiveAgo;\n        precenseInfo.currentlyActive = member.user.currentlyActive;\n    }\n\n    if (enablePresenceByHsUrl && enablePresenceByHsUrl[cli.baseUrl] !== undefined) {\n        showPresence = enablePresenceByHsUrl[cli.baseUrl];\n    }\n\n    return {\n        onMemberAvatarClick,\n        showPresence,\n        precenseInfo,\n        timezoneInfo,\n        userIdentifier,\n    };\n}\n","/*\nCopyright 2025 New Vector Ltd.\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient, type RoomMember, type User } from \"matrix-js-sdk/src/matrix\";\nimport { useContext } from \"react\";\nimport { type UserVerificationStatus } from \"matrix-js-sdk/src/crypto-api\";\n\nimport MatrixClientContext from \"../../../../contexts/MatrixClientContext\";\nimport { type IDevice } from \"../../../views/right_panel/UserInfo\";\nimport { useAsyncMemo } from \"../../../../hooks/useAsyncMemo\";\nimport { verifyUser } from \"../../../../verification\";\n\nexport interface UserInfoVerificationSectionState {\n    /**\n     * variables used to check if we can verify the user and display the verify button\n     */\n    canVerify: boolean;\n    hasCrossSigningKeys: boolean | undefined;\n    /**\n     * used to display correct badge value\n     */\n    isUserVerified: boolean;\n    /**\n     * callback function when verifyUser button is clicked\n     */\n    verifySelectedUser: () => Promise<void>;\n}\n\nconst useHasCrossSigningKeys = (cli: MatrixClient, member: User, canVerify: boolean): boolean | undefined => {\n    return useAsyncMemo(async () => {\n        if (!canVerify) return undefined;\n        return cli.getCrypto()?.userHasCrossSigningKeys(member.userId, true);\n    }, [cli, member, canVerify]);\n};\n\n/**\n * View model for the userInfoVerificationHeaderView\n * @see {@link UserInfoVerificationSectionState} for more information about what this view model returns.\n */\nexport const useUserInfoVerificationViewModel = (\n    member: User | RoomMember,\n    devices: IDevice[],\n): UserInfoVerificationSectionState => {\n    const cli = useContext(MatrixClientContext);\n\n    const userTrust = useAsyncMemo<UserVerificationStatus | undefined>(\n        async () => cli.getCrypto()?.getUserVerificationStatus(member.userId),\n        [member.userId],\n        // the user verification status is not initialized\n        undefined,\n    );\n    const hasUserVerificationStatus = Boolean(userTrust);\n    const isUserVerified = Boolean(userTrust?.isVerified());\n    const isMe = member.userId === cli.getUserId();\n    const canVerify = hasUserVerificationStatus && !isUserVerified && !isMe && devices && devices.length > 0;\n\n    const hasCrossSigningKeys = useHasCrossSigningKeys(cli, member as User, canVerify);\n    const verifySelectedUser = (): Promise<void> => verifyUser(cli, member as User);\n\n    return {\n        canVerify,\n        hasCrossSigningKeys,\n        isUserVerified,\n        verifySelectedUser,\n    };\n};\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type User, type RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { Text, Button, InlineSpinner, Badge } from \"@vector-im/compound-web\";\nimport { VerifiedIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\nimport { Flex } from \"@element-hq/web-shared-components\";\n\nimport { useUserInfoVerificationViewModel } from \"../../../viewmodels/right_panel/user_info/UserInfoHeaderVerificationViewModel\";\nimport { type IDevice } from \"../UserInfo\";\nimport { _t } from \"../../../../languageHandler\";\n\nexport const UserInfoHeaderVerificationView: React.FC<{\n    member: User | RoomMember;\n    devices: IDevice[];\n}> = ({ member, devices }) => {\n    let content;\n    const vm = useUserInfoVerificationViewModel(member, devices);\n\n    if (vm.isUserVerified) {\n        content = (\n            <Badge kind=\"green\" className=\"mx_UserInfo_verified_badge\">\n                <VerifiedIcon className=\"mx_UserInfo_verified_icon\" height=\"16px\" width=\"16px\" />\n                <Text size=\"sm\" weight=\"medium\" className=\"mx_UserInfo_verified_label\">\n                    {_t(\"common|verified\")}\n                </Text>\n            </Badge>\n        );\n    } else if (vm.hasCrossSigningKeys === undefined) {\n        // We are still fetching the cross-signing keys for the user, show spinner.\n        content = <InlineSpinner size={24} />;\n    } else if (vm.canVerify && vm.hasCrossSigningKeys) {\n        content = (\n            <div className=\"mx_UserInfo_container_verifyButton\">\n                <Button\n                    className=\"mx_UserInfo_verify_button\"\n                    kind=\"tertiary\"\n                    size=\"sm\"\n                    onClick={() => vm.verifySelectedUser()}\n                >\n                    {_t(\"user_info|verify_button\")}\n                </Button>\n            </div>\n        );\n    } else {\n        content = (\n            <Text className=\"mx_UserInfo_verification_unavailable\" size=\"sm\">\n                ({_t(\"user_info|verification_unavailable\")})\n            </Text>\n        );\n    }\n\n    return (\n        <Flex justify=\"center\" align=\"center\" className=\"mx_UserInfo_verification\">\n            {content}\n        </Flex>\n    );\n};\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { type User, type RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { Heading, Tooltip, Text } from \"@vector-im/compound-web\";\nimport { Flex } from \"@element-hq/web-shared-components\";\n\nimport { useUserfoHeaderViewModel } from \"../../../viewmodels/right_panel/user_info/UserInfoHeaderViewModel\";\nimport MemberAvatar from \"../../avatars/MemberAvatar\";\nimport { Container, type Member, type IDevice } from \"../UserInfo\";\nimport PresenceLabel from \"../../rooms/PresenceLabel\";\nimport CopyableText from \"../../elements/CopyableText\";\nimport { UserInfoHeaderVerificationView } from \"./UserInfoHeaderVerificationView\";\n\nexport interface UserInfoHeaderViewProps {\n    member: Member;\n    roomId?: string;\n    devices: IDevice[];\n    hideVerificationSection: boolean;\n}\n\nexport const UserInfoHeaderView: React.FC<UserInfoHeaderViewProps> = ({\n    member,\n    devices,\n    roomId,\n    hideVerificationSection,\n}) => {\n    const vm = useUserfoHeaderViewModel({ member, roomId });\n    const avatarUrl = (member as User).avatarUrl;\n    const displayName = (member as RoomMember).rawDisplayName;\n\n    let presenceLabel: JSX.Element | undefined;\n\n    if (vm.showPresence) {\n        presenceLabel = (\n            <PresenceLabel\n                activeAgo={vm.precenseInfo.lastActiveAgo}\n                currentlyActive={vm.precenseInfo.currentlyActive}\n                presenceState={vm.precenseInfo.state}\n                className=\"mx_UserInfo_profileStatus\"\n                coloured\n            />\n        );\n    }\n\n    return (\n        <React.Fragment>\n            <div className=\"mx_UserInfo_avatar\">\n                <div className=\"mx_UserInfo_avatar_transition\">\n                    <div className=\"mx_UserInfo_avatar_transition_child\">\n                        <MemberAvatar\n                            key={member.userId} // to instantly blank the avatar when UserInfo changes members\n                            member={member as RoomMember}\n                            size=\"120px\"\n                            resizeMethod=\"scale\"\n                            fallbackUserId={member.userId}\n                            onClick={vm.onMemberAvatarClick}\n                            urls={avatarUrl ? [avatarUrl] : undefined}\n                        />\n                    </div>\n                </div>\n            </div>\n\n            <Container className=\"mx_UserInfo_header\">\n                <Flex direction=\"column\" align=\"center\" className=\"mx_UserInfo_profile\">\n                    <Heading size=\"sm\" weight=\"semibold\" as=\"h1\" dir=\"auto\">\n                        <Flex className=\"mx_UserInfo_profile_name\" direction=\"row-reverse\" align=\"center\">\n                            {displayName}\n                        </Flex>\n                    </Heading>\n                    {presenceLabel}\n                    {vm.timezoneInfo && (\n                        <Tooltip label={vm.timezoneInfo?.timezone ?? \"\"}>\n                            <Flex align=\"center\" className=\"mx_UserInfo_timezone\">\n                                <Text size=\"sm\" weight=\"regular\">\n                                    {vm.timezoneInfo?.friendly ?? \"\"}\n                                </Text>\n                            </Flex>\n                        </Tooltip>\n                    )}\n                    <Text size=\"sm\" weight=\"semibold\" className=\"mx_UserInfo_profile_mxid\">\n                        <CopyableText getTextToCopy={() => vm.userIdentifier} border={false}>\n                            {vm.userIdentifier}\n                        </CopyableText>\n                    </Text>\n                </Flex>\n                {!hideVerificationSection && <UserInfoHeaderVerificationView member={member} devices={devices} />}\n            </Container>\n        </React.Fragment>\n    );\n};\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useCallback, useEffect, useState } from \"react\";\nimport {\n    EventType,\n    type RoomMember,\n    type IPowerLevelsContent,\n    type Room,\n    RoomStateEvent,\n    type MatrixClient,\n    type User,\n    type MatrixEvent,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { useAsyncMemo } from \"../../../../hooks/useAsyncMemo\";\nimport { useTypedEventEmitter } from \"../../../../hooks/useEventEmitter\";\nimport Modal from \"../../../../Modal\";\nimport ErrorDialog from \"../../../views/dialogs/ErrorDialog\";\nimport { _t } from \"../../../../languageHandler\";\nimport { type IRoomPermissions } from \"../../../views/right_panel/UserInfo\";\nimport { useMatrixClientContext } from \"../../../../contexts/MatrixClientContext\";\nimport QuestionDialog from \"../../../views/dialogs/QuestionDialog\";\nimport DMRoomMap from \"../../../../utils/DMRoomMap\";\n\nexport interface UserInfoBasicState {\n    // current room powerlevels\n    powerLevels: IPowerLevelsContent;\n    // getting user permissions in this room\n    roomPermissions: IRoomPermissions;\n    // numbers of operation in progress > 0\n    pendingUpdateCount: number;\n    // true if user is me\n    isMe: boolean;\n    // true if room is a DM for the user\n    isRoomDMForMember: boolean;\n    // Boolean to hide or show the deactivate button\n    showDeactivateButton: boolean;\n    // Method called when a deactivate user action is triggered\n    onSynapseDeactivate: () => void;\n    startUpdating: () => void;\n    stopUpdating: () => void;\n}\n\nexport const getPowerLevels = (room: Room): IPowerLevelsContent =>\n    room?.currentState?.getStateEvents(EventType.RoomPowerLevels, \"\")?.getContent() || {};\n\nexport const useRoomPermissions = (cli: MatrixClient, room: Room, user: RoomMember): IRoomPermissions => {\n    const [roomPermissions, setRoomPermissions] = useState<IRoomPermissions>({\n        // modifyLevelMax is the max PL we can set this user to, typically min(their PL, our PL) && canSetPL\n        modifyLevelMax: -1,\n        canEdit: false,\n        canInvite: false,\n    });\n\n    const updateRoomPermissions = useCallback(() => {\n        const powerLevels = room?.currentState.getStateEvents(EventType.RoomPowerLevels, \"\")?.getContent();\n        if (!powerLevels) return;\n\n        const me = room.getMember(cli.getUserId() || \"\");\n        if (!me) return;\n\n        const them = user;\n        const isMe = me.userId === them.userId;\n        const canAffectUser = them.powerLevel < me.powerLevel || isMe;\n\n        let modifyLevelMax = -1;\n        if (canAffectUser) {\n            const editPowerLevel = powerLevels.events?.[EventType.RoomPowerLevels] ?? powerLevels.state_default ?? 50;\n            if (me.powerLevel >= editPowerLevel) {\n                modifyLevelMax = me.powerLevel;\n            }\n        }\n\n        setRoomPermissions({\n            canInvite: me.powerLevel >= (powerLevels.invite ?? 0),\n            canEdit: modifyLevelMax >= 0,\n            modifyLevelMax,\n        });\n    }, [cli, user, room]);\n\n    useTypedEventEmitter(cli, RoomStateEvent.Update, updateRoomPermissions);\n    useEffect(() => {\n        updateRoomPermissions();\n        return () => {\n            setRoomPermissions({\n                modifyLevelMax: -1,\n                canEdit: false,\n                canInvite: false,\n            });\n        };\n    }, [updateRoomPermissions]);\n\n    return roomPermissions;\n};\n\nconst useIsSynapseAdmin = (cli?: MatrixClient): boolean => {\n    return useAsyncMemo(async () => (cli ? cli.isSynapseAdministrator().catch(() => false) : false), [cli], false);\n};\n\nexport const useRoomPowerLevels = (cli: MatrixClient, room: Room): IPowerLevelsContent => {\n    const [powerLevels, setPowerLevels] = useState<IPowerLevelsContent>(getPowerLevels(room));\n\n    const update = useCallback(\n        (ev?: MatrixEvent) => {\n            if (!room) return;\n            if (ev && ev.getType() !== EventType.RoomPowerLevels) return;\n            setPowerLevels(getPowerLevels(room));\n        },\n        [room],\n    );\n\n    useTypedEventEmitter(cli, RoomStateEvent.Events, update);\n    useEffect(() => {\n        update();\n        return () => {\n            setPowerLevels({});\n        };\n    }, [update]);\n    return powerLevels;\n};\n\nexport const useUserInfoBasicViewModel = (room: Room, member: User | RoomMember): UserInfoBasicState => {\n    const cli = useMatrixClientContext();\n\n    const powerLevels = useRoomPowerLevels(cli, room);\n    // Load whether or not we are a Synapse Admin\n    const isSynapseAdmin = useIsSynapseAdmin(cli);\n\n    // Count of how many operations are currently in progress, if > 0 then show a Spinner\n    const [pendingUpdateCount, setPendingUpdateCount] = useState(0);\n\n    const roomPermissions = useRoomPermissions(cli, room, member as RoomMember);\n\n    // selected member is current user\n    const isMe = member.userId === cli.getUserId();\n\n    // is needed to hide the Roles section for DMs as it doesn't make sense there\n    const isRoomDMForMember = !!DMRoomMap.shared().getUserIdForRoomId((member as RoomMember).roomId);\n\n    // used to check if user can deactivate another member\n    const isMemberSameDomain = member.userId.endsWith(`:${cli.getDomain()}`);\n\n    // We don't need a perfect check here, just something to pass as \"probably not our homeserver\". If\n    // someone does figure out how to bypass this check the worst that happens is an error.\n    const showDeactivateButton = isSynapseAdmin && isMemberSameDomain;\n\n    const startUpdating = useCallback(() => {\n        setPendingUpdateCount(pendingUpdateCount + 1);\n    }, [pendingUpdateCount]);\n\n    const stopUpdating = useCallback(() => {\n        setPendingUpdateCount(pendingUpdateCount - 1);\n    }, [pendingUpdateCount]);\n\n    const onSynapseDeactivate = useCallback(async () => {\n        const { finished } = Modal.createDialog(QuestionDialog, {\n            title: _t(\"user_info|deactivate_confirm_title\"),\n            description: <div>{_t(\"user_info|deactivate_confirm_description\")}</div>,\n            button: _t(\"user_info|deactivate_confirm_action\"),\n            danger: true,\n        });\n\n        const [accepted] = await finished;\n        if (!accepted) return;\n        try {\n            await cli.deactivateSynapseUser(member.userId);\n        } catch (err) {\n            logger.error(\"Failed to deactivate user\");\n            logger.error(err);\n\n            const description = err instanceof Error ? err.message : _t(\"invite|failed_generic\");\n\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"user_info|error_deactivate\"),\n                description,\n            });\n        }\n    }, [cli, member.userId]);\n\n    return {\n        showDeactivateButton,\n        powerLevels,\n        roomPermissions,\n        pendingUpdateCount,\n        isMe,\n        isRoomDMForMember,\n        onSynapseDeactivate,\n        startUpdating,\n        stopUpdating,\n    };\n};\n","/*\nCopyright 2025 New Vector Ltd.\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useContext, useEffect, useState, useCallback } from \"react\";\nimport { logger } from \"@sentry/browser\";\nimport { type RoomMember, type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { _t } from \"../../../languageHandler\";\nimport Modal from \"../../../Modal\";\nimport ErrorDialog from \"../../views/dialogs/ErrorDialog\";\nimport QuestionDialog from \"../../views/dialogs/QuestionDialog\";\nimport { warnSelfDemote } from \"../../views/right_panel/UserInfo\";\n\n/**\n *\n */\nexport interface UserInfoPowerLevelState {\n    /**\n     * default power level value of the selected user\n     */\n    powerLevelUsersDefault: number;\n    /**\n     * The new power level to apply\n     */\n    selectedPowerLevel: number;\n    /**\n     * Method to call When power level selection change\n     */\n    onPowerChange: (powerLevel: number) => void;\n}\n\nexport const useUserInfoPowerlevelViewModel = (user: RoomMember, room: Room): UserInfoPowerLevelState => {\n    const [selectedPowerLevel, setSelectedPowerLevel] = useState(user.powerLevel);\n\n    useEffect(() => {\n        setSelectedPowerLevel(user.powerLevel);\n    }, [user]);\n\n    const cli = useContext(MatrixClientContext);\n    const onPowerChange = useCallback(\n        async (powerLevel: number) => {\n            setSelectedPowerLevel(powerLevel);\n\n            const applyPowerChange = (roomId: string, target: string, powerLevel: number): Promise<unknown> => {\n                return cli.setPowerLevel(roomId, target, powerLevel).then(\n                    function () {\n                        logger.info(\"Power change success\");\n                    },\n                    function (err) {\n                        logger.error(\"Failed to change power level \" + err);\n                        Modal.createDialog(ErrorDialog, {\n                            title: _t(\"common|error\"),\n                            description: _t(\"error|update_power_level\"),\n                        });\n                    },\n                );\n            };\n\n            const roomId = user.roomId;\n            const target = user.userId;\n\n            const powerLevelEvent = room.currentState.getStateEvents(\"m.room.power_levels\", \"\");\n            if (!powerLevelEvent) return;\n\n            const myUserId = cli.getUserId();\n            const myPower = powerLevelEvent.getContent().users[myUserId || \"\"];\n            if (myPower && parseInt(myPower) <= powerLevel && myUserId !== target) {\n                const { finished } = Modal.createDialog(QuestionDialog, {\n                    title: _t(\"common|warning\"),\n                    description: (\n                        <div>\n                            {_t(\"user_info|promote_warning\")}\n                            <br />\n                            {_t(\"common|are_you_sure\")}\n                        </div>\n                    ),\n                    button: _t(\"action|continue\"),\n                });\n\n                const [confirmed] = await finished;\n                if (!confirmed) return;\n            } else if (myUserId === target && myPower && parseInt(myPower) > powerLevel) {\n                // If we are changing our own PL it can only ever be decreasing, which we cannot reverse.\n                try {\n                    if (!(await warnSelfDemote(room?.isSpaceRoom()))) return;\n                } catch (e) {\n                    logger.error(\"Failed to warn about self demotion: \" + e);\n                }\n            }\n\n            await applyPowerChange(roomId, target, powerLevel);\n        },\n        [user.roomId, user.userId, cli, room],\n    );\n\n    const powerLevelEvent = room.currentState.getStateEvents(\"m.room.power_levels\", \"\");\n    const powerLevelUsersDefault = powerLevelEvent ? powerLevelEvent.getContent().users_default : 0;\n\n    return {\n        powerLevelUsersDefault,\n        onPowerChange,\n        selectedPowerLevel,\n    };\n};\n","/*\nCopyright 2025 New Vector Ltd.\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type RoomMember, type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { textualPowerLevel } from \"../../../../Roles\";\nimport PowerSelector from \"../../elements/PowerSelector\";\nimport { type IRoomPermissions } from \"../UserInfo\";\nimport {\n    type UserInfoPowerLevelState,\n    useUserInfoPowerlevelViewModel,\n} from \"../../../viewmodels/right_panel/UserInfoPowerlevelViewModel\";\n\nexport const PowerLevelSection: React.FC<{\n    user: RoomMember;\n    room: Room;\n    roomPermissions: IRoomPermissions;\n}> = ({ user, room, roomPermissions }) => {\n    const vm = useUserInfoPowerlevelViewModel(user, room);\n\n    if (roomPermissions.canEdit) {\n        return <PowerLevelEditor vm={vm} roomPermissions={roomPermissions} />;\n    }\n\n    const powerLevel = user.powerLevel;\n    const role = textualPowerLevel(powerLevel, vm.powerLevelUsersDefault);\n    return (\n        <div className=\"mx_UserInfo_profileField\">\n            <div className=\"mx_UserInfo_roleDescription\">{role}</div>\n        </div>\n    );\n};\n\nexport const PowerLevelEditor: React.FC<{\n    vm: UserInfoPowerLevelState;\n    roomPermissions: IRoomPermissions;\n}> = ({ vm, roomPermissions }) => {\n    return (\n        <div className=\"mx_UserInfo_profileField\">\n            <PowerSelector\n                label={undefined}\n                value={vm.selectedPowerLevel}\n                maxValue={roomPermissions.modifyLevelMax}\n                usersDefault={vm.powerLevelUsersDefault}\n                onChange={vm.onPowerChange}\n            />\n        </div>\n    );\n};\n","/*\nCopyright 2025 New Vector Ltd.\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useContext, useEffect, useState, useCallback } from \"react\";\nimport { type RoomMember, User, ClientEvent, type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport MatrixClientContext from \"../../../../contexts/MatrixClientContext\";\nimport { _t } from \"../../../../languageHandler\";\nimport Modal from \"../../../../Modal\";\nimport QuestionDialog from \"../../../views/dialogs/QuestionDialog\";\nimport { useTypedEventEmitter } from \"../../../../hooks/useEventEmitter\";\n\nexport interface UserInfoPowerLevelState {\n    /**\n     * Weither the member is ignored by current user or not\n     */\n    isIgnored: boolean;\n    /**\n     * Trigger the method to ignore or unignore a user\n     * @param ev - The click event\n     */\n    ignoreButtonClick: (ev: Event) => void;\n}\n\nexport const useUserInfoIgnoreButtonViewModel = (member: User | RoomMember): UserInfoPowerLevelState => {\n    const cli = useContext(MatrixClientContext);\n\n    const unignore = useCallback(() => {\n        const ignoredUsers = cli.getIgnoredUsers();\n        const index = ignoredUsers.indexOf(member.userId);\n        if (index !== -1) ignoredUsers.splice(index, 1);\n        cli.setIgnoredUsers(ignoredUsers);\n    }, [cli, member]);\n\n    const ignore = useCallback(async () => {\n        const name = (member instanceof User ? member.displayName : member.name) || member.userId;\n        const { finished } = Modal.createDialog(QuestionDialog, {\n            title: _t(\"user_info|ignore_confirm_title\", { user: name }),\n            description: <div>{_t(\"user_info|ignore_confirm_description\")}</div>,\n            button: _t(\"action|ignore\"),\n        });\n        const [confirmed] = await finished;\n\n        if (confirmed) {\n            const ignoredUsers = cli.getIgnoredUsers();\n            ignoredUsers.push(member.userId);\n            cli.setIgnoredUsers(ignoredUsers);\n        }\n    }, [cli, member]);\n\n    // Check whether the user is ignored\n    const [isIgnored, setIsIgnored] = useState(cli.isUserIgnored(member.userId));\n    // Recheck if the user or client changes\n    useEffect(() => {\n        setIsIgnored(cli.isUserIgnored(member.userId));\n    }, [cli, member.userId]);\n\n    // Recheck also if we receive new accountData m.ignored_user_list\n    const accountDataHandler = useCallback(\n        (ev: MatrixEvent) => {\n            if (ev.getType() === \"m.ignored_user_list\") {\n                setIsIgnored(cli.isUserIgnored(member.userId));\n            }\n        },\n        [cli, member.userId],\n    );\n    useTypedEventEmitter(cli, ClientEvent.AccountData, accountDataHandler);\n\n    const ignoreButtonClick = (ev: Event): void => {\n        ev.preventDefault();\n        if (isIgnored) {\n            unignore();\n        } else {\n            ignore();\n        }\n    };\n\n    return {\n        ignoreButtonClick,\n        isIgnored,\n    };\n};\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type RoomMember, type User } from \"matrix-js-sdk/src/matrix\";\nimport React from \"react\";\nimport { MenuItem } from \"@vector-im/compound-web\";\nimport { BlockIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport { useUserInfoIgnoreButtonViewModel } from \"../../../viewmodels/right_panel/user_info/UserInfoIgnoreButtonViewModel\";\n\nexport const IgnoreToggleButton: React.FC<{\n    member: User | RoomMember;\n}> = ({ member }) => {\n    const vm = useUserInfoIgnoreButtonViewModel(member);\n\n    return (\n        <MenuItem\n            role=\"button\"\n            onSelect={async (ev) => vm.ignoreButtonClick(ev)}\n            label={vm.isIgnored ? _t(\"user_info|unignore_button\") : _t(\"user_info|ignore_button\")}\n            kind=\"critical\"\n            Icon={BlockIcon}\n        />\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ComponentProps, useMemo, useState } from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { InfoSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport ConfirmUserActionDialog from \"./ConfirmUserActionDialog\";\nimport SpaceStore from \"../../../stores/spaces/SpaceStore\";\nimport SpaceChildrenPicker from \"../spaces/SpaceChildrenPicker\";\n\ntype BaseProps = ComponentProps<typeof ConfirmUserActionDialog>;\ninterface IProps extends Omit<BaseProps, \"matrixClient\" | \"children\" | \"onFinished\"> {\n    space: Room;\n    allLabel: string;\n    specificLabel: string;\n    noneLabel?: string;\n    warningMessage?: string;\n    onFinished(success?: boolean, reason?: string, rooms?: Room[]): void;\n    spaceChildFilter?(child: Room): boolean;\n}\n\nconst ConfirmSpaceUserActionDialog: React.FC<IProps> = ({\n    space,\n    spaceChildFilter,\n    allLabel,\n    specificLabel,\n    noneLabel,\n    warningMessage,\n    onFinished,\n    ...props\n}) => {\n    const spaceChildren = useMemo(() => {\n        const children = SpaceStore.instance.getChildren(space.roomId);\n        if (spaceChildFilter) {\n            return children.filter(spaceChildFilter);\n        }\n        return children;\n    }, [space.roomId, spaceChildFilter]);\n\n    const [roomsToLeave, setRoomsToLeave] = useState<Room[]>([]);\n    const selectedRooms = useMemo(() => new Set(roomsToLeave), [roomsToLeave]);\n\n    let warning: JSX.Element | undefined;\n    if (warningMessage) {\n        warning = (\n            <div className=\"mx_ConfirmSpaceUserActionDialog_warning\">\n                <InfoSolidIcon />\n                {warningMessage}\n            </div>\n        );\n    }\n\n    return (\n        <ConfirmUserActionDialog\n            {...props}\n            onFinished={(success?: boolean, reason?: string) => {\n                onFinished(success, reason, roomsToLeave);\n            }}\n            className=\"mx_ConfirmSpaceUserActionDialog\"\n            roomId={space.roomId}\n        >\n            {warning}\n            <SpaceChildrenPicker\n                space={space}\n                spaceChildren={spaceChildren}\n                selected={selectedRooms}\n                allLabel={allLabel}\n                specificLabel={specificLabel}\n                noneLabel={noneLabel}\n                onChange={setRoomsToLeave}\n            />\n        </ConfirmUserActionDialog>\n    );\n};\n\nexport default ConfirmSpaceUserActionDialog;\n","/*\nCopyright 2025 New Vector Ltd.\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"@sentry/browser\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport { useMatrixClientContext } from \"../../../../../contexts/MatrixClientContext\";\nimport { _t } from \"../../../../../languageHandler\";\nimport Modal from \"../../../../../Modal\";\nimport { bulkSpaceBehaviour } from \"../../../../../utils/space\";\nimport ConfirmSpaceUserActionDialog from \"../../../../views/dialogs/ConfirmSpaceUserActionDialog\";\nimport ConfirmUserActionDialog from \"../../../../views/dialogs/ConfirmUserActionDialog\";\nimport ErrorDialog from \"../../../../views/dialogs/ErrorDialog\";\nimport { type RoomAdminToolsProps } from \"./UserInfoAdminToolsContainerViewModel\";\n\nexport interface BanButtonState {\n    /**\n     * The function to call when the button is clicked\n     */\n    onBanOrUnbanClick: () => Promise<void>;\n    /**\n     * The label of the ban button can be ban or unban\n     */\n    banLabel: string;\n}\n/**\n * The view model for the room ban button used in the UserInfoAdminToolsContainer\n * @param {RoomAdminToolsProps} props - the object containing the necceray props for banButton the view model\n * @param {Room} props.room - the room to ban/unban the user in\n * @param {RoomMember} props.member - the member to ban/unban\n * @param {boolean} props.isUpdating - whether the operation is currently in progress\n * @param {function} props.startUpdating - callback function to start the operation\n * @param {function} props.stopUpdating - callback function to stop the operation\n * @returns {BanButtonState} the room ban/unban button state\n */\nexport const useBanButtonViewModel = (props: RoomAdminToolsProps): BanButtonState => {\n    const { isUpdating, startUpdating, stopUpdating, room, member } = props;\n\n    const cli = useMatrixClientContext();\n\n    const isBanned = member.membership === KnownMembership.Ban;\n\n    let banLabel = room.isSpaceRoom() ? _t(\"user_info|ban_button_space\") : _t(\"user_info|ban_button_room\");\n    if (isBanned) {\n        banLabel = room.isSpaceRoom() ? _t(\"user_info|unban_button_space\") : _t(\"user_info|unban_button_room\");\n    }\n\n    const onBanOrUnbanClick = async (): Promise<void> => {\n        if (isUpdating) return; // only allow one operation at a time\n        startUpdating();\n\n        const commonProps = {\n            member,\n            action: room.isSpaceRoom()\n                ? isBanned\n                    ? _t(\"user_info|unban_button_space\")\n                    : _t(\"user_info|ban_button_space\")\n                : isBanned\n                  ? _t(\"user_info|unban_button_room\")\n                  : _t(\"user_info|ban_button_room\"),\n            title: isBanned\n                ? _t(\"user_info|unban_room_confirm_title\", { roomName: room.name })\n                : _t(\"user_info|ban_room_confirm_title\", { roomName: room.name }),\n            askReason: !isBanned,\n            danger: !isBanned,\n        };\n\n        let finished: Promise<[success?: boolean, reason?: string, rooms?: Room[]]>;\n\n        if (room.isSpaceRoom()) {\n            ({ finished } = Modal.createDialog(\n                ConfirmSpaceUserActionDialog,\n                {\n                    ...commonProps,\n                    space: room,\n                    spaceChildFilter: isBanned\n                        ? (child: Room) => {\n                              // Return true if the target member is banned and we have sufficient PL to unban\n                              const myMember = child.getMember(cli.credentials.userId || \"\");\n                              const theirMember = child.getMember(member.userId);\n                              return (\n                                  !!myMember &&\n                                  !!theirMember &&\n                                  theirMember.membership === KnownMembership.Ban &&\n                                  myMember.powerLevel > theirMember.powerLevel &&\n                                  child.currentState.hasSufficientPowerLevelFor(\"ban\", myMember.powerLevel)\n                              );\n                          }\n                        : (child: Room) => {\n                              // Return true if the target member isn't banned and we have sufficient PL to ban\n                              const myMember = child.getMember(cli.credentials.userId || \"\");\n                              const theirMember = child.getMember(member.userId);\n                              return (\n                                  !!myMember &&\n                                  !!theirMember &&\n                                  theirMember.membership !== KnownMembership.Ban &&\n                                  myMember.powerLevel > theirMember.powerLevel &&\n                                  child.currentState.hasSufficientPowerLevelFor(\"ban\", myMember.powerLevel)\n                              );\n                          },\n                    allLabel: isBanned ? _t(\"user_info|unban_space_everything\") : _t(\"user_info|ban_space_everything\"),\n                    specificLabel: isBanned ? _t(\"user_info|unban_space_specific\") : _t(\"user_info|ban_space_specific\"),\n                    warningMessage: isBanned ? _t(\"user_info|unban_space_warning\") : _t(\"user_info|kick_space_warning\"),\n                },\n                \"mx_ConfirmSpaceUserActionDialog_wrapper\",\n            ));\n        } else {\n            ({ finished } = Modal.createDialog(ConfirmUserActionDialog, commonProps));\n        }\n\n        const [proceed, reason, rooms = []] = await finished;\n        if (!proceed) {\n            stopUpdating();\n            return;\n        }\n\n        const fn = (roomId: string): Promise<unknown> => {\n            if (isBanned) {\n                return cli.unban(roomId, member.userId);\n            } else {\n                return cli.ban(roomId, member.userId, reason || undefined);\n            }\n        };\n\n        bulkSpaceBehaviour(room, rooms, (room) => fn(room.roomId))\n            .then(\n                () => {\n                    // NO-OP; rely on the m.room.member event coming down else we could\n                    // get out of sync if we force setState here!\n                    logger.info(\"Ban success\");\n                },\n                function (err) {\n                    logger.error(\"Ban error: \" + err);\n                    Modal.createDialog(ErrorDialog, {\n                        title: _t(\"common|error\"),\n                        description: _t(\"user_info|error_ban_user\"),\n                    });\n                },\n            )\n            .finally(() => {\n                stopUpdating();\n            });\n    };\n\n    return {\n        onBanOrUnbanClick,\n        banLabel,\n    };\n};\n","/*\nCopyright 2024,2025 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useState } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport {\n    type MatrixClient,\n    type RoomMember,\n    type Room,\n    type MatrixEvent,\n    EventTimeline,\n    EventType,\n} from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../languageHandler\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport BaseDialog from \"../dialogs/BaseDialog\";\nimport InfoDialog from \"../dialogs/InfoDialog\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport StyledCheckbox from \"../elements/StyledCheckbox\";\n\ninterface Props {\n    matrixClient: MatrixClient;\n    room: Room;\n    member: RoomMember;\n    onFinished(redact?: boolean): void;\n}\n\nconst BulkRedactDialog: React.FC<Props> = (props) => {\n    const { matrixClient: cli, room, member, onFinished } = props;\n    const [keepStateEvents, setKeepStateEvents] = useState(true);\n\n    let timeline: EventTimeline | null = room.getLiveTimeline();\n    let eventsToRedact: MatrixEvent[] = [];\n    while (timeline) {\n        eventsToRedact = [\n            ...eventsToRedact,\n            ...timeline.getEvents().filter(\n                (event) =>\n                    event.getSender() === member.userId &&\n                    !event.isRedacted() &&\n                    !event.isRedaction() &&\n                    event.getType() !== EventType.RoomCreate &&\n                    // Don't redact ACLs because that'll obliterate the room\n                    // See https://github.com/matrix-org/synapse/issues/4042 for details.\n                    event.getType() !== EventType.RoomServerAcl &&\n                    // Redacting encryption events is equally bad\n                    event.getType() !== EventType.RoomEncryption,\n            ),\n        ];\n        timeline = timeline.getNeighbouringTimeline(EventTimeline.BACKWARDS);\n    }\n\n    if (eventsToRedact.length === 0) {\n        return (\n            <InfoDialog\n                onFinished={onFinished}\n                title={_t(\"user_info|redact|no_recent_messages_title\", { user: member.name })}\n                description={\n                    <div>\n                        <p>{_t(\"user_info|redact|no_recent_messages_description\")}</p>\n                    </div>\n                }\n            />\n        );\n    } else {\n        eventsToRedact = eventsToRedact.filter((event) => !(keepStateEvents && event.isState()));\n        const count = eventsToRedact.length;\n        const user = member.name;\n\n        const redact = async (): Promise<void> => {\n            logger.info(`Started redacting recent ${count} messages for ${member.userId} in ${room.roomId}`);\n            dis.dispatch({\n                action: Action.BulkRedactStart,\n                room_id: room.roomId,\n            });\n\n            // Submitting a large number of redactions freezes the UI,\n            // so first yield to allow to rerender after closing the dialog.\n            await Promise.resolve();\n            await Promise.all(\n                eventsToRedact.reverse().map(async (event): Promise<void> => {\n                    try {\n                        await cli.redactEvent(room.roomId, event.getId()!);\n                    } catch (err) {\n                        // log and swallow errors\n                        logger.error(\"Could not redact\", event.getId());\n                        logger.error(err);\n                    }\n                }),\n            );\n\n            logger.info(`Finished redacting recent ${count} messages for ${member.userId} in ${room.roomId}`);\n            dis.dispatch({\n                action: Action.BulkRedactEnd,\n                room_id: room.roomId,\n            });\n        };\n\n        return (\n            <BaseDialog\n                className=\"mx_BulkRedactDialog\"\n                onFinished={onFinished}\n                title={_t(\"user_info|redact|confirm_title\", { user })}\n                contentId=\"mx_Dialog_content\"\n            >\n                <div className=\"mx_Dialog_content\" id=\"mx_Dialog_content\">\n                    <p>{_t(\"user_info|redact|confirm_description_1\", { count, user })}</p>\n                    <p>{_t(\"user_info|redact|confirm_description_2\")}</p>\n                    <StyledCheckbox\n                        description={_t(\"user_info|redact|confirm_keep_state_explainer\")}\n                        checked={keepStateEvents}\n                        onChange={(e) => setKeepStateEvents(e.target.checked)}\n                    >\n                        {_t(\"user_info|redact|confirm_keep_state_label\")}\n                    </StyledCheckbox>\n                </div>\n                <DialogButtons\n                    primaryButton={_t(\"user_info|redact|confirm_button\", { count })}\n                    primaryButtonClass=\"danger\"\n                    primaryDisabled={count === 0}\n                    onPrimaryButtonClick={() => {\n                        setTimeout(redact, 0);\n                        onFinished(true);\n                    }}\n                    onCancel={() => onFinished(false)}\n                />\n            </BaseDialog>\n        );\n    }\n};\n\nexport default BulkRedactDialog;\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode } from \"react\";\nimport classNames from \"classnames\";\nimport { type RoomMember, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { MenuItem } from \"@vector-im/compound-web\";\nimport CloseIcon from \"@vector-im/compound-design-tokens/assets/web/icons/close\";\nimport ChatProblemIcon from \"@vector-im/compound-design-tokens/assets/web/icons/chat-problem\";\nimport VisibilityOffIcon from \"@vector-im/compound-design-tokens/assets/web/icons/visibility-off\";\nimport LeaveIcon from \"@vector-im/compound-design-tokens/assets/web/icons/leave\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport { type IPowerLevelsContent } from \"../UserInfo\";\nimport { useUserInfoAdminToolsContainerViewModel } from \"../../../viewmodels/right_panel/user_info/admin/UserInfoAdminToolsContainerViewModel\";\nimport { useMuteButtonViewModel } from \"../../../viewmodels/right_panel/user_info/admin/UserInfoMuteButtonViewModel\";\nimport { useBanButtonViewModel } from \"../../../viewmodels/right_panel/user_info/admin/UserInfoBanButtonViewModel\";\nimport { useRoomKickButtonViewModel } from \"../../../viewmodels/right_panel/user_info/admin/UserInfoKickButtonViewModel\";\nimport { useRedactMessagesButtonViewModel } from \"../../../viewmodels/right_panel/user_info/admin/UserInfoRedactButtonViewModel\";\n\nconst Container: React.FC<{\n    children: ReactNode;\n    className?: string;\n}> = ({ children, className }) => {\n    const classes = classNames(\"mx_UserInfo_container\", className);\n    return <div className={classes}>{children}</div>;\n};\n\ninterface IBaseProps {\n    member: RoomMember;\n    isUpdating: boolean;\n    startUpdating(): void;\n    stopUpdating(): void;\n}\n\nexport const RoomKickButton = ({\n    room,\n    member,\n    isUpdating,\n    startUpdating,\n    stopUpdating,\n}: Omit<IBaseRoomProps, \"powerLevels\">): JSX.Element | null => {\n    const vm = useRoomKickButtonViewModel({ room, member, isUpdating, startUpdating, stopUpdating });\n    // check if user can be kicked/disinvited\n    if (!vm.canUserBeKicked) return <></>;\n\n    return (\n        <MenuItem\n            role=\"button\"\n            onSelect={async (ev) => {\n                ev.preventDefault();\n                vm.onKickClick();\n            }}\n            disabled={isUpdating}\n            label={vm.kickLabel}\n            kind=\"critical\"\n            Icon={LeaveIcon}\n        />\n    );\n};\n\nconst RedactMessagesButton: React.FC<IBaseProps> = ({ member }) => {\n    const vm = useRedactMessagesButtonViewModel(member);\n\n    return (\n        <MenuItem\n            role=\"button\"\n            onSelect={async (ev) => {\n                ev.preventDefault();\n                vm.onRedactAllMessagesClick();\n            }}\n            label={_t(\"user_info|redact_button\")}\n            kind=\"critical\"\n            Icon={CloseIcon}\n        />\n    );\n};\n\nexport const BanToggleButton = ({\n    room,\n    member,\n    isUpdating,\n    startUpdating,\n    stopUpdating,\n}: Omit<IBaseRoomProps, \"powerLevels\">): JSX.Element => {\n    const vm = useBanButtonViewModel({ room, member, isUpdating, startUpdating, stopUpdating });\n\n    return (\n        <MenuItem\n            role=\"button\"\n            onSelect={async (ev) => {\n                ev.preventDefault();\n                vm.onBanOrUnbanClick();\n            }}\n            disabled={isUpdating}\n            label={vm.banLabel}\n            kind=\"critical\"\n            Icon={ChatProblemIcon}\n        />\n    );\n};\n\ninterface IBaseRoomProps extends IBaseProps {\n    room: Room;\n    powerLevels: IPowerLevelsContent;\n    children?: ReactNode;\n}\n\n// We do not show a Mute button for ourselves so it doesn't need to handle warning self demotion\nconst MuteToggleButton: React.FC<IBaseRoomProps> = ({\n    member,\n    room,\n    powerLevels,\n    isUpdating,\n    startUpdating,\n    stopUpdating,\n}) => {\n    const vm = useMuteButtonViewModel({ room, member, isUpdating, startUpdating, stopUpdating });\n    // Don't show the mute/unmute option if the user is not in the room\n    if (!vm.isMemberInTheRoom) return null;\n\n    return (\n        <MenuItem\n            role=\"button\"\n            onSelect={async (ev) => {\n                ev.preventDefault();\n                vm.onMuteButtonClick();\n            }}\n            disabled={isUpdating}\n            label={vm.muteLabel}\n            kind=\"critical\"\n            Icon={VisibilityOffIcon}\n        />\n    );\n};\n\nexport const UserInfoAdminToolsContainer: React.FC<IBaseRoomProps> = ({\n    room,\n    children,\n    member,\n    isUpdating,\n    startUpdating,\n    stopUpdating,\n    powerLevels,\n}) => {\n    let kickButton;\n    let banButton;\n    let muteButton;\n    let redactButton;\n\n    const vm = useUserInfoAdminToolsContainerViewModel({ room, member, powerLevels });\n\n    if (!vm.isCurrentUserInTheRoom) {\n        // we aren't in the room, so return no admin tooling\n        return <div />;\n    }\n\n    if (vm.shouldShowKickButton) {\n        kickButton = (\n            <RoomKickButton\n                room={room}\n                member={member}\n                isUpdating={isUpdating}\n                startUpdating={startUpdating}\n                stopUpdating={stopUpdating}\n            />\n        );\n    }\n    if (vm.shouldShowRedactButton) {\n        redactButton = (\n            <RedactMessagesButton\n                member={member}\n                isUpdating={isUpdating}\n                startUpdating={startUpdating}\n                stopUpdating={stopUpdating}\n            />\n        );\n    }\n    if (vm.shouldShowBanButton) {\n        banButton = (\n            <BanToggleButton\n                room={room}\n                member={member}\n                isUpdating={isUpdating}\n                startUpdating={startUpdating}\n                stopUpdating={stopUpdating}\n            />\n        );\n    }\n    if (vm.shouldShowMuteButton) {\n        muteButton = (\n            <MuteToggleButton\n                member={member}\n                room={room}\n                powerLevels={powerLevels}\n                isUpdating={isUpdating}\n                startUpdating={startUpdating}\n                stopUpdating={stopUpdating}\n            />\n        );\n    }\n\n    if (kickButton || banButton || muteButton || redactButton || children) {\n        return (\n            <Container>\n                {muteButton}\n                {redactButton}\n                {kickButton}\n                {banButton}\n                {children}\n            </Container>\n        );\n    }\n\n    return <div />;\n};\n","/*\nCopyright 2025 New Vector Ltd.\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"@sentry/browser\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport { useMatrixClientContext } from \"../../../../../contexts/MatrixClientContext\";\nimport { _t } from \"../../../../../languageHandler\";\nimport Modal from \"../../../../../Modal\";\nimport { bulkSpaceBehaviour } from \"../../../../../utils/space\";\nimport ConfirmSpaceUserActionDialog from \"../../../../views/dialogs/ConfirmSpaceUserActionDialog\";\nimport ConfirmUserActionDialog from \"../../../../views/dialogs/ConfirmUserActionDialog\";\nimport ErrorDialog from \"../../../../views/dialogs/ErrorDialog\";\nimport { type RoomAdminToolsProps } from \"./UserInfoAdminToolsContainerViewModel\";\n\ninterface RoomKickButtonState {\n    /**\n     * The function to call when the button is clicked\n     */\n    onKickClick: () => Promise<void>;\n    /**\n     * Whether the user can be kicked based on membership value. If the user already join or was invited, it can be kicked\n     */\n    canUserBeKicked: boolean;\n    /**\n     * The label of the kick button can be kick or disinvite\n     */\n    kickLabel: string;\n}\n\n/**\n * The view model for the room kick button used in the UserInfoAdminToolsContainer\n * @param {RoomAdminToolsProps} props - the object containing the necceray props for kickButton the view model\n * @param {Room} props.room - the room to kick/disinvite the user from\n * @param {RoomMember} props.member - the member to kick/disinvite\n * @param {boolean} props.isUpdating - whether the operation is currently in progress\n * @param {function} props.startUpdating - callback function to start the operation\n * @param {function} props.stopUpdating - callback function to stop the operation\n * @returns {KickButtonState} the room kick/disinvite button state\n */\nexport function useRoomKickButtonViewModel(props: RoomAdminToolsProps): RoomKickButtonState {\n    const { isUpdating, startUpdating, stopUpdating, room, member } = props;\n\n    const cli = useMatrixClientContext();\n\n    const onKickClick = async (): Promise<void> => {\n        if (isUpdating) return; // only allow one operation at a time\n        startUpdating();\n\n        const commonProps = {\n            member,\n            action: room.isSpaceRoom()\n                ? member.membership === KnownMembership.Invite\n                    ? _t(\"user_info|disinvite_button_space\")\n                    : _t(\"user_info|kick_button_space\")\n                : member.membership === KnownMembership.Invite\n                  ? _t(\"user_info|disinvite_button_room\")\n                  : _t(\"user_info|kick_button_room\"),\n            title:\n                member.membership === KnownMembership.Invite\n                    ? _t(\"user_info|disinvite_button_room_name\", { roomName: room.name })\n                    : _t(\"user_info|kick_button_room_name\", { roomName: room.name }),\n            askReason: member.membership === KnownMembership.Join,\n            danger: true,\n        };\n\n        let finished: Promise<[success?: boolean, reason?: string, rooms?: Room[]]>;\n\n        if (room.isSpaceRoom()) {\n            ({ finished } = Modal.createDialog(\n                ConfirmSpaceUserActionDialog,\n                {\n                    ...commonProps,\n                    space: room,\n                    spaceChildFilter: (child: Room) => {\n                        // Return true if the target member is not banned and we have sufficient PL to ban them\n                        const myMember = child.getMember(cli.credentials.userId || \"\");\n                        const theirMember = child.getMember(member.userId);\n                        return (\n                            !!myMember &&\n                            !!theirMember &&\n                            theirMember.membership === member.membership &&\n                            myMember.powerLevel > theirMember.powerLevel &&\n                            child.currentState.hasSufficientPowerLevelFor(\"kick\", myMember.powerLevel)\n                        );\n                    },\n                    allLabel: _t(\"user_info|kick_button_space_everything\"),\n                    specificLabel: _t(\"user_info|kick_space_specific\"),\n                    warningMessage: _t(\"user_info|kick_space_warning\"),\n                },\n                \"mx_ConfirmSpaceUserActionDialog_wrapper\",\n            ));\n        } else {\n            ({ finished } = Modal.createDialog(ConfirmUserActionDialog, commonProps));\n        }\n\n        const [proceed, reason, rooms = []] = await finished;\n        if (!proceed) {\n            stopUpdating();\n            return;\n        }\n\n        bulkSpaceBehaviour(room, rooms, (room) => cli.kick(room.roomId, member.userId, reason || undefined))\n            .then(\n                () => {\n                    // NO-OP; rely on the m.room.member event coming down else we could\n                    // get out of sync if we force setState here!\n                    logger.info(\"Kick success\");\n                },\n                function (err) {\n                    logger.error(\"Kick error: \" + err);\n                    Modal.createDialog(ErrorDialog, {\n                        title: _t(\"user_info|error_kicking_user\"),\n                        description: err?.message ?? \"Operation failed\",\n                    });\n                },\n            )\n            .finally(() => {\n                stopUpdating();\n            });\n    };\n\n    const canUserBeKicked = member.membership === KnownMembership.Invite || member.membership === KnownMembership.Join;\n\n    const kickLabel = room.isSpaceRoom()\n        ? member.membership === KnownMembership.Invite\n            ? _t(\"user_info|disinvite_button_space\")\n            : _t(\"user_info|kick_button_space\")\n        : member.membership === KnownMembership.Invite\n          ? _t(\"user_info|disinvite_button_room\")\n          : _t(\"user_info|kick_button_room\");\n\n    return {\n        onKickClick,\n        canUserBeKicked,\n        kickLabel,\n    };\n}\n","/*\nCopyright 2025 New Vector Ltd.\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type RoomMember } from \"matrix-js-sdk/src/matrix\";\n\nimport { useMatrixClientContext } from \"../../../../../contexts/MatrixClientContext\";\nimport Modal from \"../../../../../Modal\";\nimport BulkRedactDialog from \"../../../../views/dialogs/BulkRedactDialog\";\n\nexport interface RedactMessagesButtonState {\n    onRedactAllMessagesClick: () => void;\n}\n\n/**\n * The view model for the redact messages button used in the UserInfoAdminToolsContainer\n * @param {RoomMember} member - the selected member to redact messages for\n * @returns {RedactMessagesButtonState} the redact messages button state\n */\nexport const useRedactMessagesButtonViewModel = (member: RoomMember): RedactMessagesButtonState => {\n    const cli = useMatrixClientContext();\n\n    const onRedactAllMessagesClick = (): void => {\n        const room = cli.getRoom(member.roomId);\n        if (!room) return;\n\n        Modal.createDialog(BulkRedactDialog, {\n            matrixClient: cli,\n            room,\n            member,\n        });\n    };\n\n    return {\n        onRedactAllMessagesClick,\n    };\n};\n","/*\nCopyright 2025 New Vector Ltd.\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"@sentry/browser\";\nimport { type RoomMember, type IPowerLevelsContent } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport { useMatrixClientContext } from \"../../../../../contexts/MatrixClientContext\";\nimport { _t } from \"../../../../../languageHandler\";\nimport Modal from \"../../../../../Modal\";\nimport ErrorDialog from \"../../../../views/dialogs/ErrorDialog\";\nimport { type RoomAdminToolsProps } from \"./UserInfoAdminToolsContainerViewModel\";\n\ninterface MuteButtonState {\n    /**\n     * Whether the member is in the roomn based on the membership value\n     */\n    isMemberInTheRoom: boolean;\n    /**\n     * The label of the mute button can be mute or unmute\n     */\n    muteLabel: string;\n    /**\n     * The function to call when the mute button is clicked\n     */\n    onMuteButtonClick: () => Promise<void>;\n}\n\n/**\n * The view model for the room mute button used in the UserInfoAdminToolsContainer\n * @param {RoomAdminToolsProps} props - the object containing the necceray props for muteButton the view model\n * @param {Room} props.room - the room to mute/unmute the user in\n * @param {RoomMember} props.member - the member to mute/unmute\n * @param {boolean} props.isUpdating - whether the operation is currently in progress\n * @param {function} props.startUpdating - callback function to start the operation\n * @param {function} props.stopUpdating - callback function to stop the operation\n * @returns {MuteButtonState} the room mute/unmute button state\n */\nexport const useMuteButtonViewModel = (props: RoomAdminToolsProps): MuteButtonState => {\n    const { isUpdating, startUpdating, stopUpdating, room, member } = props;\n\n    const cli = useMatrixClientContext();\n\n    const isMuted = (member: RoomMember, powerLevelContent: IPowerLevelsContent): boolean => {\n        if (!powerLevelContent || !member) return false;\n\n        const levelToSend =\n            (powerLevelContent.events ? powerLevelContent.events[\"m.room.message\"] : null) ||\n            powerLevelContent.events_default;\n\n        // levelToSend could be undefined as .events_default is optional. Coercing in this case using\n        // Number() would always return false, so this preserves behaviour\n        // FIXME: per the spec, if `events_default` is unset, it defaults to zero. If\n        //   the member has a negative powerlevel, this will give an incorrect result.\n        if (levelToSend === undefined) return false;\n\n        return member.powerLevel < levelToSend;\n    };\n\n    const muted = isMuted(member, room.currentState.getStateEvents(\"m.room.power_levels\", \"\")?.getContent() || {});\n    const muteLabel = muted ? _t(\"common|unmute\") : _t(\"common|mute\");\n\n    const isMemberInTheRoom = member.membership == KnownMembership.Join;\n\n    const onMuteButtonClick = async (): Promise<void> => {\n        if (isUpdating) return; // only allow one operation at a time\n        startUpdating();\n\n        const roomId = member.roomId;\n        const target = member.userId;\n\n        const powerLevelEvent = room.currentState.getStateEvents(\"m.room.power_levels\", \"\");\n        const powerLevels = powerLevelEvent?.getContent();\n        const levelToSend = powerLevels?.events?.[\"m.room.message\"] ?? powerLevels?.events_default;\n\n        let level;\n        if (muted) {\n            // unmute\n            level = levelToSend;\n        } else {\n            // mute\n            level = levelToSend - 1;\n        }\n        level = parseInt(level);\n\n        console.log(\"level\", level);\n        if (isNaN(level)) {\n            stopUpdating();\n            return;\n        }\n\n        cli.setPowerLevel(roomId, target, level)\n            .then(\n                () => {\n                    // NO-OP; rely on the m.room.member event coming down else we could\n                    // get out of sync if we force setState here!\n                    logger.info(\"Mute toggle success\");\n                },\n                function (err) {\n                    logger.error(\"Mute error: \" + err);\n                    Modal.createDialog(ErrorDialog, {\n                        title: _t(\"common|error\"),\n                        description: _t(\"user_info|error_mute_user\"),\n                    });\n                },\n            )\n            .finally(() => {\n                stopUpdating();\n            });\n    };\n\n    return {\n        isMemberInTheRoom,\n        onMuteButtonClick,\n        muteLabel,\n    };\n};\n","/*\nCopyright 2025 New Vector Ltd.\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room, type RoomMember, type IPowerLevelsContent } from \"matrix-js-sdk/src/matrix\";\n\nimport { useMatrixClientContext } from \"../../../../../contexts/MatrixClientContext\";\n\n/**\n * Interface used by admin tools container subcomponents props\n */\nexport interface RoomAdminToolsProps {\n    room: Room;\n    member: RoomMember;\n    isUpdating: boolean;\n    startUpdating: () => void;\n    stopUpdating: () => void;\n}\n\n/**\n * Interface used by admin tools container props\n */\nexport interface RoomAdminToolsContainerProps {\n    room: Room;\n    member: RoomMember;\n    powerLevels: IPowerLevelsContent;\n}\n\ninterface UserInfoAdminToolsContainerState {\n    shouldShowKickButton: boolean;\n    shouldShowBanButton: boolean;\n    shouldShowMuteButton: boolean;\n    shouldShowRedactButton: boolean;\n    isCurrentUserInTheRoom: boolean;\n}\n\n/**\n * The view model for the user info admin tools container\n * @param {RoomAdminToolsContainerProps} props - the object containing the necceray props for the view model\n * @param {Room} props.room - the room that display the admin tools\n * @param {RoomMember} props.member - the selected member\n * @param {IPowerLevelsContent} props.powerLevels - current room power levels\n * @returns {UserInfoAdminToolsContainerState} the user info admin tools container state\n */\nexport const useUserInfoAdminToolsContainerViewModel = (\n    props: RoomAdminToolsContainerProps,\n): UserInfoAdminToolsContainerState => {\n    const cli = useMatrixClientContext();\n    const { room, member, powerLevels } = props;\n\n    const editPowerLevel =\n        (powerLevels.events ? powerLevels.events[\"m.room.power_levels\"] : null) || powerLevels.state_default;\n\n    // if these do not exist in the event then they should default to 50 as per the spec\n    const { ban: banPowerLevel = 50, kick: kickPowerLevel = 50, redact: redactPowerLevel = 50 } = powerLevels;\n\n    const me = room.getMember(cli.getUserId() || \"\");\n    const isCurrentUserInTheRoom = me !== null;\n\n    if (!isCurrentUserInTheRoom) {\n        return {\n            shouldShowKickButton: false,\n            shouldShowBanButton: false,\n            shouldShowMuteButton: false,\n            shouldShowRedactButton: false,\n            isCurrentUserInTheRoom: false,\n        };\n    }\n\n    const isMe = me.userId === member.userId;\n    const canAffectUser = member.powerLevel < me.powerLevel || isMe;\n\n    return {\n        shouldShowKickButton: !isMe && canAffectUser && me.powerLevel >= kickPowerLevel,\n        shouldShowRedactButton: me.powerLevel >= redactPowerLevel && !room.isSpaceRoom(),\n        shouldShowBanButton: !isMe && canAffectUser && me.powerLevel >= banPowerLevel,\n        shouldShowMuteButton: !isMe && canAffectUser && me.powerLevel >= Number(editPowerLevel) && !room.isSpaceRoom(),\n        isCurrentUserInTheRoom,\n    };\n};\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type RoomMember, type User, type Room } from \"matrix-js-sdk/src/matrix\";\nimport React, { type JSX, type ReactNode, useState } from \"react\";\nimport { MenuItem } from \"@vector-im/compound-web\";\nimport { ChatIcon, CheckIcon, MentionIcon, ShareIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\nimport InviteIcon from \"@vector-im/compound-design-tokens/assets/web/icons/user-add\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport { useUserInfoBasicOptionsViewModel } from \"../../../viewmodels/right_panel/user_info/UserInfoBasicOptionsViewModel\";\nimport { Container, type Member } from \"../UserInfo\";\nimport { shouldShowComponent } from \"../../../../customisations/helpers/UIComponents\";\nimport { UIComponent } from \"../../../../settings/UIFeature\";\n\nconst MessageButton = ({\n    member,\n    openDMForUser,\n}: {\n    member: Member;\n    openDMForUser: (user: Member) => Promise<void>;\n}): JSX.Element => {\n    const [busy, setBusy] = useState(false);\n\n    return (\n        <MenuItem\n            role=\"button\"\n            onSelect={async (ev) => {\n                ev.preventDefault();\n                if (busy) return;\n                setBusy(true);\n                await openDMForUser(member);\n                setBusy(false);\n            }}\n            disabled={busy}\n            label={_t(\"user_info|send_message\")}\n            Icon={ChatIcon}\n        />\n    );\n};\n\nexport const UserInfoBasicOptionsView: React.FC<{\n    member: User | RoomMember;\n    room: Room;\n    children?: ReactNode;\n}> = ({ room, member, children }) => {\n    const vm = useUserInfoBasicOptionsViewModel(room, member);\n\n    let insertPillButton: JSX.Element | undefined;\n    let inviteUserButton: JSX.Element | undefined;\n    let readReceiptButton: JSX.Element | undefined;\n\n    if (!vm.isMe) {\n        readReceiptButton = (\n            <MenuItem\n                role=\"button\"\n                onSelect={async (ev) => {\n                    ev.preventDefault();\n                    vm.onReadReceiptButton();\n                }}\n                label={_t(\"user_info|jump_to_rr_button\")}\n                disabled={vm.readReceiptButtonDisabled}\n                Icon={CheckIcon}\n            />\n        );\n\n        if (vm.showInsertPillButton) {\n            insertPillButton = (\n                <MenuItem\n                    role=\"button\"\n                    onSelect={async (ev) => {\n                        ev.preventDefault();\n                        vm.onInsertPillButton();\n                    }}\n                    label={_t(\"action|mention\")}\n                    Icon={MentionIcon}\n                />\n            );\n        }\n\n        if (vm.showInviteButton && shouldShowComponent(UIComponent.InviteUsers)) {\n            inviteUserButton = (\n                <MenuItem\n                    role=\"button\"\n                    onSelect={async (ev) => {\n                        ev.preventDefault();\n                        vm.onInviteUserButton(room.roomId, ev);\n                    }}\n                    label={_t(\"action|invite\")}\n                    Icon={InviteIcon}\n                />\n            );\n        }\n    }\n\n    const shareUserButton = (\n        <MenuItem\n            role=\"button\"\n            onSelect={async (ev) => {\n                ev.preventDefault();\n                vm.onShareUserClick();\n            }}\n            label={_t(\"user_info|share_button\")}\n            Icon={ShareIcon}\n        />\n    );\n\n    const directMessageButton =\n        vm.isMe || !shouldShowComponent(UIComponent.CreateRooms) ? null : (\n            <MessageButton member={member} openDMForUser={vm.onOpenDmForUser} />\n        );\n\n    return (\n        <Container>\n            {children}\n            {directMessageButton}\n            {inviteUserButton}\n            {readReceiptButton}\n            {shareUserButton}\n            {insertPillButton}\n        </Container>\n    );\n};\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useContext } from \"react\";\nimport { RoomMember, User, type Room, KnownMembership } from \"matrix-js-sdk/src/matrix\";\n\nimport Modal from \"../../../../Modal\";\nimport ErrorDialog from \"../../../views/dialogs/ErrorDialog\";\nimport { _t, UserFriendlyError } from \"../../../../languageHandler\";\nimport MatrixClientContext from \"../../../../contexts/MatrixClientContext\";\nimport dis from \"../../../../dispatcher/dispatcher\";\nimport PosthogTrackers from \"../../../../PosthogTrackers\";\nimport { ShareDialog } from \"../../../views/dialogs/ShareDialog\";\nimport { type ComposerInsertPayload } from \"../../../../dispatcher/payloads/ComposerInsertPayload\";\nimport { Action } from \"../../../../dispatcher/actions\";\nimport { TimelineRenderingType } from \"../../../../contexts/RoomContext\";\nimport MultiInviter from \"../../../../utils/MultiInviter\";\nimport { type ViewRoomPayload } from \"../../../../dispatcher/payloads/ViewRoomPayload\";\nimport { useRoomPermissions } from \"./UserInfoBasicViewModel\";\nimport { DirectoryMember, startDmOnFirstMessage } from \"../../../../utils/direct-messages\";\nimport { type Member } from \"../../../views/right_panel/UserInfo\";\n\nexport interface UserInfoBasicOptionsState {\n    // boolean to know if selected user is current user\n    isMe: boolean;\n    // boolean to display/hide invite button\n    showInviteButton: boolean;\n    // boolean to display/hide insert pill button\n    showInsertPillButton: boolean | \"\";\n    // boolean to display/hide read receipt button\n    readReceiptButtonDisabled: boolean;\n    // Method called when a insert pill button is clicked\n    onInsertPillButton: () => void;\n    // Method called when a read receipt button is clicked, will add a pill in the input message field\n    onReadReceiptButton: () => void;\n    // Method called when a share user button is clicked, will display modal with profile to share\n    onShareUserClick: () => void;\n    // Method called when a invite button is clicked, will display modal to invite user\n    onInviteUserButton: (fallbackRoomId: string, evt: Event) => Promise<void>;\n    // Method called when the DM button is clicked, will open a DM with the selected member\n    onOpenDmForUser: (member: Member) => Promise<void>;\n}\n\nexport const useUserInfoBasicOptionsViewModel = (room: Room, member: User | RoomMember): UserInfoBasicOptionsState => {\n    const cli = useContext(MatrixClientContext);\n\n    // selected member is current user\n    const isMe = member.userId === cli.getUserId();\n\n    // Those permissions are updated when a change is done on the room current state and the selected user\n    const roomPermissions = useRoomPermissions(cli, room, member as RoomMember);\n\n    const isSpace = room?.isSpaceRoom();\n\n    // read receipt button stay disable for a room space or if all events where read (null)\n    const readReceiptButtonDisabled = isSpace || !room?.getEventReadUpTo(member.userId);\n\n    // always show exempt when room is a space\n    const showInsertPillButton = member instanceof RoomMember && member.roomId && !isSpace;\n\n    // show invite button only if current user has the permission to invite and the selected user membership is LEAVE\n    const showInviteButton =\n        member instanceof RoomMember &&\n        roomPermissions.canInvite &&\n        (member?.membership ?? KnownMembership.Leave) === KnownMembership.Leave;\n\n    const onReadReceiptButton = function (): void {\n        const room = member instanceof RoomMember ? cli.getRoom(member.roomId) : null;\n        if (!room || readReceiptButtonDisabled) return;\n\n        dis.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            highlighted: true,\n            // this could return null, the default prevents a type error\n            event_id: room.getEventReadUpTo(member.userId) || undefined,\n            room_id: room.roomId,\n            metricsTrigger: undefined, // room doesn't change\n        });\n    };\n\n    const onInsertPillButton = function (): void {\n        dis.dispatch<ComposerInsertPayload>({\n            action: Action.ComposerInsert,\n            userId: member.userId,\n            timelineRenderingType: TimelineRenderingType.Room,\n        });\n    };\n\n    const onInviteUserButton = async (fallbackRoomId: string, ev: Event): Promise<void> => {\n        try {\n            const roomId = member instanceof RoomMember && member.roomId ? member.roomId : fallbackRoomId;\n\n            // We use a MultiInviter to re-use the invite logic, even though we're only inviting one user.\n            const inviter = new MultiInviter(cli, roomId || \"\");\n            await inviter.invite([member.userId]).then(() => {\n                if (inviter.getCompletionState(member.userId) !== \"invited\") {\n                    const errorStringFromInviterUtility = inviter.getErrorText(member.userId);\n                    if (errorStringFromInviterUtility) {\n                        throw new Error(errorStringFromInviterUtility);\n                    } else {\n                        throw new UserFriendlyError(\"slash_command|invite_failed\", {\n                            user: member.userId,\n                            roomId,\n                            cause: undefined,\n                        });\n                    }\n                }\n            });\n        } catch (err) {\n            const description = err instanceof Error ? err.message : _t(\"invite|failed_generic\");\n\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"invite|failed_title\"),\n                description,\n            });\n        }\n\n        PosthogTrackers.trackInteraction(\"WebRightPanelRoomUserInfoInviteButton\", ev);\n    };\n\n    const onShareUserClick = (): void => {\n        Modal.createDialog(ShareDialog, {\n            target: member,\n        });\n    };\n\n    const onOpenDmForUser = async (user: Member): Promise<void> => {\n        const avatarUrl = user instanceof User ? user.avatarUrl : user.getMxcAvatarUrl();\n        const startDmUser = new DirectoryMember({\n            user_id: user.userId,\n            display_name: user.rawDisplayName,\n            avatar_url: avatarUrl,\n        });\n        await startDmOnFirstMessage(cli, [startDmUser]);\n    };\n\n    return {\n        isMe,\n        showInviteButton,\n        showInsertPillButton,\n        readReceiptButtonDisabled,\n        onReadReceiptButton,\n        onInsertPillButton,\n        onInviteUserButton,\n        onShareUserClick,\n        onOpenDmForUser,\n    };\n};\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type RoomMember, type User, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { MenuItem } from \"@vector-im/compound-web\";\nimport { DeleteIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../../languageHandler\";\nimport { useUserInfoBasicViewModel } from \"../../../viewmodels/right_panel/user_info/UserInfoBasicViewModel\";\nimport { PowerLevelSection } from \"./UserInfoPowerLevels\";\nimport { Container } from \"../UserInfo\";\nimport { IgnoreToggleButton } from \"./UserInfoIgnoreButtonView\";\nimport Spinner from \"../../elements/Spinner\";\nimport { UserInfoAdminToolsContainer } from \"./UserInfoAdminToolsContainer\";\nimport { UserInfoBasicOptionsView } from \"./UserInfoBasicOptionsView\";\n\n/**\n * There are two types of components that can be displayed in the right panel concerning userinfo\n * Basic info or Encryption Panel\n */\nexport const UserInfoBasicView: React.FC<{\n    room: Room;\n    member: User | RoomMember;\n}> = ({ room, member }) => {\n    const vm = useUserInfoBasicViewModel(room, member);\n    let synapseDeactivateButton;\n    let spinner;\n    let memberDetails;\n    let adminToolsContainer;\n\n    if (vm.showDeactivateButton) {\n        synapseDeactivateButton = (\n            <MenuItem\n                role=\"button\"\n                onSelect={async (ev) => {\n                    ev.preventDefault();\n                    vm.onSynapseDeactivate();\n                }}\n                label={_t(\"user_info|deactivate_confirm_action\")}\n                kind=\"critical\"\n                Icon={DeleteIcon}\n            />\n        );\n    }\n\n    if (room && (member as RoomMember).roomId) {\n        // hide the Roles section for DMs as it doesn't make sense there\n        if (!vm.isRoomDMForMember) {\n            memberDetails = (\n                <PowerLevelSection user={member as RoomMember} room={room} roomPermissions={vm.roomPermissions} />\n            );\n        }\n\n        adminToolsContainer = (\n            <UserInfoAdminToolsContainer\n                powerLevels={vm.powerLevels}\n                member={member as RoomMember}\n                room={room}\n                isUpdating={vm.pendingUpdateCount > 0}\n                startUpdating={vm.startUpdating}\n                stopUpdating={vm.stopUpdating}\n            >\n                {synapseDeactivateButton}\n            </UserInfoAdminToolsContainer>\n        );\n    } else if (synapseDeactivateButton) {\n        adminToolsContainer = <Container>{synapseDeactivateButton}</Container>;\n    }\n\n    if (vm.pendingUpdateCount > 0) {\n        spinner = <Spinner />;\n    }\n\n    return (\n        <React.Fragment>\n            <UserInfoBasicOptionsView room={room} member={member}>\n                {memberDetails}\n            </UserInfoBasicOptionsView>\n            {adminToolsContainer}\n            {!vm.isMe && (\n                <Container>\n                    <IgnoreToggleButton member={member} />\n                </Container>\n            )}\n            {spinner}\n        </React.Fragment>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2017, 2018 Vector Creations Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode, useContext, useEffect, useMemo, useState } from \"react\";\nimport classNames from \"classnames\";\nimport { type MatrixClient, type RoomMember, type Room, type User, type Device } from \"matrix-js-sdk/src/matrix\";\nimport { type UserVerificationStatus, type VerificationRequest, CryptoEvent } from \"matrix-js-sdk/src/crypto-api\";\n\nimport Modal from \"../../../Modal\";\nimport { _t } from \"../../../languageHandler\";\nimport { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { RightPanelPhases } from \"../../../stores/right-panel/RightPanelStorePhases\";\nimport EncryptionPanel from \"./EncryptionPanel\";\nimport { useIsEncrypted } from \"../../../hooks/useIsEncrypted\";\nimport BaseCard from \"./BaseCard\";\nimport QuestionDialog from \"../dialogs/QuestionDialog\";\nimport RightPanelStore from \"../../../stores/right-panel/RightPanelStore\";\nimport { type IRightPanelCardState } from \"../../../stores/right-panel/RightPanelStoreIPanelState\";\nimport PosthogTrackers from \"../../../PosthogTrackers\";\nimport { UserInfoHeaderView } from \"./user_info/UserInfoHeaderView\";\nimport { UserInfoBasicView } from \"./user_info/UserInfoBasicView\";\n\nexport interface IDevice extends Device {\n    ambiguous?: boolean;\n}\n\nexport const disambiguateDevices = (devices: IDevice[]): void => {\n    const names = Object.create(null);\n    for (let i = 0; i < devices.length; i++) {\n        const name = devices[i].displayName ?? \"\";\n        const indexList = names[name] || [];\n        indexList.push(i);\n        names[name] = indexList;\n    }\n    for (const name in names) {\n        if (names[name].length > 1) {\n            names[name].forEach((j: number) => {\n                devices[j].ambiguous = true;\n            });\n        }\n    }\n};\n\nexport const warnSelfDemote = async (isSpace: boolean): Promise<boolean> => {\n    const { finished } = Modal.createDialog(QuestionDialog, {\n        title: _t(\"user_info|demote_self_confirm_title\"),\n        description: (\n            <div>\n                {isSpace\n                    ? _t(\"user_info|demote_self_confirm_description_space\")\n                    : _t(\"user_info|demote_self_confirm_room\")}\n            </div>\n        ),\n        button: _t(\"user_info|demote_button\"),\n    });\n\n    const [confirmed] = await finished;\n    return !!confirmed;\n};\n\nexport const Container: React.FC<{\n    children: ReactNode;\n    className?: string;\n}> = ({ children, className }) => {\n    const classes = classNames(\"mx_UserInfo_container\", className);\n    return <div className={classes}>{children}</div>;\n};\n\nexport interface IPowerLevelsContent {\n    events?: Record<string, number>;\n    // eslint-disable-next-line camelcase\n    users_default?: number;\n    // eslint-disable-next-line camelcase\n    events_default?: number;\n    // eslint-disable-next-line camelcase\n    state_default?: number;\n    ban?: number;\n    kick?: number;\n    redact?: number;\n}\n\nexport const isMuted = (member: RoomMember, powerLevelContent: IPowerLevelsContent): boolean => {\n    if (!powerLevelContent || !member) return false;\n\n    const levelToSend =\n        (powerLevelContent.events ? powerLevelContent.events[\"m.room.message\"] : null) ||\n        powerLevelContent.events_default;\n\n    // levelToSend could be undefined as .events_default is optional. Coercing in this case using\n    // Number() would always return false, so this preserves behaviour\n    // FIXME: per the spec, if `events_default` is unset, it defaults to zero. If\n    //   the member has a negative powerlevel, this will give an incorrect result.\n    if (levelToSend === undefined) return false;\n\n    return member.powerLevel < levelToSend;\n};\n\nexport interface IRoomPermissions {\n    modifyLevelMax: number;\n    canEdit: boolean;\n    canInvite: boolean;\n}\n\nasync function getUserDeviceInfo(\n    userId: string,\n    cli: MatrixClient,\n    downloadUncached = false,\n): Promise<Device[] | undefined> {\n    const userDeviceMap = await cli.getCrypto()?.getUserDeviceInfo([userId], downloadUncached);\n    const devicesMap = userDeviceMap?.get(userId);\n\n    if (!devicesMap) return;\n\n    return Array.from(devicesMap.values());\n}\n\nexport const useDevices = (userId: string): IDevice[] | undefined | null => {\n    const cli = useContext(MatrixClientContext);\n\n    // undefined means yet to be loaded, null means failed to load, otherwise list of devices\n    const [devices, setDevices] = useState<undefined | null | IDevice[]>(undefined);\n    // Download device lists\n    useEffect(() => {\n        setDevices(undefined);\n\n        let cancelled = false;\n\n        async function downloadDeviceList(): Promise<void> {\n            try {\n                const devices = await getUserDeviceInfo(userId, cli, true);\n\n                if (cancelled || !devices) {\n                    // we got cancelled - presumably a different user now\n                    return;\n                }\n\n                disambiguateDevices(devices);\n                setDevices(devices);\n            } catch {\n                setDevices(null);\n            }\n        }\n        downloadDeviceList();\n\n        // Handle being unmounted\n        return () => {\n            cancelled = true;\n        };\n    }, [cli, userId]);\n\n    // Listen to changes\n    useEffect(() => {\n        let cancel = false;\n        const updateDevices = async (): Promise<void> => {\n            const newDevices = await getUserDeviceInfo(userId, cli);\n            if (cancel || !newDevices) return;\n            setDevices(newDevices);\n        };\n        const onDevicesUpdated = (users: string[]): void => {\n            if (!users.includes(userId)) return;\n            updateDevices();\n        };\n        const onUserTrustStatusChanged = (_userId: string, trustLevel: UserVerificationStatus): void => {\n            if (_userId !== userId) return;\n            updateDevices();\n        };\n        cli.on(CryptoEvent.DevicesUpdated, onDevicesUpdated);\n        cli.on(CryptoEvent.UserTrustStatusChanged, onUserTrustStatusChanged);\n        // Handle being unmounted\n        return () => {\n            cancel = true;\n            cli.removeListener(CryptoEvent.DevicesUpdated, onDevicesUpdated);\n            cli.removeListener(CryptoEvent.UserTrustStatusChanged, onUserTrustStatusChanged);\n        };\n    }, [cli, userId]);\n\n    return devices;\n};\n\nexport type Member = User | RoomMember;\n\ninterface IProps {\n    user: Member;\n    room?: Room;\n    phase: RightPanelPhases.MemberInfo | RightPanelPhases.EncryptionPanel;\n    onClose(): void;\n    verificationRequest?: VerificationRequest;\n    verificationRequestPromise?: Promise<VerificationRequest>;\n}\n\nconst UserInfo: React.FC<IProps> = ({ user, room, onClose, phase = RightPanelPhases.MemberInfo, ...props }) => {\n    const cli = useContext(MatrixClientContext);\n\n    // fetch latest room member if we have a room, so we don't show historical information, falling back to user\n    const member = useMemo(() => (room ? room.getMember(user.userId) || user : user), [room, user]);\n\n    const isRoomEncrypted = useIsEncrypted(cli, room);\n    const devices = useDevices(user.userId) ?? [];\n\n    const classes = [\"mx_UserInfo\"];\n\n    let cardState: IRightPanelCardState = {};\n    // We have no previousPhase for when viewing a UserInfo without a Room at this time\n    if (room && phase === RightPanelPhases.EncryptionPanel) {\n        cardState = { member };\n    }\n\n    const onEncryptionPanelClose = (): void => {\n        RightPanelStore.instance.popCard();\n    };\n\n    let content: JSX.Element | undefined;\n    switch (phase) {\n        case RightPanelPhases.MemberInfo:\n            content = <UserInfoBasicView room={room as Room} member={member as User} />;\n            break;\n        case RightPanelPhases.EncryptionPanel:\n            classes.push(\"mx_UserInfo_smallAvatar\");\n            content = (\n                <EncryptionPanel\n                    {...(props as React.ComponentProps<typeof EncryptionPanel>)}\n                    member={member as User | RoomMember}\n                    onClose={onEncryptionPanelClose}\n                    isRoomEncrypted={Boolean(isRoomEncrypted)}\n                />\n            );\n            break;\n    }\n\n    let closeLabel: string | undefined;\n    if (phase === RightPanelPhases.EncryptionPanel) {\n        const verificationRequest = (props as React.ComponentProps<typeof EncryptionPanel>).verificationRequest;\n        if (verificationRequest && verificationRequest.pending) {\n            closeLabel = _t(\"action|cancel\");\n        }\n    }\n\n    const header = (\n        <>\n            <UserInfoHeaderView\n                hideVerificationSection={phase === RightPanelPhases.EncryptionPanel}\n                member={member}\n                devices={devices}\n                roomId={room?.roomId}\n            />\n        </>\n    );\n\n    return (\n        <BaseCard\n            className={classes.join(\" \")}\n            header={_t(\"common|profile\")}\n            onClose={onClose}\n            closeLabel={closeLabel}\n            cardState={cardState}\n            onBack={(ev: ButtonEvent) => {\n                if (RightPanelStore.instance.previousCard.phase === RightPanelPhases.MemberList) {\n                    PosthogTrackers.trackInteraction(\"WebRightPanelRoomUserInfoBackButton\", ev);\n                }\n            }}\n        >\n            {header}\n            {content}\n        </BaseCard>\n    );\n};\n\nexport default UserInfo;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nexport const CardContext = React.createContext({ isCard: false });\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport const ReadPinsEventId = \"im.vector.room.read_pins\";\n\ndeclare module \"matrix-js-sdk/src/types\" {\n    interface RoomAccountDataEvents {\n        [ReadPinsEventId]: { event_ids: string[] };\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ChangeEvent } from \"react\";\nimport { CloseIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport Field from \"./Field\";\nimport AccessibleButton, { type ButtonEvent } from \"./AccessibleButton\";\n\ninterface IItemProps {\n    index: number;\n    value?: string;\n    onRemove?(index: number): void;\n}\n\ninterface IItemState {\n    verifyRemove: boolean;\n}\n\nexport class EditableItem extends React.Component<IItemProps, IItemState> {\n    public state = {\n        verifyRemove: false,\n    };\n\n    private onRemove = (e: ButtonEvent): void => {\n        e.stopPropagation();\n        e.preventDefault();\n\n        this.setState({ verifyRemove: true });\n    };\n\n    private onDontRemove = (e: ButtonEvent): void => {\n        e.stopPropagation();\n        e.preventDefault();\n\n        this.setState({ verifyRemove: false });\n    };\n\n    private onActuallyRemove = (e: ButtonEvent): void => {\n        e.stopPropagation();\n        e.preventDefault();\n\n        if (this.props.onRemove) this.props.onRemove(this.props.index);\n        this.setState({ verifyRemove: false });\n    };\n\n    public render(): React.ReactNode {\n        if (this.state.verifyRemove) {\n            return (\n                <div className=\"mx_EditableItem\">\n                    <span className=\"mx_EditableItem_promptText\">{_t(\"common|are_you_sure\")}</span>\n                    <AccessibleButton\n                        onClick={this.onActuallyRemove}\n                        kind=\"primary_sm\"\n                        className=\"mx_EditableItem_confirmBtn\"\n                    >\n                        {_t(\"action|yes\")}\n                    </AccessibleButton>\n                    <AccessibleButton\n                        onClick={this.onDontRemove}\n                        kind=\"danger_sm\"\n                        className=\"mx_EditableItem_confirmBtn\"\n                    >\n                        {_t(\"action|no\")}\n                    </AccessibleButton>\n                </div>\n            );\n        }\n\n        return (\n            <div className=\"mx_EditableItem\">\n                <AccessibleButton\n                    onClick={this.onRemove}\n                    className=\"mx_EditableItem_delete\"\n                    title={_t(\"action|remove\")}\n                    role=\"button\"\n                >\n                    <CloseIcon />\n                </AccessibleButton>\n                <span className=\"mx_EditableItem_item\">{this.props.value}</span>\n            </div>\n        );\n    }\n}\n\ninterface IProps {\n    id: string;\n    items: string[];\n    itemsLabel?: string;\n    noItemsLabel?: string;\n    placeholder?: string;\n    newItem?: string;\n    canEdit?: boolean;\n    canRemove?: boolean;\n    suggestionsListId?: string;\n    onItemAdded?(item?: string): void;\n    onItemRemoved?(index: number): void;\n    onNewItemChanged?(item: string): void;\n}\n\nexport default class EditableItemList<P extends object> extends React.PureComponent<IProps & P> {\n    protected onItemAdded = (e: ButtonEvent): void => {\n        e.stopPropagation();\n        e.preventDefault();\n\n        this.props.onItemAdded?.(this.props.newItem);\n    };\n\n    protected onItemRemoved = (index: number): void => {\n        this.props.onItemRemoved?.(index);\n    };\n\n    protected onNewItemChanged = (e: ChangeEvent<HTMLInputElement>): void => {\n        this.props.onNewItemChanged?.(e.target.value);\n    };\n\n    protected renderNewItemField(): JSX.Element {\n        return (\n            <form\n                onSubmit={this.onItemAdded}\n                autoComplete=\"off\"\n                noValidate={true}\n                className=\"mx_EditableItemList_newItem\"\n            >\n                <Field\n                    label={this.props.placeholder}\n                    type=\"text\"\n                    autoComplete=\"off\"\n                    value={this.props.newItem || \"\"}\n                    onChange={this.onNewItemChanged}\n                    list={this.props.suggestionsListId}\n                />\n                <AccessibleButton onClick={this.onItemAdded} kind=\"primary\" disabled={!this.props.newItem}>\n                    {_t(\"action|add\")}\n                </AccessibleButton>\n            </form>\n        );\n    }\n\n    public render(): React.ReactNode {\n        const editableItems = this.props.items.map((item, index) => {\n            if (!this.props.canRemove) {\n                return <li key={item}>{item}</li>;\n            }\n\n            return <EditableItem key={item} index={index} value={item} onRemove={this.onItemRemoved} />;\n        });\n\n        const editableItemsSection = this.props.canRemove ? editableItems : <ul>{editableItems}</ul>;\n        const label = this.props.items.length > 0 ? this.props.itemsLabel : this.props.noItemsLabel;\n\n        return (\n            <div className=\"mx_EditableItemList\" id={this.props.id}>\n                <div className=\"mx_EditableItemList_label\">{label}</div>\n                {editableItemsSection}\n                {this.props.canEdit ? this.renderNewItemField() : <div />}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEventHandler } from \"react\";\nimport { JoinRule, Visibility } from \"matrix-js-sdk/src/matrix\";\nimport { SettingsToggleInput } from \"@vector-im/compound-web\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport DirectoryCustomisations from \"../../../customisations/Directory\";\nimport Modal from \"../../../Modal\";\nimport ErrorDialog from \"../dialogs/ErrorDialog\";\n\ninterface IProps {\n    roomId: string;\n    label?: string;\n    canSetCanonicalAlias?: boolean;\n}\n\ninterface IState {\n    isRoomPublished: boolean;\n    busy: boolean;\n}\n\nexport default class RoomPublishSetting extends React.PureComponent<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            isRoomPublished: false,\n            busy: false,\n        };\n    }\n\n    private showError(): void {\n        Modal.createDialog(ErrorDialog, {\n            title: _t(\"room_settings|general|error_publishing\"),\n            description: _t(\"room_settings|general|error_publishing_detail\"),\n        });\n    }\n\n    private onRoomPublishChange: ChangeEventHandler<HTMLInputElement> = async (evt): Promise<void> => {\n        const newValue = evt.target.checked;\n        this.setState({ busy: true });\n        const client = MatrixClientPeg.safeGet();\n\n        try {\n            await client.setRoomDirectoryVisibility(\n                this.props.roomId,\n                newValue ? Visibility.Public : Visibility.Private,\n            );\n            this.setState({ isRoomPublished: newValue });\n        } catch (ex) {\n            logger.error(\"Error while setting room directory visibility\", ex);\n            this.showError();\n        } finally {\n            this.setState({ busy: false });\n        }\n    };\n\n    public componentDidMount(): void {\n        const client = MatrixClientPeg.safeGet();\n        client.getRoomDirectoryVisibility(this.props.roomId).then((result) => {\n            this.setState({ isRoomPublished: result.visibility === \"public\" });\n        });\n    }\n\n    public render(): React.ReactNode {\n        const client = MatrixClientPeg.safeGet();\n\n        const room = client.getRoom(this.props.roomId);\n        const isRoomPublishable = room && room.getJoinRule() !== JoinRule.Invite;\n        const canSetCanonicalAlias =\n            DirectoryCustomisations.requireCanonicalAliasAccessToPublish?.() === false ||\n            this.props.canSetCanonicalAlias;\n\n        let disabledMessage;\n        if (!isRoomPublishable) {\n            disabledMessage = _t(\"room_settings|general|publish_warn_invite_only\");\n        } else if (!canSetCanonicalAlias) {\n            disabledMessage = _t(\"room_settings|general|publish_warn_no_canonical_permission\");\n        }\n\n        const enabled = canSetCanonicalAlias && (isRoomPublishable || this.state.isRoomPublished);\n\n        return (\n            <SettingsToggleInput\n                name=\"room-publish\"\n                checked={this.state.isRoomPublished}\n                onChange={this.onRoomPublishChange}\n                disabled={!enabled || this.state.busy}\n                disabledMessage={disabledMessage}\n                label={_t(\"room_settings|general|publish_toggle\", {\n                    domain: client.getDomain(),\n                })}\n            />\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2016-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, {\n    type JSX,\n    type ToggleEvent,\n    type ChangeEvent,\n    type ContextType,\n    createRef,\n    type SyntheticEvent,\n} from \"react\";\nimport { type MatrixEvent, EventType } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type RoomCanonicalAliasEventContent } from \"matrix-js-sdk/src/types\";\n\nimport EditableItemList from \"../elements/EditableItemList\";\nimport { _t } from \"../../../languageHandler\";\nimport Field from \"../elements/Field\";\nimport Spinner from \"../elements/Spinner\";\nimport ErrorDialog from \"../dialogs/ErrorDialog\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport Modal from \"../../../Modal\";\nimport RoomPublishSetting from \"./RoomPublishSetting\";\nimport RoomAliasField from \"../elements/RoomAliasField\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport SettingsFieldset from \"../settings/SettingsFieldset\";\n\ninterface IEditableAliasesListProps {\n    roomId?: string;\n    domain?: string;\n}\n\nclass EditableAliasesList extends EditableItemList<IEditableAliasesListProps> {\n    private aliasField = createRef<RoomAliasField>();\n\n    private onAliasAdded = async (ev: SyntheticEvent): Promise<void> => {\n        ev.preventDefault();\n\n        if (!this.aliasField.current) return;\n        await this.aliasField.current.validate({ allowEmpty: false });\n\n        if (this.aliasField.current.isValid) {\n            if (this.props.onItemAdded) this.props.onItemAdded(this.props.newItem);\n            return;\n        }\n\n        this.aliasField.current.focus();\n        this.aliasField.current.validate({ allowEmpty: false, focused: true });\n    };\n\n    protected renderNewItemField(): JSX.Element {\n        const onChange = (alias: string): void => this.props.onNewItemChanged?.(alias);\n        return (\n            <form\n                onSubmit={this.onAliasAdded}\n                autoComplete=\"off\"\n                noValidate={true}\n                className=\"mx_EditableItemList_newItem\"\n            >\n                <RoomAliasField\n                    ref={this.aliasField}\n                    onChange={onChange}\n                    value={this.props.newItem || \"\"}\n                    domain={this.props.domain}\n                    roomId={this.props.roomId}\n                />\n                <AccessibleButton onClick={this.onAliasAdded} kind=\"primary\">\n                    {_t(\"action|add\")}\n                </AccessibleButton>\n            </form>\n        );\n    }\n}\n\ninterface IProps {\n    roomId: string;\n    canSetCanonicalAlias: boolean;\n    canSetAliases: boolean;\n    canonicalAliasEvent?: MatrixEvent;\n    hidePublishSetting?: boolean;\n}\n\ninterface IState {\n    // [ #alias:domain.tld, ... ]\n    altAliases: string[];\n    // [ #alias:my-hs.tld, ... ]\n    localAliases: string[];\n    // #canonical:domain.tld\n    canonicalAlias: string | null;\n    updatingCanonicalAlias: boolean;\n    localAliasesLoading: boolean;\n    detailsOpen: boolean;\n    newAlias?: string;\n    newAltAlias?: string;\n}\n\nexport default class AliasSettings extends React.Component<IProps, IState> {\n    public static contextType = MatrixClientContext;\n    declare public context: ContextType<typeof MatrixClientContext>;\n\n    public static defaultProps = {\n        canSetAliases: false,\n        canSetCanonicalAlias: false,\n    };\n\n    public constructor(props: IProps) {\n        super(props);\n\n        const state: IState = {\n            altAliases: [],\n            localAliases: [],\n            canonicalAlias: null,\n            updatingCanonicalAlias: false,\n            localAliasesLoading: false,\n            detailsOpen: false,\n        };\n\n        if (props.canonicalAliasEvent) {\n            const content = props.canonicalAliasEvent.getContent();\n            const altAliases = content.alt_aliases;\n            if (Array.isArray(altAliases)) {\n                state.altAliases = altAliases.slice();\n            }\n            state.canonicalAlias = content.alias;\n        }\n\n        this.state = state;\n    }\n\n    public componentDidMount(): void {\n        if (this.props.canSetCanonicalAlias) {\n            // load local aliases for providing recommendations\n            // for the canonical alias and alt_aliases\n            this.loadLocalAliases();\n        }\n    }\n\n    private async loadLocalAliases(): Promise<void> {\n        this.setState({ localAliasesLoading: true });\n        try {\n            const mxClient = this.context;\n\n            let localAliases: string[] = [];\n            const response = await mxClient.getLocalAliases(this.props.roomId);\n            if (Array.isArray(response?.aliases)) {\n                localAliases = response.aliases;\n            }\n            this.setState({ localAliases });\n\n            if (localAliases.length === 0) {\n                this.setState({ detailsOpen: true });\n            }\n        } finally {\n            this.setState({ localAliasesLoading: false });\n        }\n    }\n\n    private changeCanonicalAlias(alias: string | null): void {\n        if (!this.props.canSetCanonicalAlias) return;\n\n        const oldAlias = this.state.canonicalAlias;\n        this.setState({\n            canonicalAlias: alias,\n            updatingCanonicalAlias: true,\n        });\n\n        const eventContent: RoomCanonicalAliasEventContent = {\n            alt_aliases: this.state.altAliases,\n        };\n\n        if (alias) eventContent[\"alias\"] = alias;\n\n        this.context\n            .sendStateEvent(this.props.roomId, EventType.RoomCanonicalAlias, eventContent, \"\")\n            .catch((err) => {\n                logger.error(err);\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"room_settings|general|error_updating_canonical_alias_title\"),\n                    description: _t(\"room_settings|general|error_updating_canonical_alias_description\"),\n                });\n                this.setState({ canonicalAlias: oldAlias });\n            })\n            .finally(() => {\n                this.setState({ updatingCanonicalAlias: false });\n            });\n    }\n\n    private changeAltAliases(altAliases: string[]): void {\n        if (!this.props.canSetCanonicalAlias) return;\n\n        this.setState({\n            updatingCanonicalAlias: true,\n        });\n\n        const eventContent: RoomCanonicalAliasEventContent = {};\n\n        if (this.state.canonicalAlias) {\n            eventContent[\"alias\"] = this.state.canonicalAlias;\n        }\n        if (altAliases) {\n            eventContent[\"alt_aliases\"] = altAliases;\n        }\n\n        this.context\n            .sendStateEvent(this.props.roomId, EventType.RoomCanonicalAlias, eventContent, \"\")\n            .then(() => {\n                this.setState({\n                    altAliases,\n                });\n            })\n            .catch((err) => {\n                // TODO: Add error handling based upon server validation\n                logger.error(err);\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"room_settings|general|error_updating_canonical_alias_title\"),\n                    description: _t(\"room_settings|general|error_updating_alias_description\"),\n                });\n            })\n            .finally(() => {\n                this.setState({ updatingCanonicalAlias: false });\n            });\n    }\n\n    private onNewAliasChanged = (value: string): void => {\n        this.setState({ newAlias: value });\n    };\n\n    private onLocalAliasAdded = (alias?: string): void => {\n        if (!alias || alias.length === 0) return; // ignore attempts to create blank aliases\n\n        const localDomain = this.context.getDomain();\n        if (!alias.includes(\":\")) alias += \":\" + localDomain;\n\n        this.context\n            .createAlias(alias, this.props.roomId)\n            .then(() => {\n                this.setState({\n                    localAliases: this.state.localAliases.concat(alias!),\n                    newAlias: undefined,\n                });\n                if (!this.state.canonicalAlias) {\n                    this.changeCanonicalAlias(alias!);\n                }\n            })\n            .catch((err) => {\n                logger.error(err);\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"room_settings|general|error_creating_alias_title\"),\n                    description: _t(\"room_settings|general|error_creating_alias_description\"),\n                });\n            });\n    };\n\n    private onLocalAliasDeleted = (index: number): void => {\n        const alias = this.state.localAliases[index];\n        // TODO: In future, we should probably be making sure that the alias actually belongs\n        // to this room. See https://github.com/vector-im/element-web/issues/7353\n        this.context\n            .deleteAlias(alias)\n            .then(() => {\n                const localAliases = this.state.localAliases.filter((a) => a !== alias);\n                this.setState({ localAliases });\n\n                if (this.state.canonicalAlias === alias) {\n                    this.changeCanonicalAlias(null);\n                }\n            })\n            .catch((err) => {\n                logger.error(err);\n                let description;\n                if (err.errcode === \"M_FORBIDDEN\") {\n                    description = _t(\"room_settings|general|error_deleting_alias_description_forbidden\");\n                } else {\n                    description = _t(\"room_settings|general|error_deleting_alias_description\");\n                }\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"room_settings|general|error_deleting_alias_title\"),\n                    description,\n                });\n            });\n    };\n\n    private onLocalAliasesToggled = (event: ToggleEvent<HTMLDetailsElement>): void => {\n        // expanded\n        if (event.currentTarget.open) {\n            // if local aliases haven't been preloaded yet at component mount\n            if (!this.props.canSetCanonicalAlias && this.state.localAliases.length === 0) {\n                this.loadLocalAliases();\n            }\n        }\n        this.setState({ detailsOpen: event.currentTarget.open });\n    };\n\n    private onCanonicalAliasChange = (event: ChangeEvent<HTMLSelectElement>): void => {\n        this.changeCanonicalAlias(event.target.value);\n    };\n\n    private onNewAltAliasChanged = (value: string): void => {\n        this.setState({ newAltAlias: value });\n    };\n\n    private onAltAliasAdded = (alias: string): void => {\n        const altAliases = this.state.altAliases.slice();\n        if (!altAliases.some((a) => a.trim() === alias.trim())) {\n            altAliases.push(alias.trim());\n            this.changeAltAliases(altAliases);\n            this.setState({ newAltAlias: \"\" });\n        }\n    };\n\n    private onAltAliasDeleted = (index: number): void => {\n        const altAliases = this.state.altAliases.slice();\n        altAliases.splice(index, 1);\n        this.changeAltAliases(altAliases);\n    };\n\n    private getAliases(): string[] {\n        return this.state.altAliases.concat(this.getLocalNonAltAliases());\n    }\n\n    private getLocalNonAltAliases(): string[] {\n        const { altAliases } = this.state;\n        return this.state.localAliases.filter((alias) => !altAliases.includes(alias));\n    }\n\n    public render(): React.ReactNode {\n        const mxClient = this.context;\n        const localDomain = mxClient.getDomain()!;\n        const isSpaceRoom = mxClient.getRoom(this.props.roomId)?.isSpaceRoom();\n\n        let found = false;\n        const canonicalValue = this.state.canonicalAlias || \"\";\n        const canonicalAliasSection = (\n            <Field\n                onChange={this.onCanonicalAliasChange}\n                value={canonicalValue}\n                disabled={this.state.updatingCanonicalAlias || !this.props.canSetCanonicalAlias}\n                element=\"select\"\n                id=\"canonicalAlias\"\n                label={_t(\"room_settings|general|canonical_alias_field_label\")}\n            >\n                <option value=\"\" key=\"unset\">\n                    {_t(\"room_settings|alias_not_specified\")}\n                </option>\n                {this.getAliases().map((alias, i) => {\n                    if (alias === this.state.canonicalAlias) found = true;\n                    return (\n                        <option value={alias} key={i}>\n                            {alias}\n                        </option>\n                    );\n                })}\n                {found || !this.state.canonicalAlias ? (\n                    \"\"\n                ) : (\n                    <option value={this.state.canonicalAlias} key=\"arbitrary\">\n                        {this.state.canonicalAlias}\n                    </option>\n                )}\n            </Field>\n        );\n\n        let localAliasesList: JSX.Element;\n        if (this.state.localAliasesLoading) {\n            localAliasesList = <Spinner />;\n        } else {\n            localAliasesList = (\n                <EditableAliasesList\n                    id=\"roomAliases\"\n                    items={this.state.localAliases}\n                    newItem={this.state.newAlias}\n                    onNewItemChanged={this.onNewAliasChanged}\n                    canRemove={this.props.canSetAliases}\n                    canEdit={this.props.canSetAliases}\n                    onItemAdded={this.onLocalAliasAdded}\n                    onItemRemoved={this.onLocalAliasDeleted}\n                    noItemsLabel={\n                        isSpaceRoom\n                            ? _t(\"room_settings|general|no_aliases_space\")\n                            : _t(\"room_settings|general|no_aliases_room\")\n                    }\n                    placeholder={_t(\"room_settings|general|local_alias_field_label\")}\n                    domain={localDomain}\n                />\n            );\n        }\n\n        return (\n            <>\n                <SettingsFieldset\n                    data-testid=\"published-address-fieldset\"\n                    legend={_t(\"room_settings|general|published_aliases_section\")}\n                    description={\n                        <>\n                            {isSpaceRoom\n                                ? _t(\"room_settings|general|published_aliases_explainer_space\")\n                                : _t(\"room_settings|general|published_aliases_explainer_room\")}\n                            &nbsp;\n                            {_t(\"room_settings|general|published_aliases_description\")}\n                        </>\n                    }\n                >\n                    {canonicalAliasSection}\n                    {this.props.hidePublishSetting ? null : (\n                        <RoomPublishSetting\n                            roomId={this.props.roomId}\n                            canSetCanonicalAlias={this.props.canSetCanonicalAlias}\n                        />\n                    )}\n                    <datalist id=\"mx_AliasSettings_altRecommendations\">\n                        {this.getLocalNonAltAliases().map((alias) => {\n                            return <option value={alias} key={alias} />;\n                        })}\n                    </datalist>\n                    <EditableAliasesList\n                        id=\"roomAltAliases\"\n                        items={this.state.altAliases}\n                        newItem={this.state.newAltAlias}\n                        onNewItemChanged={this.onNewAltAliasChanged}\n                        canRemove={this.props.canSetCanonicalAlias}\n                        canEdit={this.props.canSetCanonicalAlias}\n                        onItemAdded={this.onAltAliasAdded}\n                        onItemRemoved={this.onAltAliasDeleted}\n                        suggestionsListId=\"mx_AliasSettings_altRecommendations\"\n                        itemsLabel={_t(\"room_settings|general|aliases_items_label\")}\n                        noItemsLabel={_t(\"room_settings|general|aliases_no_items_label\")}\n                        placeholder={_t(\"room_settings|general|new_alias_placeholder\")}\n                        roomId={this.props.roomId}\n                    />\n                </SettingsFieldset>\n                <SettingsFieldset\n                    data-testid=\"local-address-fieldset\"\n                    legend={_t(\"room_settings|general|local_aliases_section\")}\n                    description={\n                        isSpaceRoom\n                            ? _t(\"room_settings|general|local_aliases_explainer_space\", { localDomain })\n                            : _t(\"room_settings|general|local_aliases_explainer_room\", { localDomain })\n                    }\n                >\n                    <details onToggle={this.onLocalAliasesToggled} open={this.state.detailsOpen}>\n                        <summary className=\"mx_AliasSettings_localAddresses\">\n                            {this.state.detailsOpen ? _t(\"room_list|show_less\") : _t(\"common|show_more\")}\n                        </summary>\n                        {localAliasesList}\n                    </details>\n                </SettingsFieldset>\n            </>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017-2023 The Matrix.org Foundation C.I.C.\nCopyright 2018 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2016 Aviral Dasgupta\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { sortBy, uniqBy } from \"lodash\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../languageHandler\";\nimport AutocompleteProvider from \"./AutocompleteProvider\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport QueryMatcher from \"./QueryMatcher\";\nimport { PillCompletion } from \"./Components\";\nimport { makeRoomPermalink } from \"../utils/permalinks/Permalinks\";\nimport { type ICompletion, type ISelectionRange } from \"./Autocompleter\";\nimport RoomAvatar from \"../components/views/avatars/RoomAvatar\";\nimport { type TimelineRenderingType } from \"../contexts/RoomContext\";\nimport SettingsStore from \"../settings/SettingsStore\";\n\nconst ROOM_REGEX = /\\B#\\S*/g;\n\n// Prefer canonical aliases over non-canonical ones\nfunction canonicalScore(displayedAlias: string, room: Room): number {\n    return displayedAlias === room.getCanonicalAlias() ? 0 : 1;\n}\n\nfunction matcherObject(\n    room: Room,\n    displayedAlias: string,\n    matchName = \"\",\n): {\n    room: Room;\n    matchName: string;\n    displayedAlias: string;\n} {\n    return {\n        room,\n        matchName,\n        displayedAlias,\n    };\n}\n\nexport default class RoomProvider extends AutocompleteProvider {\n    protected matcher: QueryMatcher<ReturnType<typeof matcherObject>>;\n\n    public constructor(\n        private readonly room: Room,\n        renderingType?: TimelineRenderingType,\n    ) {\n        super({ commandRegex: ROOM_REGEX, renderingType });\n        this.matcher = new QueryMatcher<ReturnType<typeof matcherObject>>([], {\n            keys: [\"displayedAlias\", \"matchName\"],\n        });\n    }\n\n    protected getRooms(): Room[] {\n        const cli = MatrixClientPeg.safeGet();\n\n        // filter out spaces here as they get their own autocomplete provider\n        return cli\n            .getVisibleRooms(SettingsStore.getValue(\"feature_dynamic_room_predecessors\"))\n            .filter((r) => !r.isSpaceRoom());\n    }\n\n    public async getCompletions(\n        query: string,\n        selection: ISelectionRange,\n        force = false,\n        limit = -1,\n    ): Promise<ICompletion[]> {\n        const { command, range } = this.getCurrentCommand(query, selection, force);\n        if (command) {\n            // the only reason we need to do this is because Fuse only matches on properties\n            let matcherObjects = this.getRooms().reduce<ReturnType<typeof matcherObject>[]>((aliases, room) => {\n                if (room.getCanonicalAlias()) {\n                    aliases = aliases.concat(matcherObject(room, room.getCanonicalAlias()!, room.name));\n                }\n                if (room.getAltAliases().length) {\n                    const altAliases = room.getAltAliases().map((alias) => matcherObject(room, alias));\n                    aliases = aliases.concat(altAliases);\n                }\n                return aliases;\n            }, []);\n            // Filter out any matches where the user will have also autocompleted new rooms\n            matcherObjects = matcherObjects.filter((r) => {\n                const tombstone = r.room.currentState.getStateEvents(\"m.room.tombstone\", \"\");\n                if (tombstone && tombstone.getContent() && tombstone.getContent()[\"replacement_room\"]) {\n                    const hasReplacementRoom = matcherObjects.some(\n                        (r2) => r2.room.roomId === tombstone.getContent()[\"replacement_room\"],\n                    );\n                    return !hasReplacementRoom;\n                }\n                return true;\n            });\n\n            this.matcher.setObjects(matcherObjects);\n            const matchedString = command[0];\n            let completions = this.matcher.match(matchedString, limit);\n            completions = sortBy(completions, [\n                (c) => canonicalScore(c.displayedAlias, c.room),\n                (c) => c.displayedAlias.length,\n            ]);\n            completions = uniqBy(completions, (match) => match.room);\n            return completions\n                .map(\n                    (room): ICompletion => ({\n                        completion: room.displayedAlias,\n                        completionId: room.room.roomId,\n                        type: \"room\",\n                        suffix: \" \",\n                        href: makeRoomPermalink(this.room.client, room.displayedAlias),\n                        component: (\n                            <PillCompletion title={room.room.name} description={room.displayedAlias}>\n                                <RoomAvatar size=\"24px\" room={room.room} />\n                            </PillCompletion>\n                        ),\n                        range: range!,\n                    }),\n                )\n                .filter((completion) => !!completion.completion && completion.completion.length > 0);\n        }\n        return [];\n    }\n\n    public getName(): string {\n        return _t(\"common|rooms\");\n    }\n\n    public renderCompletions(completions: React.ReactNode[]): React.ReactNode {\n        return (\n            <div\n                className=\"mx_Autocomplete_Completion_container_pill mx_Autocomplete_Completion_container_truncate\"\n                role=\"presentation\"\n                aria-label={_t(\"composer|autocomplete|room_a11y\")}\n            >\n                {completions}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 Ryan Browne <code@commonlawfeature.com>\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2017, 2018 New Vector Ltd\nCopyright 2017 Vector Creations Ltd\nCopyright 2016 Aviral Dasgupta\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { uniq, sortBy, uniqBy, type ListIteratee } from \"lodash\";\nimport EMOTICON_REGEX from \"emojibase-regex/emoticon\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { EMOJI, type Emoji, getEmojiFromUnicode } from \"@matrix-org/emojibase-bindings\";\n\nimport { _t } from \"../languageHandler\";\nimport AutocompleteProvider from \"./AutocompleteProvider\";\nimport QueryMatcher from \"./QueryMatcher\";\nimport { PillCompletion } from \"./Components\";\nimport { type ICompletion, type ISelectionRange } from \"./Autocompleter\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { type TimelineRenderingType } from \"../contexts/RoomContext\";\nimport * as recent from \"../emojipicker/recent\";\nimport { filterBoolean } from \"../utils/arrays\";\n\nconst LIMIT = 20;\n\n// Match for ascii-style \";-)\" emoticons or \":wink:\" shortcodes provided by emojibase\n// anchored to only match from the start of parts otherwise it'll show emoji suggestions whilst typing matrix IDs\nconst EMOJI_REGEX = new RegExp(\"(\" + EMOTICON_REGEX.source + \"|(?:^|\\\\s):[+-\\\\w]*:?)$\", \"g\");\n\ninterface ISortedEmoji {\n    emoji: Emoji;\n    _orderBy: number;\n}\n\nconst SORTED_EMOJI: ISortedEmoji[] = EMOJI.sort((a, b) => {\n    if (a.group === b.group) {\n        return a.order! - b.order!;\n    }\n    return a.group! - b.group!;\n}).map((emoji, index) => ({\n    emoji,\n    // Include the index so that we can preserve the original order\n    _orderBy: index,\n}));\n\nfunction score(query: string, space: string[] | string): number {\n    if (Array.isArray(space)) {\n        return Math.min(...space.map((s) => score(query, s)));\n    }\n\n    const index = space.indexOf(query);\n    if (index === -1) {\n        return Infinity;\n    } else {\n        return index;\n    }\n}\n\nfunction colonsTrimmed(str: string): string {\n    // Trim off leading and potentially trailing `:` to correctly match the emoji data as they exist in emojibase.\n    // Notes: The regex is pinned to the start and end of the string so that we can use the lazy-capturing `*?` matcher.\n    // It needs to be lazy so that the trailing `:` is not captured in the replacement group, if it exists.\n    return str.replace(/^:(.*?):?$/, \"$1\");\n}\n\nexport default class EmojiProvider extends AutocompleteProvider {\n    public matcher: QueryMatcher<ISortedEmoji>;\n    public nameMatcher: QueryMatcher<ISortedEmoji>;\n    private readonly recentlyUsed: Emoji[];\n\n    public constructor(room: Room, renderingType?: TimelineRenderingType) {\n        super({ commandRegex: EMOJI_REGEX, renderingType });\n        this.matcher = new QueryMatcher<ISortedEmoji>(SORTED_EMOJI, {\n            keys: [],\n            funcs: [(o) => o.emoji.shortcodes.map((s) => `:${s}:`)],\n            // For matching against ascii equivalents\n            shouldMatchWordsOnly: false,\n        });\n        this.nameMatcher = new QueryMatcher(SORTED_EMOJI, {\n            keys: [\"emoji.label\"],\n            // For removing punctuation\n            shouldMatchWordsOnly: true,\n        });\n\n        this.recentlyUsed = Array.from(new Set(filterBoolean(recent.get().map(getEmojiFromUnicode))));\n    }\n\n    public async getCompletions(\n        query: string,\n        selection: ISelectionRange,\n        force?: boolean,\n        limit = -1,\n    ): Promise<ICompletion[]> {\n        if (!SettingsStore.getValue(\"MessageComposerInput.suggestEmoji\")) {\n            return []; // don't give any suggestions if the user doesn't want them\n        }\n\n        let completions: ISortedEmoji[] = [];\n        const { command, range } = this.getCurrentCommand(query, selection);\n\n        if (command && command[0].length > 2) {\n            const matchedString = command[0];\n            completions = this.matcher.match(matchedString, limit);\n\n            // Do second match with shouldMatchWordsOnly in order to match against 'name'\n            completions = completions.concat(this.nameMatcher.match(matchedString));\n\n            const sorters: ListIteratee<ISortedEmoji>[] = [];\n            // make sure that emoticons come first\n            sorters.push((c) => score(matchedString, c.emoji.emoticon || \"\"));\n\n            // then sort by score (Infinity if matchedString not in shortcode)\n            sorters.push((c) => score(matchedString, c.emoji.shortcodes[0]));\n            // then sort by max score of all shortcodes, trim off the `:`\n            const trimmedMatch = colonsTrimmed(matchedString);\n            sorters.push((c) => Math.min(...c.emoji.shortcodes.map((s) => score(trimmedMatch, s))));\n            // If the matchedString is not empty, sort by length of shortcode. Example:\n            //  matchedString = \":bookmark\"\n            //  completions = [\":bookmark:\", \":bookmark_tabs:\", ...]\n            if (matchedString.length > 1) {\n                sorters.push((c) => c.emoji.shortcodes[0].length);\n            }\n            // Finally, sort by original ordering\n            sorters.push((c) => c._orderBy);\n            completions = sortBy<ISortedEmoji>(uniq(completions), sorters);\n\n            completions = completions.slice(0, LIMIT);\n\n            // Do a second sort to place emoji matching with frequently used one on top\n            const recentlyUsedAutocomplete: ISortedEmoji[] = [];\n            this.recentlyUsed.forEach((emoji) => {\n                if (emoji.shortcodes[0].indexOf(trimmedMatch) === 0) {\n                    recentlyUsedAutocomplete.push({ emoji: emoji, _orderBy: 0 });\n                }\n            });\n\n            //if there is an exact shortcode match in the frequently used emojis, it goes before everything\n            for (let i = 0; i < recentlyUsedAutocomplete.length; i++) {\n                if (recentlyUsedAutocomplete[i].emoji.shortcodes[0] === trimmedMatch) {\n                    const exactMatchEmoji = recentlyUsedAutocomplete[i];\n                    for (let j = i; j > 0; j--) {\n                        recentlyUsedAutocomplete[j] = recentlyUsedAutocomplete[j - 1];\n                    }\n                    recentlyUsedAutocomplete[0] = exactMatchEmoji;\n                    break;\n                }\n            }\n\n            completions = recentlyUsedAutocomplete.concat(completions);\n            completions = uniqBy(completions, \"emoji\");\n\n            return completions.map((c) => ({\n                completion: c.emoji.unicode,\n                component: (\n                    <PillCompletion title={`:${c.emoji.shortcodes[0]}:`} aria-label={c.emoji.unicode}>\n                        <span>{c.emoji.unicode}</span>\n                    </PillCompletion>\n                ),\n                range: range!,\n            }));\n        }\n        return [];\n    }\n\n    public getName(): string {\n        return \"😃 \" + _t(\"common|emoji\");\n    }\n\n    public renderCompletions(completions: React.ReactNode[]): React.ReactNode {\n        return (\n            <div\n                className=\"mx_Autocomplete_Completion_container_pill\"\n                role=\"presentation\"\n                aria-label={_t(\"composer|autocomplete|emoji_a11y\")}\n            >\n                {completions}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2017-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport AutocompleteProvider from \"./AutocompleteProvider\";\nimport { _t } from \"../languageHandler\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { PillCompletion } from \"./Components\";\nimport { type ICompletion, type ISelectionRange } from \"./Autocompleter\";\nimport RoomAvatar from \"../components/views/avatars/RoomAvatar\";\nimport { type TimelineRenderingType } from \"../contexts/RoomContext\";\n\nconst AT_ROOM_REGEX = /@\\S*/g;\n\nexport default class NotifProvider extends AutocompleteProvider {\n    public constructor(\n        public room: Room,\n        renderingType?: TimelineRenderingType,\n    ) {\n        super({ commandRegex: AT_ROOM_REGEX, renderingType });\n    }\n\n    public async getCompletions(\n        query: string,\n        selection: ISelectionRange,\n        force = false,\n        limit = -1,\n    ): Promise<ICompletion[]> {\n        const client = MatrixClientPeg.safeGet();\n\n        if (!this.room.currentState.mayTriggerNotifOfType(\"room\", client.getSafeUserId())) return [];\n\n        const { command, range } = this.getCurrentCommand(query, selection, force);\n        if (\n            command?.[0] &&\n            command[0].length > 1 &&\n            [\"@room\", \"@channel\", \"@everyone\", \"@here\"].some((c) => c.startsWith(command![0]))\n        ) {\n            return [\n                {\n                    completion: \"@room\",\n                    completionId: \"@room\",\n                    type: \"at-room\",\n                    suffix: \" \",\n                    component: (\n                        <PillCompletion title=\"@room\" description={_t(\"composer|autocomplete|@room_description\")}>\n                            <RoomAvatar size=\"24px\" room={this.room} />\n                        </PillCompletion>\n                    ),\n                    range: range!,\n                },\n            ];\n        }\n        return [];\n    }\n\n    public getName(): string {\n        return \"❗️ \" + _t(\"composer|autocomplete|notification_description\");\n    }\n\n    public renderCompletions(completions: React.ReactNode[]): React.ReactNode {\n        return (\n            <div\n                className=\"mx_Autocomplete_Completion_container_pill mx_Autocomplete_Completion_container_truncate\"\n                role=\"presentation\"\n                aria-label={_t(\"composer|autocomplete|notification_a11y\")}\n            >\n                {completions}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2017-2024 New Vector Ltd.\nCopyright 2016 Aviral Dasgupta\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ReactElement, type RefAttributes, type HTMLAttributes } from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport CommandProvider from \"./CommandProvider\";\nimport RoomProvider from \"./RoomProvider\";\nimport UserProvider from \"./UserProvider\";\nimport EmojiProvider from \"./EmojiProvider\";\nimport NotifProvider from \"./NotifProvider\";\nimport { timeout } from \"../utils/promise\";\nimport { type ICommand } from \"./AutocompleteProvider\";\nimport type AutocompleteProvider from \"./AutocompleteProvider\";\nimport SpaceProvider from \"./SpaceProvider\";\nimport { TimelineRenderingType } from \"../contexts/RoomContext\";\nimport { filterBoolean } from \"../utils/arrays\";\n\nexport interface ISelectionRange {\n    beginning?: boolean; // whether the selection is in the first block of the editor or not\n    start: number; // byte offset relative to the start anchor of the current editor selection.\n    end: number; // byte offset relative to the end anchor of the current editor selection.\n}\n\nexport interface ICompletion {\n    type?: \"at-room\" | \"command\" | \"community\" | \"room\" | \"user\";\n    completion: string;\n    completionId?: string;\n    component: ReactElement<RefAttributes<HTMLElement> & HTMLAttributes<HTMLElement>>;\n    range: ISelectionRange;\n    command?: string;\n    suffix?: string;\n    // If provided, apply a LINK entity to the completion with the\n    // data = { url: href }.\n    href?: string;\n}\n\nconst PROVIDERS = [UserProvider, RoomProvider, EmojiProvider, NotifProvider, CommandProvider, SpaceProvider];\n\n// Providers will get rejected if they take longer than this.\nconst PROVIDER_COMPLETION_TIMEOUT = 3000;\n\nexport interface IProviderCompletions {\n    completions: ICompletion[];\n    provider: AutocompleteProvider;\n    command: Partial<ICommand>;\n}\n\nexport default class Autocompleter {\n    public room: Room;\n    public providers: AutocompleteProvider[];\n\n    public constructor(room: Room, renderingType: TimelineRenderingType = TimelineRenderingType.Room) {\n        this.room = room;\n        this.providers = PROVIDERS.map((Prov) => {\n            return new Prov(room, renderingType);\n        });\n    }\n\n    public destroy(): void {\n        this.providers.forEach((p) => {\n            p.destroy();\n        });\n    }\n\n    public async getCompletions(\n        query: string,\n        selection: ISelectionRange,\n        force = false,\n        limit = -1,\n    ): Promise<IProviderCompletions[]> {\n        /* Note: This intentionally waits for all providers to return,\n         otherwise, we run into a condition where new completions are displayed\n         while the user is interacting with the list, which makes it difficult\n         to predict whether an action will actually do what is intended\n        */\n        // list of results from each provider, each being a list of completions or null if it times out\n        const completionsList: Array<ICompletion[] | null> = await Promise.all(\n            this.providers.map(async (provider): Promise<ICompletion[] | null> => {\n                return timeout(\n                    provider.getCompletions(query, selection, force, limit),\n                    null,\n                    PROVIDER_COMPLETION_TIMEOUT,\n                );\n            }),\n        );\n\n        // map then filter to maintain the index for the map-operation, for this.providers to line up\n        return filterBoolean(\n            completionsList.map((completions, i) => {\n                if (!completions || !completions.length) return;\n\n                return {\n                    completions,\n                    provider: this.providers[i],\n\n                    /* the currently matched \"command\" the completer tried to complete\n                     * we pass this through so that Autocomplete can figure out when to\n                     * re-show itself once hidden.\n                     */\n                    command: this.providers[i].getCurrentCommand(query, selection, force),\n                };\n            }),\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport React from \"react\";\n\nimport { _t } from \"../languageHandler\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport RoomProvider from \"./RoomProvider\";\n\nexport default class SpaceProvider extends RoomProvider {\n    protected getRooms(): Room[] {\n        return MatrixClientPeg.safeGet()\n            .getVisibleRooms(SettingsStore.getValue(\"feature_dynamic_room_predecessors\"))\n            .filter((r) => r.isSpaceRoom());\n    }\n\n    public getName(): string {\n        return _t(\"common|spaces\");\n    }\n\n    public renderCompletions(completions: React.ReactNode[]): React.ReactNode {\n        return (\n            <div\n                className=\"mx_Autocomplete_Completion_container_pill mx_Autocomplete_Completion_container_truncate\"\n                role=\"listbox\"\n                aria-label={_t(\"composer|autocomplete|space_a11y\")}\n            >\n                {completions}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2017-2024 New Vector Ltd.\nCopyright 2016 Aviral Dasgupta\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef, type RefObject } from \"react\";\nimport classNames from \"classnames\";\nimport { flatMap } from \"lodash\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport Autocompleter, {\n    type ICompletion,\n    type ISelectionRange,\n    type IProviderCompletions,\n} from \"../../../autocomplete/Autocompleter\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport RoomContext from \"../../../contexts/RoomContext\";\n\nconst MAX_PROVIDER_MATCHES = 20;\n\nexport const generateCompletionDomId = (n: number): string => `mx_Autocomplete_Completion_${n}`;\n\ninterface IProps {\n    // the query string for which to show autocomplete suggestions\n    query: string;\n    // method invoked with range and text content when completion is confirmed\n    onConfirm: (completion: ICompletion) => void;\n    // method invoked when selected (if any) completion changes\n    onSelectionChange?: (partIndex: number) => void;\n    selection: ISelectionRange;\n    // The room in which we're autocompleting\n    room: Room;\n}\n\ninterface IState {\n    completions: IProviderCompletions[];\n    completionList: ICompletion[];\n    selectionOffset: number;\n    shouldShowCompletions: boolean;\n    hide: boolean;\n    forceComplete: boolean;\n}\n\nexport default class Autocomplete extends React.PureComponent<IProps, IState> {\n    public autocompleter?: Autocompleter;\n    public queryRequested?: string;\n    public debounceCompletionsRequest?: number;\n    private containerRef = createRef<HTMLDivElement>();\n    private completionRefs: Record<string, RefObject<HTMLElement | null>> = {};\n\n    public static contextType = RoomContext;\n    declare public context: React.ContextType<typeof RoomContext>;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            // list of completionResults, each containing completions\n            completions: [],\n\n            // array of completions, so we can look up current selection by offset quickly\n            completionList: [],\n\n            // how far down the completion list we are (THIS IS 1-INDEXED!)\n            selectionOffset: 1,\n\n            // whether we should show completions if they're available\n            shouldShowCompletions: true,\n\n            hide: false,\n\n            forceComplete: false,\n        };\n    }\n\n    public componentDidMount(): void {\n        this.autocompleter = new Autocompleter(this.props.room, this.context.timelineRenderingType);\n        this.applyNewProps();\n    }\n\n    private applyNewProps(oldQuery?: string, oldRoom?: Room): void {\n        if (oldRoom && this.props.room.roomId !== oldRoom.roomId) {\n            this.autocompleter?.destroy();\n            this.autocompleter = new Autocompleter(this.props.room);\n        }\n\n        // Query hasn't changed so don't try to complete it\n        if (oldQuery === this.props.query) {\n            return;\n        }\n\n        this.complete(this.props.query, this.props.selection);\n    }\n\n    public componentWillUnmount(): void {\n        this.autocompleter?.destroy();\n    }\n\n    private complete(query: string, selection: ISelectionRange): Promise<void> {\n        this.queryRequested = query;\n        if (this.debounceCompletionsRequest) {\n            clearTimeout(this.debounceCompletionsRequest);\n        }\n        if (query === \"\") {\n            this.setState({\n                // Clear displayed completions\n                completions: [],\n                completionList: [],\n                // Reset selected completion\n                selectionOffset: 1,\n                // Hide the autocomplete box\n                hide: true,\n            });\n            return Promise.resolve();\n        }\n        let autocompleteDelay = SettingsStore.getValue(\"autocompleteDelay\");\n\n        // Don't debounce if we are already showing completions\n        if (this.state.completions.length > 0 || this.state.forceComplete) {\n            autocompleteDelay = 0;\n        }\n\n        return new Promise((resolve) => {\n            this.debounceCompletionsRequest = window.setTimeout(() => {\n                resolve(this.processQuery(query, selection));\n            }, autocompleteDelay);\n        });\n    }\n\n    private async processQuery(query: string, selection: ISelectionRange): Promise<void> {\n        if (!this.autocompleter) return;\n        const completions = await this.autocompleter.getCompletions(\n            query,\n            selection,\n            this.state.forceComplete,\n            MAX_PROVIDER_MATCHES,\n        );\n        // Only ever process the completions for the most recent query being processed\n        if (query !== this.queryRequested) {\n            return;\n        }\n        await this.processCompletions(completions);\n    }\n\n    private async processCompletions(completions: IProviderCompletions[]): Promise<void> {\n        const completionList = flatMap(completions, (provider) => provider.completions);\n\n        // Reset selection when completion list becomes empty.\n        let selectionOffset = 1;\n        if (completionList.length > 0) {\n            /* If the currently selected completion is still in the completion list,\n             try to find it and jump to it. If not, select composer.\n             */\n            const currentSelection =\n                this.state.selectionOffset <= 1\n                    ? null\n                    : this.state.completionList[this.state.selectionOffset - 1].completion;\n            selectionOffset = completionList.findIndex((completion) => completion.completion === currentSelection);\n            if (selectionOffset === -1) {\n                selectionOffset = 1;\n            } else {\n                selectionOffset++; // selectionOffset is 1-indexed!\n            }\n        }\n\n        let hide = true;\n        // If `completion.command.command` is truthy, then a provider has matched with the query\n        const anyMatches = completions.some((completion) => !!completion.command.command);\n        if (anyMatches) {\n            hide = false;\n            if (this.props.onSelectionChange) {\n                this.props.onSelectionChange(selectionOffset - 1);\n            }\n        }\n\n        const deferred = Promise.withResolvers<void>();\n        this.setState(\n            {\n                completions,\n                completionList,\n                selectionOffset,\n                hide,\n                // Force complete is turned off each time since we can't edit the query in that case\n                forceComplete: false,\n            },\n            deferred.resolve,\n        );\n        await deferred.promise;\n    }\n\n    public hasSelection(): boolean {\n        return this.countCompletions() > 0 && this.state.selectionOffset !== 0;\n    }\n\n    public countCompletions(): number {\n        return this.state.completionList.length;\n    }\n\n    // called from MessageComposerInput\n    public moveSelection(delta: number): void {\n        const completionCount = this.countCompletions();\n        if (completionCount === 0) return; // there are no items to move the selection through\n\n        // Note: selectionOffset 0 represents the unsubstituted text, while 1 means first pill selected\n        const index = (this.state.selectionOffset + delta + completionCount - 1) % completionCount;\n        this.setSelection(1 + index);\n    }\n\n    public onEscape(e: KeyboardEvent | React.KeyboardEvent): boolean | undefined {\n        const completionCount = this.countCompletions();\n        if (completionCount === 0) {\n            // autocomplete is already empty, so don't preventDefault\n            return;\n        }\n\n        e.preventDefault();\n\n        // selectionOffset = 0, so we don't end up completing when autocomplete is hidden\n        this.hide();\n    }\n\n    private hide = (): void => {\n        this.setState({\n            hide: true,\n            selectionOffset: 1,\n            completions: [],\n            completionList: [],\n        });\n    };\n\n    public forceComplete(): Promise<number> {\n        return new Promise((resolve) => {\n            this.setState(\n                {\n                    forceComplete: true,\n                    hide: false,\n                },\n                () => {\n                    this.complete(this.props.query, this.props.selection).then(() => {\n                        resolve(this.countCompletions());\n                    });\n                },\n            );\n        });\n    }\n\n    public onConfirmCompletion = (): void => {\n        this.onCompletionClicked(this.state.selectionOffset);\n    };\n\n    private onCompletionClicked = (selectionOffset: number): boolean => {\n        const count = this.countCompletions();\n        if (count === 0 || selectionOffset < 1 || selectionOffset > count) {\n            return false;\n        }\n\n        this.props.onConfirm(this.state.completionList[selectionOffset - 1]);\n        this.hide();\n\n        return true;\n    };\n\n    private setSelection(selectionOffset: number): void {\n        this.setState({ selectionOffset, hide: false });\n        if (this.props.onSelectionChange) {\n            this.props.onSelectionChange(selectionOffset - 1);\n        }\n    }\n\n    public componentDidUpdate(prevProps: IProps): void {\n        this.applyNewProps(prevProps.query, prevProps.room);\n        // this is the selected completion, so scroll it into view if needed\n        const selectedCompletion = this.completionRefs[`completion${this.state.selectionOffset}`]?.current;\n\n        if (selectedCompletion) {\n            selectedCompletion.scrollIntoView({\n                behavior: \"auto\",\n                block: \"nearest\",\n            });\n        } else if (this.containerRef.current) {\n            this.containerRef.current.scrollTo({ top: 0 });\n        }\n    }\n\n    public render(): React.ReactNode {\n        let position = 1;\n        const renderedCompletions = this.state.completions\n            .map((completionResult, i) => {\n                const completions = completionResult.completions.map((completion, j) => {\n                    const selected = position === this.state.selectionOffset;\n                    const className = classNames(\"mx_Autocomplete_Completion\", { selected });\n                    const componentPosition = position;\n                    position++;\n\n                    const onClick = (): void => {\n                        this.onCompletionClicked(componentPosition);\n                    };\n\n                    const refId = `completion${componentPosition}`;\n                    if (!this.completionRefs[refId]) {\n                        this.completionRefs[refId] = createRef();\n                    }\n                    return React.cloneElement(completion.component, {\n                        \"key\": j,\n                        \"ref\": this.completionRefs[refId],\n                        \"id\": generateCompletionDomId(componentPosition - 1), // 0 index the completion IDs\n                        className,\n                        onClick,\n                        \"aria-selected\": selected,\n                    });\n                });\n\n                return completions.length > 0 ? (\n                    <div key={i} className=\"mx_Autocomplete_ProviderSection\" role=\"presentation\">\n                        <div className=\"mx_Autocomplete_provider_name\">{completionResult.provider.getName()}</div>\n                        {completionResult.provider.renderCompletions(completions)}\n                    </div>\n                ) : null;\n            })\n            .filter((completion) => !!completion);\n\n        return !this.state.hide && renderedCompletions.length > 0 ? (\n            <div id=\"mx_Autocomplete\" className=\"mx_Autocomplete\" ref={this.containerRef} role=\"listbox\">\n                {renderedCompletions}\n            </div>\n        ) : null;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type EditorModel from \"./model\";\nimport { type IDiff } from \"./diff\";\nimport { type SerializedPart } from \"./parts\";\nimport { type Caret } from \"./caret\";\n\nexport interface IHistory {\n    parts: SerializedPart[];\n    caret?: Caret;\n}\n\nexport const MAX_STEP_LENGTH = 10;\n\nexport default class HistoryManager {\n    private stack: IHistory[] = [];\n    private newlyTypedCharCount = 0;\n    private currentIndex = -1;\n    private changedSinceLastPush = false;\n    private lastCaret?: Caret;\n    private nonWordBoundarySinceLastPush = false;\n    private addedSinceLastPush = false;\n    private removedSinceLastPush = false;\n\n    public clear(): void {\n        this.stack = [];\n        this.newlyTypedCharCount = 0;\n        this.currentIndex = -1;\n        this.changedSinceLastPush = false;\n        this.lastCaret = undefined;\n        this.nonWordBoundarySinceLastPush = false;\n        this.addedSinceLastPush = false;\n        this.removedSinceLastPush = false;\n    }\n\n    private shouldPush(inputType?: string, diff?: IDiff): boolean {\n        // right now we can only push a step after\n        // the input has been applied to the model,\n        // so we can't push the state before something happened.\n        // not ideal but changing this would be harder to fit cleanly into\n        // the editor model.\n        const isNonBulkInput =\n            inputType === \"insertText\" || inputType === \"deleteContentForward\" || inputType === \"deleteContentBackward\";\n        if (diff && isNonBulkInput) {\n            if (diff.added) {\n                this.addedSinceLastPush = true;\n            }\n            if (diff.removed) {\n                this.removedSinceLastPush = true;\n            }\n            // as long as you've only been adding or removing since the last push\n            if (this.addedSinceLastPush !== this.removedSinceLastPush) {\n                // add steps by word boundary, up to MAX_STEP_LENGTH characters\n                const str = diff.added ? diff.added : diff.removed!;\n                const isWordBoundary = str === \" \" || str === \"\\t\" || str === \"\\n\";\n                if (this.nonWordBoundarySinceLastPush && isWordBoundary) {\n                    return true;\n                }\n                if (!isWordBoundary) {\n                    this.nonWordBoundarySinceLastPush = true;\n                }\n                this.newlyTypedCharCount += str.length;\n                return this.newlyTypedCharCount > MAX_STEP_LENGTH;\n            } else {\n                // if starting to remove while adding before, or the opposite, push\n                return true;\n            }\n        } else {\n            // bulk input (paste, ...) should be pushed every time\n            return true;\n        }\n    }\n\n    private pushState(model: EditorModel, caret?: Caret): void {\n        // remove all steps after current step\n        while (this.currentIndex < this.stack.length - 1) {\n            this.stack.pop();\n        }\n        const parts = model.serializeParts();\n        this.stack.push({ parts, caret });\n        this.currentIndex = this.stack.length - 1;\n        this.lastCaret = undefined;\n        this.changedSinceLastPush = false;\n        this.newlyTypedCharCount = 0;\n        this.nonWordBoundarySinceLastPush = false;\n        this.addedSinceLastPush = false;\n        this.removedSinceLastPush = false;\n    }\n\n    // needs to persist parts and caret position\n    public tryPush(model: EditorModel, caret?: Caret, inputType?: string, diff?: IDiff): boolean {\n        // ignore state restoration echos.\n        // these respect the inputType values of the input event,\n        // but are actually passed in from MessageEditor calling model.reset()\n        // in the keydown event handler.\n        if (inputType === \"historyUndo\" || inputType === \"historyRedo\") {\n            return false;\n        }\n        const shouldPush = this.shouldPush(inputType, diff);\n        if (shouldPush) {\n            this.pushState(model, caret);\n        } else {\n            this.lastCaret = caret;\n            this.changedSinceLastPush = true;\n        }\n        return shouldPush;\n    }\n\n    public ensureLastChangesPushed(model: EditorModel): void {\n        if (this.changedSinceLastPush && this.lastCaret) {\n            this.pushState(model, this.lastCaret);\n        }\n    }\n\n    public canUndo(): boolean {\n        return this.currentIndex >= 1 || this.changedSinceLastPush;\n    }\n\n    public canRedo(): boolean {\n        return this.currentIndex < this.stack.length - 1;\n    }\n\n    // returns state that should be applied to model\n    public undo(model: EditorModel): IHistory | void {\n        if (this.canUndo()) {\n            this.ensureLastChangesPushed(model);\n            this.currentIndex -= 1;\n            return this.stack[this.currentIndex];\n        }\n    }\n\n    // returns state that should be applied to model\n    public redo(): IHistory | void {\n        if (this.canRedo()) {\n            this.changedSinceLastPush = false;\n            this.currentIndex += 1;\n            return this.stack[this.currentIndex];\n        }\n    }\n}\n","/*\nCopyright 2019-2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { needsCaretNodeBefore, needsCaretNodeAfter } from \"./render\";\nimport Range from \"./range\";\nimport type EditorModel from \"./model\";\nimport { type IPosition } from \"./position\";\nimport type DocumentPosition from \"./position\";\nimport { type Part, Type } from \"./parts\";\n\nexport type Caret = Range | DocumentPosition;\n\nexport function setSelection(editor: HTMLDivElement, model: EditorModel, selection: Range | IPosition): void {\n    if (selection instanceof Range) {\n        setDocumentRangeSelection(editor, model, selection);\n    } else {\n        setCaretPosition(editor, model, selection);\n    }\n}\n\nfunction setDocumentRangeSelection(editor: HTMLDivElement, model: EditorModel, range: Range): void {\n    const sel = document.getSelection()!;\n    sel.removeAllRanges();\n    const selectionRange = document.createRange();\n    const start = getNodeAndOffsetForPosition(editor, model, range.start);\n    selectionRange.setStart(start.node, start.offset);\n    const end = getNodeAndOffsetForPosition(editor, model, range.end);\n    selectionRange.setEnd(end.node, end.offset);\n    sel.addRange(selectionRange);\n}\n\nexport function setCaretPosition(editor: HTMLDivElement, model: EditorModel, caretPosition: IPosition): void {\n    if (model.isEmpty) return; // selection can't possibly be wrong, so avoid a reflow\n\n    const range = document.createRange();\n    const { node, offset } = getNodeAndOffsetForPosition(editor, model, caretPosition);\n    range.setStart(node, offset);\n    range.collapse(true);\n\n    const sel = document.getSelection()!;\n    if (sel.rangeCount === 1) {\n        const existingRange = sel.getRangeAt(0);\n        if (\n            existingRange.startContainer === range.startContainer &&\n            existingRange.startOffset === range.startOffset &&\n            existingRange.collapsed === range.collapsed\n        ) {\n            // If the selection matches, it's important to leave it alone.\n            // Recreating the selection state in at least Chrome can cause\n            // strange side effects, like touch bar flickering on every key.\n            // See https://github.com/vector-im/element-web/issues/9299\n            return;\n        }\n    }\n    sel.removeAllRanges();\n    sel.addRange(range);\n}\n\nfunction getNodeAndOffsetForPosition(\n    editor: HTMLDivElement,\n    model: EditorModel,\n    position: IPosition,\n): {\n    node: Node;\n    offset: number;\n} {\n    const { offset, lineIndex, nodeIndex } = getLineAndNodePosition(model, position);\n    const lineNode = editor.childNodes[lineIndex];\n\n    let focusNode;\n    // empty line with just a <br>\n    if (nodeIndex === -1) {\n        focusNode = lineNode;\n    } else {\n        focusNode = lineNode.childNodes[nodeIndex];\n        // make sure we have a text node\n        if (focusNode.nodeType === Node.ELEMENT_NODE && focusNode.firstChild) {\n            focusNode = focusNode.firstChild;\n        }\n    }\n    return { node: focusNode, offset };\n}\n\nexport function getLineAndNodePosition(\n    model: EditorModel,\n    caretPosition: IPosition,\n): {\n    offset: number;\n    lineIndex: number;\n    nodeIndex: number;\n} {\n    const { parts } = model;\n    const partIndex = caretPosition.index;\n    let { offset } = caretPosition;\n    const lineResult = findNodeInLineForPart(parts, partIndex, offset);\n    const { lineIndex } = lineResult;\n    let { nodeIndex } = lineResult;\n    // we're at an empty line between a newline part\n    // and another newline part or end/start of parts.\n    // set offset to 0 so it gets set to the <br> inside the line container\n    if (nodeIndex === -1) {\n        offset = 0;\n    } else {\n        // move caret out of uneditable part (into caret node, or empty line br) if needed\n        ({ nodeIndex, offset } = moveOutOfUnselectablePart(parts, partIndex, nodeIndex, offset));\n    }\n    return { lineIndex, nodeIndex, offset };\n}\n\nfunction findNodeInLineForPart(\n    parts: Part[],\n    partIndex: number,\n    offset: number,\n): { lineIndex: number; nodeIndex: number } {\n    let lineIndex = 0;\n    let nodeIndex = -1;\n\n    let prevPart: Part | undefined;\n    // go through to parts up till (and including) the index\n    // to find newline parts\n    for (let i = 0; i <= partIndex; ++i) {\n        const part = parts[i];\n        if (part.type === Type.Newline) {\n            // don't jump over the linebreak if the offset is before it\n            if (i == partIndex && offset === 0) {\n                continue;\n            }\n            lineIndex += 1;\n            nodeIndex = -1;\n            prevPart = undefined;\n        } else {\n            nodeIndex += 1;\n            if (needsCaretNodeBefore(part, prevPart)) {\n                nodeIndex += 1;\n            }\n            // only jump over caret node if we're not at our destination node already,\n            // as we'll assume in moveOutOfUnselectablePart that nodeIndex\n            // refers to the node corresponding to the part,\n            // and not an adjacent caret node\n            if (i < partIndex) {\n                const nextPart = parts[i + 1];\n                const isLastOfLine = !nextPart || nextPart.type === Type.Newline;\n                if (needsCaretNodeAfter(part, isLastOfLine)) {\n                    nodeIndex += 1;\n                }\n            }\n            prevPart = part;\n        }\n    }\n\n    return { lineIndex, nodeIndex };\n}\n\nfunction moveOutOfUnselectablePart(\n    parts: Part[],\n    partIndex: number,\n    nodeIndex: number,\n    offset: number,\n): { offset: number; nodeIndex: number } {\n    // move caret before or after unselectable part\n    const part = parts[partIndex];\n    if (part && !part.acceptsCaret) {\n        if (offset === 0) {\n            nodeIndex -= 1;\n            const prevPart = parts[partIndex - 1];\n            // if the previous node is a caret node, it's empty\n            // so the offset can stay at 0\n            // only when it's not, we need to set the offset\n            // at the end of the node\n            if (!needsCaretNodeBefore(part, prevPart)) {\n                offset = prevPart.text.length;\n            }\n        } else {\n            nodeIndex += 1;\n            offset = 0;\n        }\n    }\n    return { nodeIndex, offset };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef, type JSX } from \"react\";\nimport classNames from \"classnames\";\nimport {\n    BoldIcon,\n    ItalicIcon,\n    StrikethroughIcon,\n    InlineCodeIcon,\n    QuoteIcon,\n    LinkIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { RovingAccessibleButton } from \"../../../accessibility/RovingTabIndex\";\nimport Toolbar from \"../../../accessibility/Toolbar\";\n\nexport enum Formatting {\n    Bold = \"bold\",\n    Italics = \"italics\",\n    Strikethrough = \"strikethrough\",\n    Code = \"code\",\n    Quote = \"quote\",\n    InsertLink = \"insert_link\",\n}\n\ninterface IProps {\n    shortcuts: Partial<Record<Formatting, string>>;\n    onAction(action: Formatting): void;\n}\n\ninterface IState {\n    visible: boolean;\n}\n\nexport default class MessageComposerFormatBar extends React.PureComponent<IProps, IState> {\n    private readonly formatBarRef = createRef<HTMLDivElement>();\n    /**\n     * The height of the format bar in pixels.\n     * Height 32px + 2px border\n     * @private\n     */\n    private readonly BAR_HEIGHT = 34;\n\n    public constructor(props: IProps) {\n        super(props);\n        this.state = { visible: false };\n    }\n\n    public render(): React.ReactNode {\n        const classes = classNames(\"mx_MessageComposerFormatBar\", {\n            mx_MessageComposerFormatBar_shown: this.state.visible,\n        });\n        return (\n            <Toolbar className={classes} ref={this.formatBarRef} aria-label={_t(\"composer|formatting_toolbar_label\")}>\n                <FormatButton\n                    label={_t(\"composer|format_bold\")}\n                    onClick={() => this.props.onAction(Formatting.Bold)}\n                    icon={<BoldIcon />}\n                    shortcut={this.props.shortcuts.bold}\n                    visible={this.state.visible}\n                />\n                <FormatButton\n                    label={_t(\"composer|format_italics\")}\n                    onClick={() => this.props.onAction(Formatting.Italics)}\n                    icon={<ItalicIcon />}\n                    shortcut={this.props.shortcuts.italics}\n                    visible={this.state.visible}\n                />\n                <FormatButton\n                    label={_t(\"composer|format_strikethrough\")}\n                    onClick={() => this.props.onAction(Formatting.Strikethrough)}\n                    icon={<StrikethroughIcon />}\n                    visible={this.state.visible}\n                />\n                <FormatButton\n                    label={_t(\"composer|format_code_block\")}\n                    onClick={() => this.props.onAction(Formatting.Code)}\n                    icon={<InlineCodeIcon />}\n                    shortcut={this.props.shortcuts.code}\n                    visible={this.state.visible}\n                />\n                <FormatButton\n                    label={_t(\"action|quote\")}\n                    onClick={() => this.props.onAction(Formatting.Quote)}\n                    icon={<QuoteIcon />}\n                    shortcut={this.props.shortcuts.quote}\n                    visible={this.state.visible}\n                />\n                <FormatButton\n                    label={_t(\"composer|format_insert_link\")}\n                    onClick={() => this.props.onAction(Formatting.InsertLink)}\n                    icon={<LinkIcon />}\n                    shortcut={this.props.shortcuts.insert_link}\n                    visible={this.state.visible}\n                />\n            </Toolbar>\n        );\n    }\n\n    public showAt(selectionRect: DOMRect): void {\n        if (!this.formatBarRef.current?.parentElement) return;\n\n        this.setState({ visible: true });\n        const parentRect = this.formatBarRef.current.parentElement.getBoundingClientRect();\n        this.formatBarRef.current.style.left = `${selectionRect.left - parentRect.left}px`;\n        const halfBarHeight = this.BAR_HEIGHT / 2; // used to center the bar\n        const offset = halfBarHeight + 2; // makes sure the bar won't cover selected text\n        const offsetLimit = halfBarHeight + offset;\n        const position = Math.max(selectionRect.top - parentRect.top - offsetLimit, -offsetLimit);\n        this.formatBarRef.current.style.top = `${position}px`;\n    }\n\n    public hide(): void {\n        this.setState({ visible: false });\n    }\n}\n\ninterface IFormatButtonProps {\n    label: string;\n    icon: JSX.Element;\n    shortcut?: string;\n    visible?: boolean;\n    onClick(): void;\n}\n\nclass FormatButton extends React.PureComponent<IFormatButtonProps> {\n    public render(): React.ReactNode {\n        // element=\"button\" and type=\"button\" are necessary for the buttons to work on WebKit,\n        // otherwise the text is deselected before onClick can ever be called\n        return (\n            <RovingAccessibleButton\n                element=\"button\"\n                type=\"button\"\n                onClick={this.props.onClick}\n                aria-label={this.props.label}\n                title={this.props.label}\n                caption={this.props.shortcut}\n                className=\"mx_MessageComposerFormatBar_button\"\n            >\n                {this.props.icon}\n            </RovingAccessibleButton>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type Range from \"./range\";\nimport { type Part, Type } from \"./parts\";\nimport { Formatting } from \"../components/views/rooms/MessageComposerFormatBar\";\nimport { longestBacktickSequence } from \"./deserialize\";\n\n/**\n * Some common queries and transformations on the editor model\n */\n\n/**\n * Formats a given range with a given action\n * @param {Range} range the range that should be formatted\n * @param {Formatting} action the action that should be performed on the range\n */\nexport function formatRange(range: Range, action: Formatting): void {\n    // If the selection was empty we select the current word instead\n    if (range.wasInitializedEmpty()) {\n        selectRangeOfWordAtCaret(range);\n    } else {\n        // Remove whitespace or new lines in our selection\n        range.trim();\n    }\n\n    // Edge case when just selecting whitespace or new line.\n    // There should be no reason to format whitespace, so we can just return.\n    if (range.length === 0) {\n        return;\n    }\n\n    switch (action) {\n        case Formatting.Bold:\n            toggleInlineFormat(range, \"**\");\n            break;\n        case Formatting.Italics:\n            toggleInlineFormat(range, \"*\");\n            break;\n        case Formatting.Strikethrough:\n            toggleInlineFormat(range, \"<del>\", \"</del>\");\n            break;\n        case Formatting.Code:\n            formatRangeAsCode(range);\n            break;\n        case Formatting.Quote:\n            formatRangeAsQuote(range);\n            break;\n        case Formatting.InsertLink:\n            formatRangeAsLink(range);\n            break;\n    }\n}\n\nexport function replaceRangeAndExpandSelection(range: Range, newParts: Part[]): void {\n    const { model } = range;\n    model.transform(() => {\n        const oldLen = range.length;\n        const addedLen = range.replace(newParts);\n        const firstOffset = range.start.asOffset(model);\n        const lastOffset = firstOffset.add(oldLen + addedLen);\n        return model.startRange(firstOffset.asPosition(model), lastOffset.asPosition(model));\n    });\n}\n\nexport function replaceRangeAndMoveCaret(range: Range, newParts: Part[], offset = 0, atNodeEnd = false): void {\n    const { model } = range;\n    model.transform(() => {\n        const oldLen = range.length;\n        const addedLen = range.replace(newParts);\n        const firstOffset = range.start.asOffset(model);\n        const lastOffset = firstOffset.add(oldLen + addedLen + offset, atNodeEnd);\n        return lastOffset.asPosition(model);\n    });\n}\n\n/**\n * Replaces a range with formatting or removes existing formatting and\n * positions the cursor with respect to the prefix and suffix length.\n * @param {Range} range the previous value\n * @param {Part[]} newParts the new value\n * @param {boolean} rangeHasFormatting the new value\n * @param {number} prefixLength the length of the formatting prefix\n * @param {number} suffixLength the length of the formatting suffix, defaults to prefix length\n */\nexport function replaceRangeAndAutoAdjustCaret(\n    range: Range,\n    newParts: Part[],\n    rangeHasFormatting = false,\n    prefixLength: number,\n    suffixLength = prefixLength,\n): void {\n    const { model } = range;\n    const lastStartingPosition = range.getLastStartingPosition();\n    const relativeOffset = lastStartingPosition.offset - range.start.offset;\n    const distanceFromEnd = range.length - relativeOffset;\n    // Handle edge case where the caret is located within the suffix or prefix\n    if (rangeHasFormatting) {\n        if (relativeOffset < prefixLength) {\n            // Was the caret at the left format string?\n            replaceRangeAndMoveCaret(range, newParts, -(range.length - 2 * suffixLength));\n            return;\n        }\n        if (distanceFromEnd < suffixLength) {\n            // Was the caret at the right format string?\n            replaceRangeAndMoveCaret(range, newParts, 0, true);\n            return;\n        }\n    }\n    // Calculate new position with respect to the previous position\n    model.transform(() => {\n        const offsetDirection = Math.sign(range.replace(newParts)); // Compensates for shrinkage or expansion\n        const atEnd = distanceFromEnd === suffixLength;\n        return lastStartingPosition\n            .asOffset(model)\n            .add(offsetDirection * prefixLength, atEnd)\n            .asPosition(model);\n    });\n}\n\nconst isFormattable = (_index: number, offset: number, part: Part): boolean => {\n    return part.text[offset] !== \" \" && part.type === Type.Plain;\n};\n\nexport function selectRangeOfWordAtCaret(range: Range): void {\n    // Select right side of word\n    range.expandForwardsWhile(isFormattable);\n    // Select left side of word\n    range.expandBackwardsWhile(isFormattable);\n    // Trim possibly selected new lines\n    range.trim();\n}\n\nexport function rangeStartsAtBeginningOfLine(range: Range): boolean {\n    const { model } = range;\n    const startsWithPartial = range.start.offset !== 0;\n    const isFirstPart = range.start.index === 0;\n    const previousIsNewline = !isFirstPart && model.parts[range.start.index - 1].type === Type.Newline;\n    return !startsWithPartial && (isFirstPart || previousIsNewline);\n}\n\nexport function rangeEndsAtEndOfLine(range: Range): boolean {\n    const { model } = range;\n    const lastPart = model.parts[range.end.index];\n    const endsWithPartial = range.end.offset !== lastPart.text.length;\n    const isLastPart = range.end.index === model.parts.length - 1;\n    const nextIsNewline = !isLastPart && model.parts[range.end.index + 1].type === Type.Newline;\n    return !endsWithPartial && (isLastPart || nextIsNewline);\n}\n\nexport function formatRangeAsQuote(range: Range): void {\n    const { model, parts } = range;\n    const { partCreator } = model;\n    for (let i = 0; i < parts.length; ++i) {\n        const part = parts[i];\n        if (part.type === Type.Newline) {\n            parts.splice(i + 1, 0, partCreator.plain(\"> \"));\n        }\n    }\n    parts.unshift(partCreator.plain(\"> \"));\n    if (!rangeStartsAtBeginningOfLine(range)) {\n        parts.unshift(partCreator.newline());\n    }\n    if (!rangeEndsAtEndOfLine(range)) {\n        parts.push(partCreator.newline());\n    }\n    parts.push(partCreator.newline());\n    replaceRangeAndExpandSelection(range, parts);\n}\n\nexport function formatRangeAsCode(range: Range): void {\n    const { model, parts } = range;\n    const { partCreator } = model;\n\n    const hasBlockFormatting =\n        range.length > 0 && range.text.startsWith(\"```\") && range.text.endsWith(\"```\") && range.text.includes(\"\\n\");\n\n    const needsBlockFormatting = parts.some((p) => p.type === Type.Newline);\n\n    if (hasBlockFormatting) {\n        parts.shift();\n        parts.pop();\n        if (parts[0]?.text === \"\\n\" && parts[parts.length - 1]?.text === \"\\n\") {\n            parts.shift();\n            parts.pop();\n        }\n    } else if (needsBlockFormatting) {\n        parts.unshift(partCreator.plain(\"```\"), partCreator.newline());\n        if (!rangeStartsAtBeginningOfLine(range)) {\n            parts.unshift(partCreator.newline());\n        }\n        parts.push(partCreator.newline(), partCreator.plain(\"```\"));\n        if (!rangeEndsAtEndOfLine(range)) {\n            parts.push(partCreator.newline());\n        }\n    } else {\n        const fenceLen = longestBacktickSequence(range.text);\n        const hasInlineFormatting = range.text.startsWith(\"`\") && range.text.endsWith(\"`\");\n        //if it's already formatted untoggle based on fenceLen which returns the max. num of backtick within a text else increase the fence backticks with a factor of 1.\n        toggleInlineFormat(range, \"`\".repeat(hasInlineFormatting ? fenceLen : fenceLen + 1));\n        return;\n    }\n\n    replaceRangeAndExpandSelection(range, parts);\n}\n\nexport function formatRangeAsLink(range: Range, text?: string): void {\n    const { model } = range;\n    const { partCreator } = model;\n    const linkRegex = /\\[(.*?)]\\(.*?\\)/g;\n    const isFormattedAsLink = linkRegex.test(range.text);\n    if (isFormattedAsLink) {\n        const linkDescription = range.text.replace(linkRegex, \"$1\");\n        const newParts = [partCreator.plain(linkDescription)];\n        replaceRangeAndMoveCaret(range, newParts, 0);\n    } else {\n        // We set offset to -1 here so that the caret lands between the brackets\n        replaceRangeAndMoveCaret(range, [partCreator.plain(\"[\" + range.text + \"]\" + \"(\" + (text ?? \"\") + \")\")], -1);\n    }\n}\n\n// parts helper methods\nconst isBlank = (part: Part): boolean => !part.text || !/\\S/.test(part.text);\nconst isNL = (part: Part): boolean => part.type === Type.Newline;\n\nexport function toggleInlineFormat(range: Range, prefix: string, suffix = prefix): void {\n    const { model, parts } = range;\n    const { partCreator } = model;\n\n    // compute paragraph [start, end] indexes\n    const paragraphIndexes: [number, number][] = [];\n    let startIndex = 0;\n\n    // start at i=2 because we look at i and up to two parts behind to detect paragraph breaks at their end\n    for (let i = 2; i < parts.length; i++) {\n        // paragraph breaks can be denoted in a multitude of ways,\n        // - 2 newline parts in sequence\n        // - newline part, plain(<empty or just spaces>), newline part\n\n        // bump startIndex onto the first non-blank after the paragraph ending\n        if (isBlank(parts[i - 2]) && isNL(parts[i - 1]) && !isNL(parts[i]) && !isBlank(parts[i])) {\n            startIndex = i;\n        }\n\n        // if at a paragraph break, store the indexes of the paragraph\n        if (isNL(parts[i - 1]) && isNL(parts[i])) {\n            paragraphIndexes.push([startIndex, i - 1]);\n            startIndex = i + 1;\n        } else if (isNL(parts[i - 2]) && isBlank(parts[i - 1]) && isNL(parts[i])) {\n            paragraphIndexes.push([startIndex, i - 2]);\n            startIndex = i + 1;\n        }\n    }\n\n    const lastNonEmptyPart = parts.map(isBlank).lastIndexOf(false);\n    // If we have not yet included the final paragraph then add it now\n    if (startIndex <= lastNonEmptyPart) {\n        paragraphIndexes.push([startIndex, lastNonEmptyPart + 1]);\n    }\n\n    // keep track of how many things we have inserted as an offset:=0\n    let offset = 0;\n    paragraphIndexes.forEach(([startIdx, endIdx]) => {\n        // for each paragraph apply the same rule\n        const base = startIdx + offset;\n        const index = endIdx + offset;\n\n        const isFormatted =\n            index - base > 0 && parts[base].text.startsWith(prefix) && parts[index - 1].text.endsWith(suffix);\n\n        if (isFormatted) {\n            // remove prefix and suffix formatting string\n            const partWithoutPrefix = parts[base].serialize();\n            partWithoutPrefix.text = partWithoutPrefix.text.slice(prefix.length);\n            let deserializedPart = partCreator.deserializePart(partWithoutPrefix);\n            if (deserializedPart) {\n                parts[base] = deserializedPart;\n            }\n\n            const partWithoutSuffix = parts[index - 1].serialize();\n            const suffixPartText = partWithoutSuffix.text;\n            partWithoutSuffix.text = suffixPartText.substring(0, suffixPartText.length - suffix.length);\n            deserializedPart = partCreator.deserializePart(partWithoutSuffix);\n            if (deserializedPart) {\n                parts[index - 1] = deserializedPart;\n            }\n        } else {\n            parts.splice(index, 0, partCreator.plain(suffix)); // splice in the later one first to not change offset\n            parts.splice(base, 0, partCreator.plain(prefix));\n            offset += 2; // offset index to account for the two items we just spliced in\n        }\n    });\n\n    // If the user didn't select something initially, we want to just restore\n    // the caret position instead of making a new selection.\n    if (range.wasInitializedEmpty() && prefix === suffix) {\n        // Check if we need to add a offset for a toggle or untoggle\n        const hasFormatting = range.text.startsWith(prefix) && range.text.endsWith(suffix);\n        replaceRangeAndAutoAdjustCaret(range, parts, hasFormatting, prefix.length);\n    } else {\n        replaceRangeAndExpandSelection(range, parts);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport classNames from \"classnames\";\nimport React, { type JSX, createRef, type ClipboardEvent, type SyntheticEvent } from \"react\";\nimport { type Room, type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport EMOTICON_REGEX from \"emojibase-regex/emoticon\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { EMOTICON_TO_EMOJI } from \"@matrix-org/emojibase-bindings\";\n\nimport type EditorModel from \"../../../editor/model\";\nimport HistoryManager from \"../../../editor/history\";\nimport { type Caret, setSelection } from \"../../../editor/caret\";\nimport {\n    formatRange,\n    formatRangeAsLink,\n    replaceRangeAndMoveCaret,\n    toggleInlineFormat,\n} from \"../../../editor/operations\";\nimport { getCaretOffsetAndText, getRangeForSelection } from \"../../../editor/dom\";\nimport Autocomplete, { generateCompletionDomId } from \"../rooms/Autocomplete\";\nimport { getAutoCompleteCreator, type Part, type SerializedPart, Type } from \"../../../editor/parts\";\nimport { parseEvent, parsePlainTextMessage } from \"../../../editor/deserialize\";\nimport { renderModel } from \"../../../editor/render\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { IS_MAC, Key } from \"../../../Keyboard\";\nimport { CommandCategories, CommandMap, parseCommandString } from \"../../../slash-commands/SlashCommands\";\nimport Range from \"../../../editor/range\";\nimport MessageComposerFormatBar, { Formatting } from \"./MessageComposerFormatBar\";\nimport type DocumentOffset from \"../../../editor/offset\";\nimport { type IDiff } from \"../../../editor/diff\";\nimport type AutocompleteWrapperModel from \"../../../editor/autocomplete\";\nimport type DocumentPosition from \"../../../editor/position\";\nimport { type ICompletion } from \"../../../autocomplete/Autocompleter\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { ALTERNATE_KEY_NAME, KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { _t } from \"../../../languageHandler\";\nimport { linkify } from \"../../../linkify-matrix\";\nimport { SdkContextClass } from \"../../../contexts/SDKContext\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { Landmark, LandmarkNavigation } from \"../../../accessibility/LandmarkNavigation\";\n\n// matches emoticons which follow the start of a line or whitespace\nconst REGEX_EMOTICON_WHITESPACE = new RegExp(\"(?:^|\\\\s)(\" + EMOTICON_REGEX.source + \")\\\\s|:^$\");\nexport const REGEX_EMOTICON = new RegExp(\"(?:^|\\\\s)(\" + EMOTICON_REGEX.source + \")$\");\n\nconst SURROUND_WITH_CHARACTERS = ['\"', \"_\", \"`\", \"'\", \"*\", \"~\", \"$\"];\nconst SURROUND_WITH_DOUBLE_CHARACTERS = new Map([\n    [\"(\", \")\"],\n    [\"[\", \"]\"],\n    [\"{\", \"}\"],\n    [\"<\", \">\"],\n]);\n\nfunction ctrlShortcutLabel(key: string, needsShift = false, needsAlt = false): string {\n    return (\n        (IS_MAC ? \"⌘\" : _t(ALTERNATE_KEY_NAME[Key.CONTROL])) +\n        (needsShift ? \"+\" + _t(ALTERNATE_KEY_NAME[Key.SHIFT]) : \"\") +\n        (needsAlt ? \"+\" + _t(ALTERNATE_KEY_NAME[Key.ALT]) : \"\") +\n        \"+\" +\n        key\n    );\n}\n\nfunction cloneSelection(selection: Selection): Partial<Selection> {\n    return {\n        anchorNode: selection.anchorNode,\n        anchorOffset: selection.anchorOffset,\n        focusNode: selection.focusNode,\n        focusOffset: selection.focusOffset,\n        isCollapsed: selection.isCollapsed,\n        rangeCount: selection.rangeCount,\n        type: selection.type,\n    };\n}\n\nfunction selectionEquals(a: Partial<Selection>, b: Selection): boolean {\n    return (\n        a.anchorNode === b.anchorNode &&\n        a.anchorOffset === b.anchorOffset &&\n        a.focusNode === b.focusNode &&\n        a.focusOffset === b.focusOffset &&\n        a.isCollapsed === b.isCollapsed &&\n        a.rangeCount === b.rangeCount &&\n        a.type === b.type\n    );\n}\n\ninterface IProps {\n    model: EditorModel;\n    room: Room;\n    threadId?: string;\n    placeholder?: string;\n    label?: string;\n    initialCaret?: DocumentOffset;\n    disabled?: boolean;\n\n    onChange?(selection?: Caret, inputType?: string, diff?: IDiff): void;\n    onPaste?(event: Event | SyntheticEvent, data: DataTransfer, model: EditorModel): boolean;\n}\n\ninterface IState {\n    useMarkdown: boolean;\n    showPillAvatar: boolean;\n    query?: string;\n    showVisualBell?: boolean;\n    autoComplete?: AutocompleteWrapperModel;\n    completionIndex?: number;\n    surroundWith: boolean;\n}\n\nexport default class BasicMessageEditor extends React.Component<IProps, IState> {\n    public readonly editorRef = createRef<HTMLDivElement>();\n    private autocompleteRef = createRef<Autocomplete>();\n    private formatBarRef = createRef<MessageComposerFormatBar>();\n\n    private modifiedFlag = false;\n    private isIMEComposing = false;\n    private hasTextSelected = false;\n    private readonly isSafari: boolean;\n\n    private _isCaretAtEnd = false;\n    private lastCaret!: DocumentOffset;\n    private lastSelection: ReturnType<typeof cloneSelection> | null = null;\n\n    private useMarkdownHandle?: string;\n    private emoticonSettingHandle?: string;\n    private shouldShowPillAvatarSettingHandle?: string;\n    private surroundWithHandle?: string;\n    private readonly historyManager = new HistoryManager();\n\n    public constructor(props: IProps) {\n        super(props);\n        this.state = {\n            showPillAvatar: SettingsStore.getValue(\"Pill.shouldShowPillAvatar\"),\n            useMarkdown: SettingsStore.getValue(\"MessageComposerInput.useMarkdown\"),\n            surroundWith: SettingsStore.getValue(\"MessageComposerInput.surroundWith\"),\n            showVisualBell: false,\n        };\n\n        const ua = navigator.userAgent.toLowerCase();\n        this.isSafari = ua.includes(\"safari/\") && !ua.includes(\"chrome/\");\n        this.configureEmoticonAutoReplace();\n    }\n\n    public componentDidUpdate(prevProps: IProps): void {\n        // We need to re-check the placeholder when the enabled state changes because it causes the\n        // placeholder element to remount, which gets rid of the `::before` class. Re-evaluating the\n        // placeholder means we get a proper `::before` with the placeholder.\n        const enabledChange = this.props.disabled !== prevProps.disabled;\n        const placeholderChanged = this.props.placeholder !== prevProps.placeholder;\n        if (this.props.placeholder && (placeholderChanged || enabledChange)) {\n            const { isEmpty } = this.props.model;\n            if (isEmpty) {\n                this.showPlaceholder();\n            } else {\n                this.hidePlaceholder();\n            }\n        }\n    }\n\n    public replaceEmoticon(caretPosition: DocumentPosition, regex: RegExp): number | undefined {\n        const { model } = this.props;\n        const range = model.startRange(caretPosition);\n        // expand range max 9 characters backwards from caretPosition,\n        // as a space to look for an emoticon\n        let n = 9;\n        range.expandBackwardsWhile((index, offset) => {\n            const part = model.parts[index];\n            n -= 1;\n            return n >= 0 && [Type.Plain, Type.PillCandidate, Type.Newline].includes(part.type);\n        });\n        const emoticonMatch = regex.exec(range.text);\n        // ignore matches at start of proper substrings\n        // so xd will not match if the string was \"mixd 123456\"\n        // and we are lookinh at xd 123456 part of the string\n        if (emoticonMatch && (n >= 0 || emoticonMatch.index !== 0)) {\n            const query = emoticonMatch[1];\n            // variations of plaintext emoitcons(E.g. :P vs :p vs :-P) are handled upstream by the emojibase-bindings library\n            const data = EMOTICON_TO_EMOJI.get(query);\n\n            if (data) {\n                const { partCreator } = model;\n                const firstMatch = emoticonMatch[0];\n                const moveStart = firstMatch[0] === \" \" ? 1 : 0;\n\n                // we need the range to only comprise of the emoticon\n                // because we'll replace the whole range with an emoji,\n                // so move the start forward to the start of the emoticon.\n                // Take + 1 because index is reported without the possible preceding space.\n                range.moveStartForwards(emoticonMatch.index + moveStart);\n                // If the end is a trailing space/newline move end backwards, so that we don't replace it\n                if ([\"\\n\", \" \"].includes(firstMatch[firstMatch.length - 1])) {\n                    range.moveEndBackwards(1);\n                }\n\n                // this returns the amount of added/removed characters during the replace\n                // so the caret position can be adjusted.\n                return range.replace([partCreator.emoji(data.unicode)]);\n            }\n        }\n    }\n\n    private updateEditorState = (selection?: Caret, inputType?: string, diff?: IDiff): void => {\n        if (!this.editorRef.current) return;\n        renderModel(this.editorRef.current, this.props.model);\n        if (selection) {\n            // set the caret/selection\n            try {\n                setSelection(this.editorRef.current, this.props.model, selection);\n            } catch (err) {\n                logger.error(err);\n            }\n            // if caret selection is a range, take the end position\n            const position = selection instanceof Range ? selection.end : selection;\n            this.setLastCaretFromPosition(position);\n        }\n        const { isEmpty } = this.props.model;\n        if (this.props.placeholder) {\n            if (isEmpty) {\n                this.showPlaceholder();\n            } else {\n                this.hidePlaceholder();\n            }\n        }\n        if (isEmpty) {\n            this.formatBarRef.current?.hide();\n        }\n        this.setState({\n            autoComplete: this.props.model.autoComplete ?? undefined,\n            // if a change is happening then clear the showVisualBell\n            showVisualBell: diff ? false : this.state.showVisualBell,\n        });\n        this.historyManager.tryPush(this.props.model, selection, inputType, diff);\n\n        // inputType is falsy during initial mount, don't consider re-loading the draft as typing\n        let isTyping = !this.props.model.isEmpty && !!inputType;\n        // If the user is entering a command, only consider them typing if it is one which sends a message into the room\n        if (isTyping && this.props.model.parts[0].type === \"command\") {\n            const { cmd } = parseCommandString(this.props.model.parts[0].text);\n            const command = CommandMap.get(cmd!);\n            if (\n                !command?.isEnabled(MatrixClientPeg.get(), this.props.room.roomId) ||\n                command.category !== CommandCategories.messages\n            ) {\n                isTyping = false;\n            }\n        }\n        SdkContextClass.instance.typingStore.setSelfTyping(\n            this.props.room.roomId,\n            this.props.threadId ?? null,\n            isTyping,\n        );\n\n        this.props.onChange?.(selection, inputType, diff);\n    };\n\n    private showPlaceholder(): void {\n        this.editorRef.current?.style.setProperty(\"--placeholder\", `'${CSS.escape(this.props.placeholder ?? \"\")}'`);\n        this.editorRef.current?.classList.add(\"mx_BasicMessageComposer_inputEmpty\");\n    }\n\n    private hidePlaceholder(): void {\n        this.editorRef.current?.classList.remove(\"mx_BasicMessageComposer_inputEmpty\");\n        this.editorRef.current?.style.removeProperty(\"--placeholder\");\n    }\n\n    private onCompositionStart = (): void => {\n        this.isIMEComposing = true;\n        // even if the model is empty, the composition text shouldn't be mixed with the placeholder\n        this.hidePlaceholder();\n    };\n\n    private onCompositionEnd = (): void => {\n        this.isIMEComposing = false;\n        // some browsers (Chrome) don't fire an input event after ending a composition,\n        // so trigger a model update after the composition is done by calling the input handler.\n\n        // however, modifying the DOM (caused by the editor model update) from the compositionend handler seems\n        // to confuse the IME in Chrome, likely causing https://github.com/vector-im/element-web/issues/10913 ,\n        // so we do it async\n\n        // however, doing this async seems to break things in Safari for some reason, so browser sniff.\n\n        if (this.isSafari) {\n            this.onInput({ inputType: \"insertCompositionText\" });\n        } else {\n            Promise.resolve().then(() => {\n                this.onInput({ inputType: \"insertCompositionText\" });\n            });\n        }\n    };\n\n    public isComposing(event: React.KeyboardEvent): boolean {\n        // checking the event.isComposing flag just in case any browser out there\n        // emits events related to the composition after compositionend\n        // has been fired\n\n        // From https://www.stum.de/2016/06/24/handling-ime-events-in-javascript/\n        // Safari emits an additional keyDown after compositionend\n        return !!(this.isIMEComposing || (event.nativeEvent && event.nativeEvent.isComposing));\n    }\n\n    private onCutCopy = (event: ClipboardEvent, type: string): void => {\n        const selection = document.getSelection()!;\n        const text = selection.toString();\n        if (text && this.editorRef.current) {\n            const { model } = this.props;\n            const range = getRangeForSelection(this.editorRef.current, model, selection);\n            const selectedParts = range.parts.map((p) => p.serialize());\n            event.clipboardData.setData(\"application/x-element-composer\", JSON.stringify(selectedParts));\n            event.clipboardData.setData(\"text/plain\", text); // so plain copy/paste works\n            if (type === \"cut\") {\n                // Remove the text, updating the model as appropriate\n                this.modifiedFlag = true;\n                replaceRangeAndMoveCaret(range, []);\n            }\n            event.preventDefault();\n        }\n    };\n\n    private onCopy = (event: ClipboardEvent): void => {\n        this.onCutCopy(event, \"copy\");\n    };\n\n    private onCut = (event: ClipboardEvent): void => {\n        this.onCutCopy(event, \"cut\");\n    };\n\n    private onPasteHandler = (event: Event | SyntheticEvent, data: DataTransfer): boolean | undefined => {\n        event.preventDefault(); // we always handle the paste ourselves\n        if (!this.editorRef.current) return;\n        if (this.props.onPaste?.(event, data, this.props.model)) {\n            // to prevent double handling, allow props.onPaste to skip internal onPaste\n            return true;\n        }\n\n        const { model } = this.props;\n        const { partCreator } = model;\n        const plainText = data.getData(\"text/plain\");\n        const partsText = data.getData(\"application/x-element-composer\");\n\n        let parts: Part[];\n        if (partsText) {\n            const serializedTextParts = JSON.parse(partsText);\n            parts = serializedTextParts.map((p: SerializedPart) => partCreator.deserializePart(p));\n        } else {\n            parts = parsePlainTextMessage(plainText, partCreator, { shouldEscape: false });\n        }\n\n        this.modifiedFlag = true;\n        const range = getRangeForSelection(this.editorRef.current, model, document.getSelection()!);\n\n        // If the user is pasting a link, and has a range selected which is not a link, wrap the range with the link\n        if (plainText && range.length > 0 && linkify.test(plainText) && !linkify.test(range.text)) {\n            formatRangeAsLink(range, plainText);\n        } else {\n            replaceRangeAndMoveCaret(range, parts);\n        }\n    };\n\n    private onPaste = (event: ClipboardEvent<HTMLDivElement>): boolean | undefined => {\n        return this.onPasteHandler(event, event.clipboardData);\n    };\n\n    private onBeforeInput = (event: InputEvent): void => {\n        // ignore any input while doing IME compositions\n        if (this.isIMEComposing) {\n            return;\n        }\n\n        if (event.inputType === \"insertFromPaste\" && event.dataTransfer) {\n            this.onPasteHandler(event, event.dataTransfer);\n        }\n    };\n\n    private onInput = (event: Partial<InputEvent>): void => {\n        if (!this.editorRef.current) return;\n        // ignore any input while doing IME compositions\n        if (this.isIMEComposing) {\n            return;\n        }\n        this.modifiedFlag = true;\n        const sel = document.getSelection()!;\n        const { caret, text } = getCaretOffsetAndText(this.editorRef.current, sel);\n        this.props.model.update(text, event.inputType, caret);\n    };\n\n    private insertText(textToInsert: string, inputType = \"insertText\"): void {\n        if (!this.editorRef.current) return;\n        const sel = document.getSelection()!;\n        const { caret, text } = getCaretOffsetAndText(this.editorRef.current, sel);\n        const newText = text.slice(0, caret.offset) + textToInsert + text.slice(caret.offset);\n        caret.offset += textToInsert.length;\n        this.modifiedFlag = true;\n        this.props.model.update(newText, inputType, caret);\n    }\n\n    // this is used later to see if we need to recalculate the caret\n    // on selectionchange. If it is just a consequence of typing\n    // we don't need to. But if the user is navigating the caret without input\n    // we need to recalculate it, to be able to know where to insert content after\n    // losing focus\n    private setLastCaretFromPosition(position: DocumentPosition): void {\n        const { model } = this.props;\n        this._isCaretAtEnd = position.isAtEnd(model);\n        this.lastCaret = position.asOffset(model);\n        this.lastSelection = cloneSelection(document.getSelection()!);\n    }\n\n    private refreshLastCaretIfNeeded(): DocumentOffset | undefined {\n        // XXX: needed when going up and down in editing messages ... not sure why yet\n        // because the editors should stop doing this when when blurred ...\n        // maybe it's on focus and the _editorRef isn't available yet or something.\n        if (!this.editorRef.current) {\n            return;\n        }\n        const selection = document.getSelection()!;\n        if (!this.lastSelection || !selectionEquals(this.lastSelection, selection)) {\n            this.lastSelection = cloneSelection(selection);\n            const { caret, text } = getCaretOffsetAndText(this.editorRef.current, selection);\n            this.lastCaret = caret;\n            this._isCaretAtEnd = caret.offset === text.length;\n        }\n        return this.lastCaret;\n    }\n\n    public clearUndoHistory(): void {\n        this.historyManager.clear();\n    }\n\n    public getCaret(): DocumentOffset {\n        return this.lastCaret;\n    }\n\n    public isSelectionCollapsed(): boolean {\n        return !this.lastSelection || !!this.lastSelection.isCollapsed;\n    }\n\n    public isCaretAtStart(): boolean {\n        return this.getCaret().offset === 0;\n    }\n\n    public isCaretAtEnd(): boolean {\n        return this._isCaretAtEnd;\n    }\n\n    private onBlur = (): void => {\n        document.removeEventListener(\"selectionchange\", this.onSelectionChange);\n    };\n\n    private onFocus = (): void => {\n        document.addEventListener(\"selectionchange\", this.onSelectionChange);\n        // force to recalculate\n        this.lastSelection = null;\n        this.refreshLastCaretIfNeeded();\n    };\n\n    private onSelectionChange = (): void => {\n        if (!this.editorRef.current) return;\n        const { isEmpty } = this.props.model;\n\n        this.refreshLastCaretIfNeeded();\n        const selection = document.getSelection()!;\n        if (this.hasTextSelected && selection.isCollapsed) {\n            this.hasTextSelected = false;\n            this.formatBarRef.current?.hide();\n        } else if (!selection.isCollapsed && !isEmpty) {\n            this.hasTextSelected = true;\n            const range = getRangeForSelection(this.editorRef.current, this.props.model, selection);\n            if (this.formatBarRef.current && this.state.useMarkdown && !!range.text.trim()) {\n                const selectionRect = selection.getRangeAt(0).getBoundingClientRect();\n                this.formatBarRef.current.showAt(selectionRect);\n            }\n        }\n    };\n\n    private onKeyDown = (event: React.KeyboardEvent): void => {\n        if (!this.editorRef.current) return;\n        // Ignore any keypress while doing IME compositions to prevent cursor position issues\n        // This matches the behavior in SendMessageComposer and EditMessageComposer\n        if (this.isComposing(event)) {\n            return;\n        }\n        if (this.isSafari && event.which == 229) {\n            // Swallow the extra keyDown by Safari\n            event.stopPropagation();\n            return;\n        }\n        const model = this.props.model;\n        let handled = false;\n\n        if (this.state.surroundWith && document.getSelection()!.type !== \"Caret\") {\n            // This surrounds the selected text with a character. This is\n            // intentionally left out of the keybinding manager as the keybinds\n            // here shouldn't be changeable\n\n            const selectionRange = getRangeForSelection(\n                this.editorRef.current,\n                this.props.model,\n                document.getSelection()!,\n            );\n            // trim the range as we want it to exclude leading/trailing spaces\n            selectionRange.trim();\n\n            if ([...SURROUND_WITH_DOUBLE_CHARACTERS.keys(), ...SURROUND_WITH_CHARACTERS].includes(event.key)) {\n                this.historyManager.ensureLastChangesPushed(this.props.model);\n                this.modifiedFlag = true;\n                toggleInlineFormat(selectionRange, event.key, SURROUND_WITH_DOUBLE_CHARACTERS.get(event.key));\n                handled = true;\n            }\n        }\n\n        const navAction = getKeyBindingsManager().getNavigationAction(event);\n\n        if (navAction === KeyBindingAction.NextLandmark || navAction === KeyBindingAction.PreviousLandmark) {\n            LandmarkNavigation.findAndFocusNextLandmark(\n                Landmark.MESSAGE_COMPOSER_OR_HOME,\n                navAction === KeyBindingAction.PreviousLandmark,\n            );\n            handled = true;\n        }\n\n        const autocompleteAction = getKeyBindingsManager().getAutocompleteAction(event);\n        const accessibilityAction = getKeyBindingsManager().getAccessibilityAction(event);\n        if (model.autoComplete?.hasCompletions()) {\n            const autoComplete = model.autoComplete;\n            switch (autocompleteAction) {\n                case KeyBindingAction.ForceCompleteAutocomplete:\n                case KeyBindingAction.CompleteAutocomplete:\n                    this.historyManager.ensureLastChangesPushed(this.props.model);\n                    this.modifiedFlag = true;\n                    autoComplete.confirmCompletion();\n                    handled = true;\n                    break;\n                case KeyBindingAction.PrevSelectionInAutocomplete:\n                    autoComplete.selectPreviousSelection();\n                    handled = true;\n                    break;\n                case KeyBindingAction.NextSelectionInAutocomplete:\n                    autoComplete.selectNextSelection();\n                    handled = true;\n                    break;\n                case KeyBindingAction.CancelAutocomplete:\n                    autoComplete.onEscape(event);\n                    handled = true;\n                    break;\n            }\n        } else if (autocompleteAction === KeyBindingAction.ForceCompleteAutocomplete && !this.state.showVisualBell) {\n            // there is no current autocomplete window, try to open it\n            this.tabCompleteName();\n            handled = true;\n        } else if ([KeyBindingAction.Delete, KeyBindingAction.Backspace].includes(accessibilityAction!)) {\n            this.formatBarRef.current?.hide();\n        }\n\n        if (handled) {\n            event.preventDefault();\n            event.stopPropagation();\n            return;\n        }\n\n        const action = getKeyBindingsManager().getMessageComposerAction(event);\n        switch (action) {\n            case KeyBindingAction.FormatBold:\n                this.onFormatAction(Formatting.Bold);\n                handled = true;\n                break;\n            case KeyBindingAction.FormatItalics:\n                this.onFormatAction(Formatting.Italics);\n                handled = true;\n                break;\n            case KeyBindingAction.FormatCode:\n                this.onFormatAction(Formatting.Code);\n                handled = true;\n                break;\n            case KeyBindingAction.FormatQuote:\n                this.onFormatAction(Formatting.Quote);\n                handled = true;\n                break;\n            case KeyBindingAction.FormatLink:\n                this.onFormatAction(Formatting.InsertLink);\n                handled = true;\n                break;\n            case KeyBindingAction.EditRedo: {\n                const history = this.historyManager.redo();\n                if (history) {\n                    const { parts, caret } = history;\n                    // pass matching inputType so historyManager doesn't push echo\n                    // when invoked from rerender callback.\n                    model.reset(parts, caret, \"historyRedo\");\n                }\n                handled = true;\n                break;\n            }\n            case KeyBindingAction.EditUndo: {\n                const history = this.historyManager.undo(this.props.model);\n                if (history) {\n                    const { parts, caret } = history;\n                    // pass matching inputType so historyManager doesn't push echo\n                    // when invoked from rerender callback.\n                    model.reset(parts, caret, \"historyUndo\");\n                }\n                handled = true;\n                break;\n            }\n            case KeyBindingAction.NewLine:\n                this.insertText(\"\\n\");\n                handled = true;\n                break;\n            case KeyBindingAction.MoveCursorToStart:\n                setSelection(this.editorRef.current, model, {\n                    index: 0,\n                    offset: 0,\n                });\n                handled = true;\n                break;\n            case KeyBindingAction.MoveCursorToEnd:\n                setSelection(this.editorRef.current, model, {\n                    index: model.parts.length - 1,\n                    offset: model.parts[model.parts.length - 1].text.length,\n                });\n                handled = true;\n                break;\n        }\n        if (handled) {\n            event.preventDefault();\n            event.stopPropagation();\n        }\n    };\n\n    private async tabCompleteName(): Promise<void> {\n        try {\n            await new Promise<void>((resolve) => this.setState({ showVisualBell: false }, resolve));\n            const { model } = this.props;\n            const caret = this.getCaret();\n            const position = model.positionForOffset(caret.offset, caret.atNodeEnd);\n            const range = model.startRange(position);\n            range.expandBackwardsWhile((index, offset, part) => {\n                return (\n                    part.text[offset] !== \" \" &&\n                    part.text[offset] !== \"+\" &&\n                    (part.type === Type.Plain || part.type === Type.PillCandidate || part.type === Type.Command)\n                );\n            });\n            const { partCreator } = model;\n            // await for auto-complete to be open\n            await model.transform(() => {\n                const addedLen = range.replace([partCreator.pillCandidate(range.text)]);\n                return model.positionForOffset(caret.offset + addedLen, true);\n            });\n\n            // Don't try to do things with the autocomplete if there is none shown\n            if (model.autoComplete) {\n                await model.autoComplete.startSelection();\n                if (!model.autoComplete.hasSelection()) {\n                    this.setState({ showVisualBell: true });\n                    model.autoComplete.close();\n                }\n            } else {\n                this.setState({ showVisualBell: true });\n            }\n        } catch (err) {\n            logger.error(err);\n        }\n    }\n\n    public isModified(): boolean {\n        return this.modifiedFlag;\n    }\n\n    private onAutoCompleteConfirm = (completion: ICompletion): void => {\n        this.modifiedFlag = true;\n        this.props.model.autoComplete?.onComponentConfirm(completion);\n    };\n\n    private onAutoCompleteSelectionChange = (completionIndex: number): void => {\n        this.modifiedFlag = true;\n        this.setState({ completionIndex });\n    };\n\n    private configureUseMarkdown = (): void => {\n        const useMarkdown = SettingsStore.getValue(\"MessageComposerInput.useMarkdown\");\n        this.setState({ useMarkdown });\n        if (!useMarkdown && this.formatBarRef.current) {\n            this.formatBarRef.current.hide();\n        }\n    };\n\n    private configureEmoticonAutoReplace = (): void => {\n        this.props.model.setTransformCallback(this.transform);\n    };\n\n    private configureShouldShowPillAvatar = (): void => {\n        const showPillAvatar = SettingsStore.getValue(\"Pill.shouldShowPillAvatar\");\n        this.setState({ showPillAvatar });\n    };\n\n    private surroundWithSettingChanged = (): void => {\n        const surroundWith = SettingsStore.getValue(\"MessageComposerInput.surroundWith\");\n        this.setState({ surroundWith });\n    };\n\n    private transform = (documentPosition: DocumentPosition): void => {\n        const shouldReplace = SettingsStore.getValue(\"MessageComposerInput.autoReplaceEmoji\");\n        if (shouldReplace) this.replaceEmoticon(documentPosition, REGEX_EMOTICON_WHITESPACE);\n    };\n\n    public componentWillUnmount(): void {\n        document.removeEventListener(\"selectionchange\", this.onSelectionChange);\n        this.editorRef.current?.removeEventListener(\"beforeinput\", this.onBeforeInput, true);\n        this.editorRef.current?.removeEventListener(\"input\", this.onInput, true);\n        this.editorRef.current?.removeEventListener(\"compositionstart\", this.onCompositionStart, true);\n        this.editorRef.current?.removeEventListener(\"compositionend\", this.onCompositionEnd, true);\n        SettingsStore.unwatchSetting(this.useMarkdownHandle);\n        SettingsStore.unwatchSetting(this.emoticonSettingHandle);\n        SettingsStore.unwatchSetting(this.shouldShowPillAvatarSettingHandle);\n        SettingsStore.unwatchSetting(this.surroundWithHandle);\n    }\n\n    public componentDidMount(): void {\n        this.useMarkdownHandle = SettingsStore.watchSetting(\n            \"MessageComposerInput.useMarkdown\",\n            null,\n            this.configureUseMarkdown,\n        );\n        this.emoticonSettingHandle = SettingsStore.watchSetting(\n            \"MessageComposerInput.autoReplaceEmoji\",\n            null,\n            this.configureEmoticonAutoReplace,\n        );\n        this.shouldShowPillAvatarSettingHandle = SettingsStore.watchSetting(\n            \"Pill.shouldShowPillAvatar\",\n            null,\n            this.configureShouldShowPillAvatar,\n        );\n        this.surroundWithHandle = SettingsStore.watchSetting(\n            \"MessageComposerInput.surroundWith\",\n            null,\n            this.surroundWithSettingChanged,\n        );\n\n        const model = this.props.model;\n        model.setUpdateCallback(this.updateEditorState);\n        const partCreator = model.partCreator;\n        // TODO: does this allow us to get rid of EditorStateTransfer?\n        // not really, but we could not serialize the parts, and just change the autoCompleter\n        partCreator.setAutoCompleteCreator(\n            getAutoCompleteCreator(\n                () => this.autocompleteRef.current,\n                (query) => new Promise((resolve) => this.setState({ query }, resolve)),\n            ),\n        );\n        // initial render of model\n        this.updateEditorState(this.getInitialCaretPosition());\n        // attach input listener by hand so React doesn't proxy the events,\n        // as the proxied event doesn't support inputType, which we need.\n        this.editorRef.current?.addEventListener(\"beforeinput\", this.onBeforeInput, true);\n        this.editorRef.current?.addEventListener(\"input\", this.onInput, true);\n        this.editorRef.current?.addEventListener(\"compositionstart\", this.onCompositionStart, true);\n        this.editorRef.current?.addEventListener(\"compositionend\", this.onCompositionEnd, true);\n        this.editorRef.current?.focus();\n    }\n\n    private getInitialCaretPosition(): DocumentPosition {\n        let caretPosition: DocumentPosition;\n        if (this.props.initialCaret) {\n            // if restoring state from a previous editor,\n            // restore caret position from the state\n            const caret = this.props.initialCaret;\n            caretPosition = this.props.model.positionForOffset(caret.offset, caret.atNodeEnd);\n        } else {\n            // otherwise, set it at the end\n            caretPosition = this.props.model.getPositionAtEnd();\n        }\n        return caretPosition;\n    }\n\n    public onFormatAction = (action: Formatting): void => {\n        if (!this.state.useMarkdown || !this.editorRef.current) {\n            return;\n        }\n\n        const range: Range = getRangeForSelection(this.editorRef.current, this.props.model, document.getSelection()!);\n\n        this.historyManager.ensureLastChangesPushed(this.props.model);\n        this.modifiedFlag = true;\n\n        formatRange(range, action);\n    };\n\n    public render(): React.ReactNode {\n        let autoComplete: JSX.Element | undefined;\n        if (this.state.autoComplete && this.state.query) {\n            const query = this.state.query;\n            const queryLen = query.length;\n            autoComplete = (\n                <div className=\"mx_BasicMessageComposer_AutoCompleteWrapper\">\n                    <Autocomplete\n                        ref={this.autocompleteRef}\n                        query={query}\n                        onConfirm={this.onAutoCompleteConfirm}\n                        onSelectionChange={this.onAutoCompleteSelectionChange}\n                        selection={{ beginning: true, end: queryLen, start: queryLen }}\n                        room={this.props.room}\n                    />\n                </div>\n            );\n        }\n        const wrapperClasses = classNames(\"mx_BasicMessageComposer\", {\n            mx_BasicMessageComposer_input_error: this.state.showVisualBell,\n        });\n        const classes = classNames(\"mx_BasicMessageComposer_input\", {\n            mx_BasicMessageComposer_input_shouldShowPillAvatar: this.state.showPillAvatar,\n            mx_BasicMessageComposer_input_disabled: this.props.disabled,\n        });\n\n        const shortcuts = {\n            [Formatting.Bold]: ctrlShortcutLabel(\"B\"),\n            [Formatting.Italics]: ctrlShortcutLabel(\"I\"),\n            [Formatting.Code]: ctrlShortcutLabel(\"E\"),\n            [Formatting.Quote]: ctrlShortcutLabel(\">\", true),\n            [Formatting.InsertLink]: ctrlShortcutLabel(\"L\", true),\n        };\n\n        const { completionIndex } = this.state;\n        const hasAutocomplete = !!this.state.autoComplete;\n        let activeDescendant: string | undefined;\n        if (hasAutocomplete && completionIndex! >= 0) {\n            activeDescendant = generateCompletionDomId(completionIndex!);\n        }\n\n        return (\n            <div className={wrapperClasses}>\n                {autoComplete}\n                <MessageComposerFormatBar\n                    ref={this.formatBarRef}\n                    onAction={this.onFormatAction}\n                    shortcuts={shortcuts}\n                />\n                <div\n                    className={classes}\n                    contentEditable={this.props.disabled ? undefined : true}\n                    tabIndex={0}\n                    onBlur={this.onBlur}\n                    onFocus={this.onFocus}\n                    onCopy={this.onCopy}\n                    onCut={this.onCut}\n                    onPaste={this.onPaste}\n                    onKeyDown={this.onKeyDown}\n                    ref={this.editorRef}\n                    aria-label={this.props.label}\n                    role=\"textbox\"\n                    aria-multiline=\"true\"\n                    aria-autocomplete=\"list\"\n                    aria-haspopup=\"listbox\"\n                    aria-expanded={hasAutocomplete ? !this.autocompleteRef.current?.state.hide : undefined}\n                    aria-owns={hasAutocomplete ? \"mx_Autocomplete\" : undefined}\n                    aria-activedescendant={activeDescendant}\n                    dir=\"auto\"\n                    aria-disabled={this.props.disabled}\n                    data-testid=\"basicmessagecomposer\"\n                    translate=\"no\"\n                />\n            </div>\n        );\n    }\n\n    public focus(): void {\n        this.editorRef.current?.focus();\n    }\n\n    public insertMention(userId: string): void {\n        this.modifiedFlag = true;\n        const { model } = this.props;\n        const { partCreator } = model;\n        const member = this.props.room.getMember(userId);\n        const displayName = member ? member.rawDisplayName : userId;\n        const caret = this.getCaret();\n        const position = model.positionForOffset(caret.offset, caret.atNodeEnd);\n        // Insert suffix only if the caret is at the start of the composer\n        const parts = partCreator.createMentionParts(caret.offset === 0, displayName, userId);\n        model.transform(() => {\n            const addedLen = model.insert(parts, position);\n            return model.positionForOffset(caret.offset + addedLen, true);\n        });\n        // refocus on composer, as we just clicked \"Mention\"\n        this.focus();\n    }\n\n    public insertQuotedMessage(event: MatrixEvent): void {\n        this.modifiedFlag = true;\n        const { model } = this.props;\n        const { partCreator } = model;\n        const quoteParts = parseEvent(event, partCreator, { isQuotedMessage: true });\n        // add two newlines\n        quoteParts.push(partCreator.newline());\n        quoteParts.push(partCreator.newline());\n        model.transform(() => {\n            const addedLen = model.insert(quoteParts, model.positionForOffset(0));\n            return model.positionForOffset(addedLen, true);\n        });\n        // refocus on composer, as we just clicked \"Quote\"\n        this.focus();\n    }\n\n    public insertPlaintext(text: string): void {\n        this.modifiedFlag = true;\n        const { model } = this.props;\n        const { partCreator } = model;\n        const caret = this.getCaret();\n        const position = model.positionForOffset(caret.offset, caret.atNodeEnd);\n        model.transform(() => {\n            const addedLen = model.insert(partCreator.plainWithEmoji(text), position);\n            return model.positionForOffset(caret.offset + addedLen, true);\n        });\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ComponentProps, type CSSProperties } from \"react\";\nimport classNames from \"classnames\";\nimport { Tooltip } from \"@vector-im/compound-web\";\nimport { ErrorSolidIcon, ShieldIcon, LockSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t, _td } from \"../../../languageHandler\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport { E2EStatus } from \"../../../utils/ShieldUtils\";\n\nexport const crossSigningUserTitles: { [key in E2EStatus]?: TranslationKey } = {\n    [E2EStatus.Warning]: _td(\"encryption|cross_signing_user_warning\"),\n    [E2EStatus.Normal]: _td(\"encryption|cross_signing_user_normal\"),\n    [E2EStatus.Verified]: _td(\"encryption|cross_signing_user_verified\"),\n};\nconst crossSigningRoomTitles: { [key in E2EStatus]?: TranslationKey } = {\n    [E2EStatus.Warning]: _td(\"encryption|cross_signing_room_warning\"),\n    [E2EStatus.Normal]: _td(\"encryption|cross_signing_room_normal\"),\n    [E2EStatus.Verified]: _td(\"encryption|cross_signing_room_verified\"),\n};\n\ninterface Props {\n    className?: string;\n    size?: number;\n    onClick?: () => void;\n    hideTooltip?: boolean;\n    tooltipPlacement?: ComponentProps<typeof Tooltip>[\"placement\"];\n    status: E2EStatus;\n    isUser?: boolean;\n}\n\nconst icons: Record<E2EStatus, JSX.Element> = {\n    [E2EStatus.Warning]: <ErrorSolidIcon color=\"var(--cpd-color-icon-critical-primary)\" />,\n    [E2EStatus.Normal]: <LockSolidIcon color=\"var(--cpd-color-icon-tertiary)\" />,\n    [E2EStatus.Verified]: <ShieldIcon color=\"var(--cpd-color-icon-success-primary)\" />,\n};\n\nconst E2EIcon: React.FC<Props> = ({ isUser, status, className, size, onClick, hideTooltip, tooltipPlacement }) => {\n    const icon = icons[status];\n\n    const classes = classNames(\"mx_E2EIcon\", className);\n\n    let e2eTitle: TranslationKey | undefined;\n    if (isUser) {\n        e2eTitle = crossSigningUserTitles[status];\n    } else {\n        e2eTitle = crossSigningRoomTitles[status];\n    }\n\n    let style: CSSProperties | undefined;\n    if (size) {\n        style = { width: `${size}px`, height: `${size}px` };\n    }\n\n    const label = e2eTitle ? _t(e2eTitle) : \"\";\n\n    let content: JSX.Element;\n    if (onClick) {\n        content = (\n            <AccessibleButton onClick={onClick} className={classes} style={style} data-testid=\"e2e-icon\">\n                {icon}\n            </AccessibleButton>\n        );\n    } else {\n        content = (\n            <div className={classes} style={style} data-testid=\"e2e-icon\">\n                {icon}\n            </div>\n        );\n    }\n\n    if (!e2eTitle || hideTooltip) {\n        return content;\n    }\n\n    return (\n        <Tooltip label={label} placement={tooltipPlacement} isTriggerInteractive={!!onClick}>\n            {content}\n        </Tooltip>\n    );\n};\n\nexport default E2EIcon;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport classNames from \"classnames\";\n\nimport { RovingAccessibleButton } from \"../../../accessibility/RovingTabIndex\";\nimport NotificationBadge from \"./NotificationBadge\";\nimport { type NotificationState } from \"../../../stores/notifications/NotificationState\";\nimport { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport useHover from \"../../../hooks/useHover\";\n\ninterface ExtraTileProps {\n    isMinimized: boolean;\n    isSelected: boolean;\n    displayName: string;\n    avatar: React.ReactElement;\n    notificationState?: NotificationState;\n    onClick: (ev: ButtonEvent) => void;\n}\n\nexport default function ExtraTile({\n    isSelected,\n    isMinimized,\n    notificationState,\n    displayName,\n    onClick,\n    avatar,\n}: ExtraTileProps): JSX.Element {\n    const [, { onMouseOver, onMouseLeave }] = useHover(() => false);\n\n    // XXX: We copy classes because it's easier\n    const classes = classNames({\n        mx_ExtraTile: true,\n        mx_RoomTile: true,\n        mx_RoomTile_selected: isSelected,\n        mx_RoomTile_minimized: isMinimized,\n    });\n\n    let badge: JSX.Element | null = null;\n    if (notificationState) {\n        badge = <NotificationBadge notification={notificationState} />;\n    }\n\n    let name = displayName;\n    if (typeof name !== \"string\") name = \"\";\n    name = name.replace(\":\", \":\\u200b\"); // add a zero-width space to allow linewrapping after the colon\n\n    const nameClasses = classNames({\n        mx_RoomTile_title: true,\n        mx_RoomTile_titleHasUnreadEvents: notificationState?.isUnread,\n    });\n\n    let nameContainer: JSX.Element | null = (\n        <div className=\"mx_RoomTile_titleContainer\">\n            <div title={name} className={nameClasses} tabIndex={-1} dir=\"auto\">\n                {name}\n            </div>\n        </div>\n    );\n    if (isMinimized) nameContainer = null;\n\n    return (\n        <RovingAccessibleButton\n            className={classes}\n            onMouseEnter={onMouseOver}\n            onMouseLeave={onMouseLeave}\n            onClick={onClick}\n            role=\"treeitem\"\n            title={name}\n            disableTooltip={!isMinimized}\n        >\n            <div className=\"mx_RoomTile_avatarContainer\">{avatar}</div>\n            <div className=\"mx_RoomTile_details\">\n                <div className=\"mx_RoomTile_primaryDetails\">\n                    {nameContainer}\n                    <div className=\"mx_RoomTile_badgeContainer\">{badge}</div>\n                </div>\n            </div>\n        </RovingAccessibleButton>\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useState } from \"react\";\n\nexport default function useHover(\n    ignoreHover: (ev: React.MouseEvent) => boolean,\n): [boolean, { onMouseOver: () => void; onMouseLeave: () => void; onMouseMove: (ev: React.MouseEvent) => void }] {\n    const [hovered, setHoverState] = useState(false);\n\n    const props = {\n        onMouseOver: () => setHoverState(true),\n        onMouseLeave: () => setHoverState(false),\n        onMouseMove: (ev: React.MouseEvent): void => {\n            setHoverState(!ignoreHover(ev));\n        },\n    };\n\n    return [hovered, props];\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2018 , 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EventType, type Room, RoomType } from \"matrix-js-sdk/src/matrix\";\nimport React, { type JSX, type ComponentType, createRef, type ReactComponentElement, type SyntheticEvent } from \"react\";\nimport {\n    PlusIcon,\n    UserAddSolidIcon,\n    RoomIcon,\n    SearchIcon,\n    ShareIcon,\n    VideoCallSolidIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { type IState as IRovingTabIndexState, RovingTabIndexProvider } from \"../../../accessibility/RovingTabIndex.tsx\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext.tsx\";\nimport { shouldShowComponent } from \"../../../customisations/helpers/UIComponents.ts\";\nimport { Action } from \"../../../dispatcher/actions.ts\";\nimport defaultDispatcher from \"../../../dispatcher/dispatcher.ts\";\nimport { type ActionPayload } from \"../../../dispatcher/payloads.ts\";\nimport { type ViewRoomDeltaPayload } from \"../../../dispatcher/payloads/ViewRoomDeltaPayload.ts\";\nimport { type ViewRoomPayload } from \"../../../dispatcher/payloads/ViewRoomPayload.ts\";\nimport { useEventEmitterState } from \"../../../hooks/useEventEmitter.ts\";\nimport { _t, _td } from \"../../../languageHandler.tsx\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg.ts\";\nimport PosthogTrackers from \"../../../PosthogTrackers.ts\";\nimport SettingsStore from \"../../../settings/SettingsStore.ts\";\nimport { useFeatureEnabled } from \"../../../hooks/useSettings.ts\";\nimport { UIComponent } from \"../../../settings/UIFeature.ts\";\nimport { RoomNotificationStateStore } from \"../../../stores/notifications/RoomNotificationStateStore.ts\";\nimport { type ITagMap } from \"../../../stores/room-list/algorithms/models.ts\";\nimport { DefaultTagID, type TagID } from \"../../../stores/room-list/models.ts\";\nimport { UPDATE_EVENT } from \"../../../stores/AsyncStore.ts\";\nimport RoomListStore, { LISTS_UPDATE_EVENT } from \"../../../stores/room-list/RoomListStore.ts\";\nimport {\n    isMetaSpace,\n    type ISuggestedRoom,\n    MetaSpace,\n    type SpaceKey,\n    UPDATE_SELECTED_SPACE,\n    UPDATE_SUGGESTED_ROOMS,\n} from \"../../../stores/spaces/index.ts\";\nimport SpaceStore from \"../../../stores/spaces/SpaceStore.ts\";\nimport { arrayFastClone, arrayHasDiff } from \"../../../utils/arrays.ts\";\nimport { objectShallowClone, objectWithOnly } from \"../../../utils/objects.ts\";\nimport type ResizeNotifier from \"../../../utils/ResizeNotifier.ts\";\nimport {\n    shouldShowSpaceInvite,\n    showAddExistingRooms,\n    showCreateNewRoom,\n    showSpaceInvite,\n} from \"../../../utils/space.tsx\";\nimport {\n    ChevronFace,\n    ContextMenuTooltipButton,\n    type MenuProps,\n    useContextMenu,\n} from \"../../structures/ContextMenu.tsx\";\nimport RoomAvatar from \"../avatars/RoomAvatar.tsx\";\nimport { BetaPill } from \"../beta/BetaCard.tsx\";\nimport IconizedContextMenu, {\n    IconizedContextMenuOption,\n    IconizedContextMenuOptionList,\n} from \"../context_menus/IconizedContextMenu.tsx\";\nimport ExtraTile from \"./ExtraTile.tsx\";\nimport RoomSublist, { type IAuxButtonProps } from \"./RoomSublist.tsx\";\nimport { SdkContextClass } from \"../../../contexts/SDKContext.ts\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts.ts\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager.ts\";\nimport AccessibleButton from \"../elements/AccessibleButton.tsx\";\nimport { Landmark, LandmarkNavigation } from \"../../../accessibility/LandmarkNavigation.ts\";\nimport LegacyCallHandler, { LegacyCallHandlerEvent } from \"../../../LegacyCallHandler.tsx\";\n\ninterface IProps {\n    onKeyDown: (ev: React.KeyboardEvent, state: IRovingTabIndexState) => void;\n    onFocus: (ev: React.FocusEvent) => void;\n    onBlur: (ev: React.FocusEvent) => void;\n    onResize: () => void;\n    onListCollapse?: (isExpanded: boolean) => void;\n    resizeNotifier: ResizeNotifier;\n    isMinimized: boolean;\n    activeSpace: SpaceKey;\n}\n\ninterface IState {\n    sublists: ITagMap;\n    currentRoomId?: string;\n    suggestedRooms: ISuggestedRoom[];\n}\n\nexport const TAG_ORDER: TagID[] = [\n    DefaultTagID.Invite,\n    DefaultTagID.Favourite,\n    DefaultTagID.DM,\n    DefaultTagID.Untagged,\n    DefaultTagID.Conference,\n    DefaultTagID.LowPriority,\n    DefaultTagID.ServerNotice,\n    DefaultTagID.Suggested,\n    // DefaultTagID.Archived isn't here any more: we don't show it at all.\n    // The section still exists in the code as a place for rooms that we know\n    // about but aren't joined. At some point it could be removed entirely\n    // but we'd have to make sure that rooms you weren't in were hidden.\n];\nconst ALWAYS_VISIBLE_TAGS: TagID[] = [DefaultTagID.DM, DefaultTagID.Untagged];\n\ninterface ITagAesthetics {\n    sectionLabel: TranslationKey;\n    sectionLabelRaw?: string;\n    AuxButtonComponent?: ComponentType<IAuxButtonProps>;\n    isInvite: boolean;\n    defaultHidden: boolean;\n}\n\ntype TagAestheticsMap = Partial<{\n    [tagId in TagID]: ITagAesthetics;\n}>;\n\nconst auxButtonContextMenuPosition = (handle: HTMLDivElement): MenuProps => {\n    const rect = handle.getBoundingClientRect();\n    return {\n        chevronFace: ChevronFace.None,\n        left: rect.left - 7,\n        top: rect.top + rect.height,\n    };\n};\n\nconst DmAuxButton: React.FC<IAuxButtonProps> = ({ tabIndex, dispatcher = defaultDispatcher }) => {\n    const [menuDisplayed, handle, openMenu, closeMenu] = useContextMenu<HTMLDivElement>();\n    const activeSpace = useEventEmitterState(SpaceStore.instance, UPDATE_SELECTED_SPACE, () => {\n        return SpaceStore.instance.activeSpaceRoom;\n    });\n\n    const showCreateRooms = shouldShowComponent(UIComponent.CreateRooms);\n    const showInviteUsers = shouldShowComponent(UIComponent.InviteUsers);\n\n    if (activeSpace && (showCreateRooms || showInviteUsers)) {\n        let contextMenu: JSX.Element | undefined;\n        if (menuDisplayed && handle.current) {\n            const canInvite = shouldShowSpaceInvite(activeSpace);\n\n            contextMenu = (\n                <IconizedContextMenu {...auxButtonContextMenuPosition(handle.current)} onFinished={closeMenu} compact>\n                    <IconizedContextMenuOptionList first>\n                        {showCreateRooms && (\n                            <IconizedContextMenuOption\n                                label={_t(\"action|start_new_chat\")}\n                                icon={<UserAddSolidIcon />}\n                                onClick={(e) => {\n                                    e.preventDefault();\n                                    e.stopPropagation();\n                                    closeMenu();\n                                    defaultDispatcher.dispatch({ action: Action.CreateChat });\n                                    PosthogTrackers.trackInteraction(\n                                        \"WebRoomListRoomsSublistPlusMenuCreateChatItem\",\n                                        e,\n                                    );\n                                }}\n                            />\n                        )}\n                        {showInviteUsers && (\n                            <IconizedContextMenuOption\n                                label={_t(\"action|invite_to_space\")}\n                                icon={<ShareIcon />}\n                                onClick={(e) => {\n                                    e.preventDefault();\n                                    e.stopPropagation();\n                                    closeMenu();\n                                    showSpaceInvite(activeSpace);\n                                }}\n                                disabled={!canInvite}\n                                title={canInvite ? undefined : _t(\"spaces|error_no_permission_invite\")}\n                            />\n                        )}\n                    </IconizedContextMenuOptionList>\n                </IconizedContextMenu>\n            );\n        }\n\n        return (\n            <>\n                <ContextMenuTooltipButton\n                    tabIndex={tabIndex}\n                    onClick={openMenu}\n                    className=\"mx_RoomSublist_auxButton\"\n                    aria-label={_t(\"action|add_people\")}\n                    title={_t(\"action|add_people\")}\n                    isExpanded={menuDisplayed}\n                    ref={handle}\n                >\n                    <PlusIcon />\n                </ContextMenuTooltipButton>\n\n                {contextMenu}\n            </>\n        );\n    } else if (!activeSpace && showCreateRooms) {\n        return (\n            <AccessibleButton\n                tabIndex={tabIndex}\n                onClick={(e) => {\n                    dispatcher.dispatch({ action: Action.CreateChat });\n                    PosthogTrackers.trackInteraction(\"WebRoomListRoomsSublistPlusMenuCreateChatItem\", e);\n                }}\n                className=\"mx_RoomSublist_auxButton\"\n                aria-label={_t(\"action|start_chat\")}\n                title={_t(\"action|start_chat\")}\n            >\n                <PlusIcon />\n            </AccessibleButton>\n        );\n    }\n\n    return null;\n};\n\nconst UntaggedAuxButton: React.FC<IAuxButtonProps> = ({ tabIndex }) => {\n    const [menuDisplayed, handle, openMenu, closeMenu] = useContextMenu<HTMLDivElement>();\n    const activeSpace = useEventEmitterState<Room | null>(SpaceStore.instance, UPDATE_SELECTED_SPACE, () => {\n        return SpaceStore.instance.activeSpaceRoom;\n    });\n\n    const showCreateRoom = shouldShowComponent(UIComponent.CreateRooms);\n    const showExploreRooms = shouldShowComponent(UIComponent.ExploreRooms);\n\n    const videoRoomsEnabled = useFeatureEnabled(\"feature_video_rooms\");\n    const elementCallVideoRoomsEnabled = useFeatureEnabled(\"feature_element_call_video_rooms\");\n\n    let contextMenuContent: JSX.Element | undefined;\n    if (menuDisplayed && activeSpace) {\n        const canAddRooms = activeSpace.currentState.maySendStateEvent(\n            EventType.SpaceChild,\n            MatrixClientPeg.safeGet().getSafeUserId(),\n        );\n\n        contextMenuContent = (\n            <IconizedContextMenuOptionList first>\n                <IconizedContextMenuOption\n                    label={_t(\"action|explore_rooms\")}\n                    icon={<SearchIcon />}\n                    onClick={(e) => {\n                        e.preventDefault();\n                        e.stopPropagation();\n                        closeMenu();\n                        defaultDispatcher.dispatch<ViewRoomPayload>({\n                            action: Action.ViewRoom,\n                            room_id: activeSpace.roomId,\n                            metricsTrigger: undefined, // other\n                        });\n                        PosthogTrackers.trackInteraction(\"WebRoomListRoomsSublistPlusMenuExploreRoomsItem\", e);\n                    }}\n                />\n                {showCreateRoom ? (\n                    <>\n                        <IconizedContextMenuOption\n                            label={_t(\"action|new_room\")}\n                            icon={<PlusIcon />}\n                            onClick={(e) => {\n                                e.preventDefault();\n                                e.stopPropagation();\n                                closeMenu();\n                                showCreateNewRoom(activeSpace);\n                                PosthogTrackers.trackInteraction(\"WebRoomListRoomsSublistPlusMenuCreateRoomItem\", e);\n                            }}\n                            disabled={!canAddRooms}\n                            title={canAddRooms ? undefined : _t(\"spaces|error_no_permission_create_room\")}\n                        />\n                        {videoRoomsEnabled && (\n                            <IconizedContextMenuOption\n                                label={_t(\"action|new_video_room\")}\n                                icon={<VideoCallSolidIcon />}\n                                onClick={(e) => {\n                                    e.preventDefault();\n                                    e.stopPropagation();\n                                    closeMenu();\n                                    showCreateNewRoom(\n                                        activeSpace,\n                                        elementCallVideoRoomsEnabled ? RoomType.UnstableCall : RoomType.ElementVideo,\n                                    );\n                                }}\n                                disabled={!canAddRooms}\n                                title={canAddRooms ? undefined : _t(\"spaces|error_no_permission_create_room\")}\n                            >\n                                <BetaPill />\n                            </IconizedContextMenuOption>\n                        )}\n                        <IconizedContextMenuOption\n                            label={_t(\"action|add_existing_room\")}\n                            icon={<RoomIcon />}\n                            onClick={(e) => {\n                                e.preventDefault();\n                                e.stopPropagation();\n                                closeMenu();\n                                showAddExistingRooms(activeSpace);\n                            }}\n                            disabled={!canAddRooms}\n                            title={canAddRooms ? undefined : _t(\"spaces|error_no_permission_add_room\")}\n                        />\n                    </>\n                ) : null}\n            </IconizedContextMenuOptionList>\n        );\n    } else if (menuDisplayed) {\n        contextMenuContent = (\n            <IconizedContextMenuOptionList first>\n                {showCreateRoom && (\n                    <>\n                        <IconizedContextMenuOption\n                            label={_t(\"action|new_room\")}\n                            icon={<PlusIcon />}\n                            onClick={(e) => {\n                                e.preventDefault();\n                                e.stopPropagation();\n                                closeMenu();\n                                defaultDispatcher.dispatch({ action: Action.CreateRoom });\n                                PosthogTrackers.trackInteraction(\"WebRoomListRoomsSublistPlusMenuCreateRoomItem\", e);\n                            }}\n                        />\n                        {videoRoomsEnabled && (\n                            <IconizedContextMenuOption\n                                label={_t(\"action|new_video_room\")}\n                                icon={<VideoCallSolidIcon />}\n                                onClick={(e) => {\n                                    e.preventDefault();\n                                    e.stopPropagation();\n                                    closeMenu();\n                                    defaultDispatcher.dispatch({\n                                        action: Action.CreateRoom,\n                                        type: elementCallVideoRoomsEnabled\n                                            ? RoomType.UnstableCall\n                                            : RoomType.ElementVideo,\n                                    });\n                                }}\n                            >\n                                <BetaPill />\n                            </IconizedContextMenuOption>\n                        )}\n                    </>\n                )}\n                {showExploreRooms ? (\n                    <IconizedContextMenuOption\n                        label={_t(\"action|explore_public_rooms\")}\n                        icon={<SearchIcon />}\n                        onClick={(e) => {\n                            e.preventDefault();\n                            e.stopPropagation();\n                            closeMenu();\n                            PosthogTrackers.trackInteraction(\"WebRoomListRoomsSublistPlusMenuExploreRoomsItem\", e);\n                            defaultDispatcher.fire(Action.ViewRoomDirectory);\n                        }}\n                    />\n                ) : null}\n            </IconizedContextMenuOptionList>\n        );\n    }\n\n    let contextMenu: JSX.Element | null = null;\n    if (menuDisplayed && handle.current) {\n        contextMenu = (\n            <IconizedContextMenu {...auxButtonContextMenuPosition(handle.current)} onFinished={closeMenu} compact>\n                {contextMenuContent}\n            </IconizedContextMenu>\n        );\n    }\n\n    if (showCreateRoom || showExploreRooms) {\n        return (\n            <>\n                <ContextMenuTooltipButton\n                    tabIndex={tabIndex}\n                    onClick={openMenu}\n                    className=\"mx_RoomSublist_auxButton\"\n                    aria-label={_t(\"room_list|add_room_label\")}\n                    title={_t(\"room_list|add_room_label\")}\n                    isExpanded={menuDisplayed}\n                    ref={handle}\n                >\n                    <PlusIcon />\n                </ContextMenuTooltipButton>\n\n                {contextMenu}\n            </>\n        );\n    }\n\n    return null;\n};\n\nconst TAG_AESTHETICS: TagAestheticsMap = {\n    [DefaultTagID.Invite]: {\n        sectionLabel: _td(\"action|invites_list\"),\n        isInvite: true,\n        defaultHidden: false,\n    },\n    [DefaultTagID.Favourite]: {\n        sectionLabel: _td(\"common|favourites\"),\n        isInvite: false,\n        defaultHidden: false,\n    },\n    [DefaultTagID.DM]: {\n        sectionLabel: _td(\"common|people\"),\n        isInvite: false,\n        defaultHidden: false,\n        AuxButtonComponent: DmAuxButton,\n    },\n    [DefaultTagID.Conference]: {\n        sectionLabel: _td(\"voip|metaspace_video_rooms|conference_room_section\"),\n        isInvite: false,\n        defaultHidden: false,\n    },\n    [DefaultTagID.Untagged]: {\n        sectionLabel: _td(\"common|rooms\"),\n        isInvite: false,\n        defaultHidden: false,\n        AuxButtonComponent: UntaggedAuxButton,\n    },\n    [DefaultTagID.LowPriority]: {\n        sectionLabel: _td(\"common|low_priority\"),\n        isInvite: false,\n        defaultHidden: false,\n    },\n    [DefaultTagID.ServerNotice]: {\n        sectionLabel: _td(\"common|system_alerts\"),\n        isInvite: false,\n        defaultHidden: false,\n    },\n\n    // TODO: Replace with archived view: https://github.com/vector-im/element-web/issues/14038\n    [DefaultTagID.Archived]: {\n        sectionLabel: _td(\"common|historical\"),\n        isInvite: false,\n        defaultHidden: true,\n    },\n\n    [DefaultTagID.Suggested]: {\n        sectionLabel: _td(\"room_list|suggested_rooms_heading\"),\n        isInvite: false,\n        defaultHidden: false,\n    },\n};\n\nexport default class LegacyRoomList extends React.PureComponent<IProps, IState> {\n    private dispatcherRef?: string;\n    private treeRef = createRef<HTMLDivElement>();\n\n    public static contextType = MatrixClientContext;\n    declare public context: React.ContextType<typeof MatrixClientContext>;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            sublists: {},\n            suggestedRooms: SpaceStore.instance.suggestedRooms,\n        };\n    }\n\n    public componentDidMount(): void {\n        this.dispatcherRef = defaultDispatcher.register(this.onAction);\n        SdkContextClass.instance.roomViewStore.on(UPDATE_EVENT, this.onRoomViewStoreUpdate);\n        SpaceStore.instance.on(UPDATE_SUGGESTED_ROOMS, this.updateSuggestedRooms);\n        RoomListStore.instance.on(LISTS_UPDATE_EVENT, this.updateLists);\n        LegacyCallHandler.instance.on(LegacyCallHandlerEvent.ProtocolSupport, this.updateProtocolSupport);\n        this.updateLists(); // trigger the first update\n    }\n\n    public componentWillUnmount(): void {\n        SpaceStore.instance.off(UPDATE_SUGGESTED_ROOMS, this.updateSuggestedRooms);\n        RoomListStore.instance.off(LISTS_UPDATE_EVENT, this.updateLists);\n        defaultDispatcher.unregister(this.dispatcherRef);\n        SdkContextClass.instance.roomViewStore.off(UPDATE_EVENT, this.onRoomViewStoreUpdate);\n        LegacyCallHandler.instance.off(LegacyCallHandlerEvent.ProtocolSupport, this.updateProtocolSupport);\n    }\n\n    private updateProtocolSupport = (): void => {\n        this.updateLists();\n    };\n\n    private onRoomViewStoreUpdate = (): void => {\n        this.setState({\n            currentRoomId: SdkContextClass.instance.roomViewStore.getRoomId() ?? undefined,\n        });\n    };\n\n    private onAction = (payload: ActionPayload): void => {\n        if (payload.action === Action.ViewRoomDelta) {\n            const viewRoomDeltaPayload = payload as ViewRoomDeltaPayload;\n            const currentRoomId = SdkContextClass.instance.roomViewStore.getRoomId();\n            if (!currentRoomId) return;\n            const room = this.getRoomDelta(currentRoomId, viewRoomDeltaPayload.delta, viewRoomDeltaPayload.unread);\n            if (room) {\n                defaultDispatcher.dispatch<ViewRoomPayload>({\n                    action: Action.ViewRoom,\n                    room_id: room.roomId,\n                    show_room_tile: true, // to make sure the room gets scrolled into view\n                    metricsTrigger: \"WebKeyboardShortcut\",\n                    metricsViaKeyboard: true,\n                });\n            }\n        }\n    };\n\n    private getRoomDelta = (roomId: string, delta: number, unread = false): Room => {\n        const lists = RoomListStore.instance.orderedLists;\n        const rooms: Room[] = [];\n        TAG_ORDER.forEach((t) => {\n            let listRooms = lists[t];\n\n            if (unread) {\n                // filter to only notification rooms (and our current active room so we can index properly)\n                listRooms = listRooms.filter((r) => {\n                    const state = RoomNotificationStateStore.instance.getRoomState(r);\n                    return state.room.roomId === roomId || state.isUnread;\n                });\n            }\n\n            rooms.push(...listRooms);\n        });\n\n        const currentIndex = rooms.findIndex((r) => r.roomId === roomId);\n        // use slice to account for looping around the start\n        const [room] = rooms.slice((currentIndex + delta) % rooms.length);\n        return room;\n    };\n\n    private updateSuggestedRooms = (suggestedRooms: ISuggestedRoom[]): void => {\n        this.setState({ suggestedRooms });\n    };\n\n    private updateLists = (): void => {\n        const newLists = RoomListStore.instance.orderedLists;\n        const previousListIds = Object.keys(this.state.sublists);\n        const newListIds = Object.keys(newLists);\n\n        let doUpdate = arrayHasDiff(previousListIds, newListIds);\n        if (!doUpdate) {\n            // so we didn't have the visible sublists change, but did the contents of those\n            // sublists change significantly enough to break the sticky headers? Probably, so\n            // let's check the length of each.\n            for (const tagId of newListIds) {\n                const oldRooms = this.state.sublists[tagId];\n                const newRooms = newLists[tagId];\n                if (oldRooms.length !== newRooms.length) {\n                    doUpdate = true;\n                    break;\n                }\n            }\n        }\n\n        if (doUpdate) {\n            // We have to break our reference to the room list store if we want to be able to\n            // diff the object for changes, so do that.\n            // @ts-ignore - ITagMap is ts-ignored so this will have to be too\n            const newSublists = objectWithOnly(newLists, newListIds);\n            const sublists = objectShallowClone(newSublists, (k, v) => arrayFastClone(v));\n\n            this.setState({ sublists }, () => {\n                this.props.onResize();\n            });\n        }\n    };\n\n    private renderSuggestedRooms(): ReactComponentElement<typeof ExtraTile>[] {\n        return this.state.suggestedRooms.map((room) => {\n            const name = room.name || room.canonical_alias || room.aliases?.[0] || _t(\"empty_room\");\n            const avatar = (\n                <RoomAvatar\n                    oobData={{\n                        name,\n                        avatarUrl: room.avatar_url,\n                    }}\n                    size=\"32px\"\n                />\n            );\n            const viewRoom = (ev: SyntheticEvent): void => {\n                defaultDispatcher.dispatch<ViewRoomPayload>({\n                    action: Action.ViewRoom,\n                    room_alias: room.canonical_alias || room.aliases?.[0],\n                    room_id: room.room_id,\n                    via_servers: room.viaServers,\n                    oob_data: {\n                        avatarUrl: room.avatar_url,\n                        name,\n                    },\n                    metricsTrigger: \"RoomList\",\n                    metricsViaKeyboard: ev.type !== \"click\",\n                });\n            };\n            return (\n                <ExtraTile\n                    isMinimized={this.props.isMinimized}\n                    isSelected={this.state.currentRoomId === room.room_id}\n                    displayName={name}\n                    avatar={avatar}\n                    onClick={viewRoom}\n                    key={`suggestedRoomTile_${room.room_id}`}\n                />\n            );\n        });\n    }\n\n    private renderSublists(): React.ReactElement[] {\n        // show a skeleton UI if the user is in no rooms and they are not filtering and have no suggested rooms\n        const showSkeleton =\n            !this.state.suggestedRooms?.length &&\n            Object.values(RoomListStore.instance.orderedLists).every((list) => !list?.length);\n\n        return TAG_ORDER.map((orderedTagId) => {\n            let extraTiles: ReactComponentElement<typeof ExtraTile>[] | undefined;\n            if (orderedTagId === DefaultTagID.Suggested) {\n                extraTiles = this.renderSuggestedRooms();\n            }\n\n            const aesthetics = TAG_AESTHETICS[orderedTagId];\n            if (!aesthetics) throw new Error(`Tag ${orderedTagId} does not have aesthetics`);\n\n            let alwaysVisible = ALWAYS_VISIBLE_TAGS.includes(orderedTagId);\n            if (\n                (this.props.activeSpace === MetaSpace.Favourites && orderedTagId !== DefaultTagID.Favourite) ||\n                (this.props.activeSpace === MetaSpace.People && orderedTagId !== DefaultTagID.DM) ||\n                (this.props.activeSpace === MetaSpace.Orphans && orderedTagId === DefaultTagID.DM) ||\n                (this.props.activeSpace === MetaSpace.VideoRooms && orderedTagId === DefaultTagID.DM) ||\n                (!isMetaSpace(this.props.activeSpace) &&\n                    orderedTagId === DefaultTagID.DM &&\n                    !SettingsStore.getValue(\"Spaces.showPeopleInSpace\", this.props.activeSpace))\n            ) {\n                alwaysVisible = false;\n            }\n\n            let forceExpanded = false;\n            if (\n                (this.props.activeSpace === MetaSpace.Favourites && orderedTagId === DefaultTagID.Favourite) ||\n                (this.props.activeSpace === MetaSpace.People && orderedTagId === DefaultTagID.DM)\n            ) {\n                forceExpanded = true;\n            }\n            // The cost of mounting/unmounting this component offsets the cost\n            // of keeping it in the DOM and hiding it when it is not required\n            return (\n                <RoomSublist\n                    key={`sublist-${orderedTagId}`}\n                    tagId={orderedTagId}\n                    forRooms={true}\n                    startAsHidden={aesthetics.defaultHidden}\n                    label={aesthetics.sectionLabelRaw ? aesthetics.sectionLabelRaw : _t(aesthetics.sectionLabel)}\n                    AuxButtonComponent={aesthetics.AuxButtonComponent}\n                    isMinimized={this.props.isMinimized}\n                    showSkeleton={showSkeleton}\n                    extraTiles={extraTiles}\n                    resizeNotifier={this.props.resizeNotifier}\n                    alwaysVisible={alwaysVisible}\n                    onListCollapse={this.props.onListCollapse}\n                    forceExpanded={forceExpanded}\n                />\n            );\n        });\n    }\n\n    public focus(): void {\n        // focus the first focusable element in this aria treeview widget\n        const treeItems = this.treeRef.current?.querySelectorAll<HTMLElement>('[role=\"treeitem\"]');\n        if (!treeItems) return;\n        [...treeItems].find((e) => e.offsetParent !== null)?.focus();\n    }\n\n    public render(): React.ReactNode {\n        const sublists = this.renderSublists();\n        return (\n            <RovingTabIndexProvider handleHomeEnd handleUpDown onKeyDown={this.props.onKeyDown}>\n                {({ onKeyDownHandler }) => (\n                    <div\n                        onFocus={this.props.onFocus}\n                        onBlur={this.props.onBlur}\n                        onKeyDown={(ev) => {\n                            const navAction = getKeyBindingsManager().getNavigationAction(ev);\n                            if (\n                                navAction === KeyBindingAction.NextLandmark ||\n                                navAction === KeyBindingAction.PreviousLandmark\n                            ) {\n                                LandmarkNavigation.findAndFocusNextLandmark(\n                                    Landmark.ROOM_LIST,\n                                    navAction === KeyBindingAction.PreviousLandmark,\n                                );\n                                ev.stopPropagation();\n                                ev.preventDefault();\n                                return;\n                            }\n                            onKeyDownHandler(ev);\n                        }}\n                        className=\"mx_LegacyRoomList\"\n                        role=\"tree\"\n                        aria-label={_t(\"common|rooms\")}\n                        ref={this.treeRef}\n                    >\n                        {sublists}\n                    </div>\n                )}\n            </RovingTabIndexProvider>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type FC } from \"react\";\nimport classNames from \"classnames\";\nimport { GroupIcon, VideoCallSolidIcon, VoiceCallSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\n\nexport enum LiveContentType {\n    Video,\n    Voice,\n}\n\ninterface Props {\n    type: LiveContentType;\n    text: string;\n    active: boolean;\n    participantCount: number;\n}\n\n/**\n * Summary line used to call out live, interactive content such as calls.\n */\nexport const LiveContentSummary: FC<Props> = ({ type, text, active, participantCount }) => (\n    <span className=\"mx_LiveContentSummary\">\n        <span\n            className={classNames(\"mx_LiveContentSummary_text\", {\n                mx_LiveContentSummary_text_active: active,\n            })}\n        >\n            {type === LiveContentType.Video ? <VideoCallSolidIcon /> : <VoiceCallSolidIcon />}\n            {text}\n        </span>\n        {participantCount > 0 && (\n            <>\n                {\" • \"}\n                <span\n                    className=\"mx_LiveContentSummary_participants\"\n                    aria-label={_t(\"voip|n_people_joined\", { count: participantCount })}\n                >\n                    <GroupIcon />\n                    {participantCount}\n                </span>\n            </>\n        )}\n    </span>\n);\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode } from \"react\";\nimport { Tooltip } from \"@vector-im/compound-web\";\n\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { type XOR } from \"../../../@types/common\";\nimport { type NotificationState, NotificationStateEvents } from \"../../../stores/notifications/NotificationState\";\nimport { _t } from \"../../../languageHandler\";\nimport { NotificationLevel } from \"../../../stores/notifications/NotificationLevel\";\nimport { StatelessNotificationBadge } from \"./NotificationBadge/StatelessNotificationBadge\";\n\ninterface IProps {\n    notification: NotificationState;\n\n    /**\n     * If true, show nothing if the notification would only cause a dot to be shown rather than\n     * a badge. That is: only display badges and not dots. Default: false.\n     */\n    hideIfDot?: boolean;\n\n    /**\n     * The room ID, if any, the badge represents.\n     */\n    roomId?: string;\n}\n\ninterface IClickableProps extends IProps, React.InputHTMLAttributes<Element> {\n    showUnsentTooltip?: boolean;\n    /**\n     * If specified will return an AccessibleButton instead of a div.\n     */\n    onClick(ev: React.MouseEvent): void;\n}\n\ninterface IState {\n    showCounts: boolean; // whether to show counts.\n}\n\nexport default class NotificationBadge extends React.PureComponent<XOR<IProps, IClickableProps>, IState> {\n    private countWatcherRef?: string;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            showCounts: SettingsStore.getValue(\"Notifications.alwaysShowBadgeCounts\", this.roomId),\n        };\n    }\n\n    private get roomId(): string | null {\n        // We should convert this to null for safety with the SettingsStore\n        return this.props.roomId || null;\n    }\n\n    public componentDidMount(): void {\n        this.props.notification.on(NotificationStateEvents.Update, this.onNotificationUpdate);\n\n        this.countWatcherRef = SettingsStore.watchSetting(\n            \"Notifications.alwaysShowBadgeCounts\",\n            this.roomId,\n            this.countPreferenceChanged,\n        );\n    }\n\n    public componentWillUnmount(): void {\n        SettingsStore.unwatchSetting(this.countWatcherRef);\n        this.props.notification.off(NotificationStateEvents.Update, this.onNotificationUpdate);\n    }\n\n    public componentDidUpdate(prevProps: Readonly<IProps>): void {\n        if (prevProps.notification) {\n            prevProps.notification.off(NotificationStateEvents.Update, this.onNotificationUpdate);\n        }\n\n        this.props.notification.on(NotificationStateEvents.Update, this.onNotificationUpdate);\n    }\n\n    private countPreferenceChanged = (): void => {\n        this.setState({ showCounts: SettingsStore.getValue(\"Notifications.alwaysShowBadgeCounts\", this.roomId) });\n    };\n\n    private onNotificationUpdate = (): void => {\n        this.forceUpdate(); // notification state changed - update\n    };\n\n    public render(): ReactNode {\n        /* eslint @typescript-eslint/no-unused-vars: [\"error\", { \"ignoreRestSiblings\": true }] */\n        const { notification, showUnsentTooltip, hideIfDot, onClick, tabIndex } = this.props;\n\n        if (notification.isIdle && !notification.knocked) return null;\n        if (hideIfDot && notification.level < NotificationLevel.Notification) {\n            // This would just be a dot and we've been told not to show dots, so don't show it\n            return null;\n        }\n\n        const commonProps: React.ComponentProps<typeof StatelessNotificationBadge> = {\n            symbol: notification.symbol,\n            count: notification.count,\n            level: notification.level,\n            knocked: notification.knocked,\n        };\n\n        let badge: JSX.Element;\n        if (onClick) {\n            badge = <StatelessNotificationBadge {...commonProps} onClick={onClick} tabIndex={tabIndex} />;\n        } else {\n            badge = <StatelessNotificationBadge {...commonProps} />;\n        }\n\n        if (showUnsentTooltip && notification.level === NotificationLevel.Unsent) {\n            return (\n                <Tooltip label={_t(\"notifications|message_didnt_send\")} placement=\"right\">\n                    {badge}\n                </Tooltip>\n            );\n        }\n\n        return badge;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type Ref, type JSX, type ReactNode } from \"react\";\nimport classNames from \"classnames\";\nimport { AskToJoinIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { formatCount } from \"../../../../utils/FormattingUtils\";\nimport AccessibleButton, { type ButtonEvent } from \"../../elements/AccessibleButton\";\nimport { NotificationLevel } from \"../../../../stores/notifications/NotificationLevel\";\nimport { useSettingValue } from \"../../../../hooks/useSettings\";\nimport { type XOR } from \"../../../../@types/common\";\nimport { _t } from \"../../../../languageHandler.tsx\";\n\ninterface Props {\n    symbol: string | null;\n    count: number;\n    level: NotificationLevel;\n    knocked?: boolean;\n    /**\n     * If true, where we would normally show a badge, we instead show a dot. No numeric count will\n     * be displayed (but may affect whether the the dot is displayed). See class doc\n     * for the difference between the two.\n     */\n    forceDot?: boolean;\n    children?: ReactNode;\n    ref?: Ref<HTMLDivElement>;\n}\n\ninterface ClickableProps extends Props {\n    /**\n     * If specified will return an AccessibleButton instead of a div.\n     */\n    onClick(ev: ButtonEvent): void;\n    tabIndex?: number;\n}\n\n/**\n * A notification indicator that conveys what activity / notifications the user has in whatever\n * context it is being used.\n *\n * Can either be a 'badge': a small circle with a number in it (the 'count'), or a 'dot': a smaller, empty circle.\n * The two can be used to convey the same meaning but in different contexts, for example: for unread\n * notifications in the room list, it may have a green badge with the number of unread notifications,\n * but somewhere else it may just have a green dot as a more compact representation of the same information.\n */\nexport const StatelessNotificationBadge = ({\n    symbol,\n    count,\n    level,\n    knocked,\n    forceDot = false,\n    ...props\n}: XOR<Props, ClickableProps>): JSX.Element => {\n    const hideBold = useSettingValue(\"feature_hidebold\");\n\n    // Don't show a badge if we don't need to\n    if ((level === NotificationLevel.None || (hideBold && level == NotificationLevel.Activity)) && !knocked) {\n        return <></>;\n    }\n\n    const hasUnreadCount = level >= NotificationLevel.Notification && (!!count || !!symbol);\n\n    const isEmptyBadge = symbol === null && count === 0;\n\n    if (symbol === null && count > 0) {\n        symbol = formatCount(count);\n    }\n\n    let icon: JSX.Element | undefined;\n    if (knocked) {\n        icon = <AskToJoinIcon aria-label={_t(\"room|knock_sent\")} />;\n    }\n\n    // We show a dot if either:\n    // * The props force us to, or\n    // * It's just an activity-level notification or (in theory) lower and the room isn't knocked\n    const badgeType =\n        forceDot || (level <= NotificationLevel.Activity && !icon)\n            ? \"dot\"\n            : !symbol || symbol.length < 3\n              ? \"badge_2char\"\n              : \"badge_3char\";\n\n    const classes = classNames({\n        \"mx_NotificationBadge\": true,\n        \"mx_NotificationBadge_visible\": isEmptyBadge || knocked ? true : hasUnreadCount,\n        \"mx_NotificationBadge_level_notification\": level == NotificationLevel.Notification,\n        \"mx_NotificationBadge_level_highlight\": level >= NotificationLevel.Highlight,\n        \"mx_NotificationBadge_knocked\": knocked,\n\n        // Exactly one of mx_NotificationBadge_dot, mx_NotificationBadge_2char, mx_NotificationBadge_3char\n        \"mx_NotificationBadge_dot\": badgeType === \"dot\",\n        \"mx_NotificationBadge_2char\": badgeType === \"badge_2char\",\n        \"mx_NotificationBadge_3char\": badgeType === \"badge_3char\",\n        // Badges with text should always use light colors\n        \"cpd-theme-light\": badgeType !== \"dot\",\n    });\n\n    const content = icon || <span className=\"mx_NotificationBadge_count\">{symbol}</span>;\n\n    if (props.onClick) {\n        return (\n            <AccessibleButton {...props} className={classes} onClick={props.onClick} ref={props.ref}>\n                {content}\n                {props.children}\n            </AccessibleButton>\n        );\n    }\n\n    return (\n        <div className={classes} ref={props.ref}>\n            {content}\n        </div>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { UnstableValue } from \"matrix-js-sdk/src/NamespacedValue\";\nimport classNames from \"classnames\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { formatDuration } from \"../../../DateUtils\";\n\nexport const BUSY_PRESENCE_NAME = new UnstableValue(\"busy\", \"org.matrix.msc3026.busy\");\n\ninterface IProps {\n    // number of milliseconds ago this user was last active.\n    // zero = unknown\n    activeAgo?: number;\n    // if true, activeAgo is an approximation and \"Now\" should\n    // be shown instead\n    currentlyActive?: boolean;\n    // offline, online, etc\n    presenceState?: string;\n    // whether to apply colouring to the label\n    coloured?: boolean;\n    className?: string;\n}\n\nexport default class PresenceLabel extends React.Component<IProps> {\n    public static defaultProps = {\n        activeAgo: -1,\n    };\n\n    private getPrettyPresence(presence?: string, activeAgo?: number, currentlyActive?: boolean): string {\n        // for busy presence, we ignore the 'currentlyActive' flag: they're busy whether\n        // they're active or not. It can be set while the user is active in which case\n        // the 'active ago' ends up being 0.\n        if (presence && BUSY_PRESENCE_NAME.matches(presence)) return _t(\"presence|busy\");\n\n        if (presence === \"io.element.unreachable\") return _t(\"presence|unreachable\");\n\n        if (!currentlyActive && activeAgo !== undefined && activeAgo > 0) {\n            const duration = formatDuration(activeAgo);\n            if (presence === \"online\") return _t(\"presence|online_for\", { duration: duration });\n            if (presence === \"unavailable\") return _t(\"presence|idle_for\", { duration: duration }); // XXX: is this actually right?\n            if (presence === \"offline\") return _t(\"presence|offline_for\", { duration: duration });\n            return _t(\"presence|unknown_for\", { duration: duration });\n        } else {\n            if (presence === \"online\") return _t(\"presence|online\");\n            if (presence === \"unavailable\") return _t(\"presence|idle\"); // XXX: is this actually right?\n            if (presence === \"offline\") return _t(\"presence|offline\");\n            return _t(\"presence|unknown\");\n        }\n    }\n\n    public render(): React.ReactNode {\n        return (\n            <div\n                className={classNames(\"mx_PresenceLabel\", this.props.className, {\n                    mx_PresenceLabel_online: this.props.coloured && this.props.presenceState === \"online\",\n                })}\n            >\n                {this.getPrettyPresence(this.props.presenceState, this.props.activeAgo, this.props.currentlyActive)}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useContext } from \"react\";\n\nimport { type RightPanelPhases } from \"../../../../../stores/right-panel/RightPanelStorePhases\";\nimport { CurrentRightPanelPhaseContext } from \"../../../../../contexts/CurrentRightPanelPhaseContext\";\n\n/**\n * Hook to easily track whether a given right panel phase is toggled on/off.\n */\nexport function useToggled(phase: RightPanelPhases): boolean {\n    const context = useContext(CurrentRightPanelPhaseContext);\n    if (!context) {\n        return false;\n    }\n    const { currentPhase, isPanelOpen } = context;\n    return !!(isPanelOpen && currentPhase === phase);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017, 2018 Vector Creations Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport classNames from \"classnames\";\nimport { type Enable, Resizable } from \"re-resizable\";\nimport { type Direction } from \"re-resizable/lib/resizer\";\nimport React, { type JSX, type ComponentType, createRef, type ReactComponentElement, type ReactNode } from \"react\";\nimport {\n    ChevronDownIcon,\n    ChevronRightIcon,\n    ChevronUpIcon,\n    OverflowHorizontalIcon,\n} from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { polyfillTouchEvent } from \"../../../@types/polyfill\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { RovingAccessibleButton, RovingTabIndexWrapper } from \"../../../accessibility/RovingTabIndex\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport defaultDispatcher, { type MatrixDispatcher } from \"../../../dispatcher/dispatcher\";\nimport { type ActionPayload } from \"../../../dispatcher/payloads\";\nimport { type ViewRoomPayload } from \"../../../dispatcher/payloads/ViewRoomPayload\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { _t } from \"../../../languageHandler\";\nimport { type ListNotificationState } from \"../../../stores/notifications/ListNotificationState\";\nimport { RoomNotificationStateStore } from \"../../../stores/notifications/RoomNotificationStateStore\";\nimport { ListAlgorithm, SortAlgorithm } from \"../../../stores/room-list/algorithms/models\";\nimport { type ListLayout } from \"../../../stores/room-list/ListLayout\";\nimport { DefaultTagID, type TagID } from \"../../../stores/room-list/models\";\nimport RoomListLayoutStore from \"../../../stores/room-list/RoomListLayoutStore\";\nimport RoomListStore, { LISTS_UPDATE_EVENT, LISTS_LOADING_EVENT } from \"../../../stores/room-list/RoomListStore\";\nimport { arrayFastClone, arrayHasOrderChange } from \"../../../utils/arrays\";\nimport { objectExcluding, objectHasDiff } from \"../../../utils/objects\";\nimport type ResizeNotifier from \"../../../utils/ResizeNotifier\";\nimport ContextMenu, {\n    ChevronFace,\n    ContextMenuTooltipButton,\n    StyledMenuItemCheckbox,\n    StyledMenuItemRadio,\n} from \"../../structures/ContextMenu\";\nimport AccessibleButton, { type ButtonEvent } from \"../../views/elements/AccessibleButton\";\nimport type ExtraTile from \"./ExtraTile\";\nimport NotificationBadge from \"./NotificationBadge\";\nimport RoomTile from \"./RoomTile\";\n\nconst SHOW_N_BUTTON_HEIGHT = 28; // As defined by CSS\nconst RESIZE_HANDLE_HEIGHT = 4; // As defined by CSS\nexport const HEADER_HEIGHT = 32; // As defined by CSS\n\nconst MAX_PADDING_HEIGHT = SHOW_N_BUTTON_HEIGHT + RESIZE_HANDLE_HEIGHT;\n\n// HACK: We really shouldn't have to do this.\npolyfillTouchEvent();\n\nexport interface IAuxButtonProps {\n    tabIndex: number;\n    dispatcher?: MatrixDispatcher;\n}\n\ninterface IProps {\n    forRooms: boolean;\n    startAsHidden: boolean;\n    label: string;\n    AuxButtonComponent?: ComponentType<IAuxButtonProps>;\n    isMinimized: boolean;\n    tagId: TagID;\n    showSkeleton?: boolean;\n    alwaysVisible?: boolean;\n    forceExpanded?: boolean;\n    resizeNotifier: ResizeNotifier;\n    extraTiles?: ReactComponentElement<typeof ExtraTile>[] | null;\n    onListCollapse?: (isExpanded: boolean) => void;\n}\n\nfunction getLabelId(tagId: TagID): string {\n    return `mx_RoomSublist_label_${tagId}`;\n}\n\n// TODO: Use re-resizer's NumberSize when it is exposed as the type\ninterface ResizeDelta {\n    width: number;\n    height: number;\n}\n\ntype PartialDOMRect = Pick<DOMRect, \"left\" | \"top\" | \"height\">;\n\ninterface IState {\n    contextMenuPosition?: PartialDOMRect;\n    isResizing: boolean;\n    isExpanded: boolean; // used for the for expand of the sublist when the room list is being filtered\n    height: number;\n    rooms: Room[];\n    roomsLoading: boolean;\n}\n\nexport default class RoomSublist extends React.Component<IProps, IState> {\n    private headerButton = createRef<HTMLDivElement>();\n    private sublistRef = createRef<HTMLDivElement>();\n    private tilesRef = createRef<HTMLDivElement>();\n    private dispatcherRef?: string;\n    private layout: ListLayout;\n    private heightAtStart: number;\n    private notificationState: ListNotificationState;\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.layout = RoomListLayoutStore.instance.getLayoutFor(this.props.tagId);\n        this.heightAtStart = 0;\n        this.notificationState = RoomNotificationStateStore.instance.getListState(this.props.tagId);\n        this.state = {\n            isResizing: false,\n            isExpanded: !this.layout.isCollapsed,\n            height: 0, // to be fixed in a moment, we need `rooms` to calculate this.\n            rooms: arrayFastClone(RoomListStore.instance.orderedLists[this.props.tagId] || []),\n            roomsLoading: false,\n        };\n        // Why Object.assign() and not this.state.height? Because TypeScript says no.\n        this.state = Object.assign(this.state, { height: this.calculateInitialHeight() });\n    }\n\n    private calculateInitialHeight(): number {\n        const requestedVisibleTiles = Math.max(Math.floor(this.layout.visibleTiles), this.layout.minVisibleTiles);\n        const tileCount = Math.min(this.numTiles, requestedVisibleTiles);\n        return this.layout.tilesToPixelsWithPadding(tileCount, this.padding);\n    }\n\n    private get padding(): number {\n        let padding = RESIZE_HANDLE_HEIGHT;\n        // this is used for calculating the max height of the whole container,\n        // and takes into account whether there should be room reserved for the show more/less button\n        // when fully expanded. We can't rely purely on the layout's defaultVisible tile count\n        // because there are conditions in which we need to know that the 'show more' button\n        // is present while well under the default tile limit.\n        const needsShowMore = this.numTiles > this.numVisibleTiles;\n\n        // ...but also check this or we'll miss if the section is expanded and we need a\n        // 'show less'\n        const needsShowLess = this.numTiles > this.layout.defaultVisibleTiles;\n\n        if (needsShowMore || needsShowLess) {\n            padding += SHOW_N_BUTTON_HEIGHT;\n        }\n        return padding;\n    }\n\n    private get extraTiles(): ReactComponentElement<typeof ExtraTile>[] | null {\n        return this.props.extraTiles ?? null;\n    }\n\n    private get numTiles(): number {\n        return RoomSublist.calcNumTiles(this.state.rooms, this.extraTiles);\n    }\n\n    private static calcNumTiles(rooms: Room[], extraTiles?: any[] | null): number {\n        return (rooms || []).length + (extraTiles || []).length;\n    }\n\n    private get numVisibleTiles(): number {\n        const nVisible = Math.ceil(this.layout.visibleTiles);\n        return Math.min(nVisible, this.numTiles);\n    }\n\n    public componentDidUpdate(prevProps: Readonly<IProps>, prevState: Readonly<IState>): void {\n        const prevExtraTiles = prevProps.extraTiles;\n        // as the rooms can come in one by one we need to reevaluate\n        // the amount of available rooms to cap the amount of requested visible rooms by the layout\n        if (RoomSublist.calcNumTiles(prevState.rooms, prevExtraTiles) !== this.numTiles) {\n            this.setState({ height: this.calculateInitialHeight() });\n        }\n    }\n\n    public shouldComponentUpdate(nextProps: Readonly<IProps>, nextState: Readonly<IState>): boolean {\n        if (objectHasDiff(this.props, nextProps)) {\n            // Something we don't care to optimize has updated, so update.\n            return true;\n        }\n\n        // Do the same check used on props for state, without the rooms we're going to no-op\n        const prevStateNoRooms = objectExcluding(this.state, [\"rooms\"]);\n        const nextStateNoRooms = objectExcluding(nextState, [\"rooms\"]);\n        if (objectHasDiff(prevStateNoRooms, nextStateNoRooms)) {\n            return true;\n        }\n\n        // If we're supposed to handle extra tiles, take the performance hit and re-render all the\n        // time so we don't have to consider them as part of the visible room optimization.\n        const prevExtraTiles = this.props.extraTiles || [];\n        const nextExtraTiles = nextProps.extraTiles || [];\n        if (prevExtraTiles.length > 0 || nextExtraTiles.length > 0) {\n            return true;\n        }\n\n        // If we're about to update the height of the list, we don't really care about which rooms\n        // are visible or not for no-op purposes, so ensure that the height calculation runs through.\n        if (RoomSublist.calcNumTiles(nextState.rooms, nextExtraTiles) !== this.numTiles) {\n            return true;\n        }\n\n        // Before we go analyzing the rooms, we can see if we're collapsed. If we're collapsed, we don't need\n        // to render anything. We do this after the height check though to ensure that the height gets appropriately\n        // calculated for when/if we become uncollapsed.\n        if (!nextState.isExpanded) {\n            return false;\n        }\n\n        // Quickly double check we're not about to break something due to the number of rooms changing.\n        if (this.state.rooms.length !== nextState.rooms.length) {\n            return true;\n        }\n\n        // Finally, determine if the room update (as presumably that's all that's left) is within\n        // our visible range. If it is, then do a render. If the update is outside our visible range\n        // then we can skip the update.\n        //\n        // We also optimize for order changing here: if the update did happen in our visible range\n        // but doesn't result in the list re-sorting itself then there's no reason for us to update\n        // on our own.\n        const prevSlicedRooms = this.state.rooms.slice(0, this.numVisibleTiles);\n        const nextSlicedRooms = nextState.rooms.slice(0, this.numVisibleTiles);\n        if (arrayHasOrderChange(prevSlicedRooms, nextSlicedRooms)) {\n            return true;\n        }\n\n        // Finally, nothing happened so no-op the update\n        return false;\n    }\n\n    public componentDidMount(): void {\n        this.dispatcherRef = defaultDispatcher.register(this.onAction);\n        RoomListStore.instance.on(LISTS_UPDATE_EVENT, this.onListsUpdated);\n        RoomListStore.instance.on(LISTS_LOADING_EVENT, this.onListsLoading);\n\n        // Using the passive option to not block the main thread\n        // https://developer.mozilla.org/en-US/docs/Web/API/EventTarget/addEventListener#improving_scrolling_performance_with_passive_listeners\n        this.tilesRef.current?.addEventListener(\"scroll\", this.onScrollPrevent, { passive: true });\n    }\n\n    public componentWillUnmount(): void {\n        defaultDispatcher.unregister(this.dispatcherRef);\n        RoomListStore.instance.off(LISTS_UPDATE_EVENT, this.onListsUpdated);\n        RoomListStore.instance.off(LISTS_LOADING_EVENT, this.onListsLoading);\n        this.tilesRef.current?.removeEventListener(\"scroll\", this.onScrollPrevent);\n    }\n\n    private onListsLoading = (tagId: TagID, isLoading: boolean): void => {\n        if (this.props.tagId !== tagId) {\n            return;\n        }\n        this.setState({\n            roomsLoading: isLoading,\n        });\n    };\n\n    private onListsUpdated = (): void => {\n        const stateUpdates = {} as IState;\n\n        const currentRooms = this.state.rooms;\n        const newRooms = arrayFastClone(RoomListStore.instance.orderedLists[this.props.tagId] || []);\n        if (arrayHasOrderChange(currentRooms, newRooms)) {\n            stateUpdates.rooms = newRooms;\n        }\n\n        if (Object.keys(stateUpdates).length > 0) {\n            this.setState(stateUpdates);\n        }\n    };\n\n    private onAction = (payload: ActionPayload): void => {\n        if (payload.action === Action.ViewRoom && payload.show_room_tile && this.state.rooms) {\n            // XXX: we have to do this a tick later because we have incorrect intermediate props during a room change\n            // where we lose the room we are changing from temporarily and then it comes back in an update right after.\n            setTimeout(() => {\n                const roomIndex = this.state.rooms.findIndex((r) => r.roomId === payload.room_id);\n\n                if (!this.state.isExpanded && roomIndex > -1) {\n                    this.toggleCollapsed();\n                }\n                // extend the visible section to include the room if it is entirely invisible\n                if (roomIndex >= this.numVisibleTiles) {\n                    this.layout.visibleTiles = this.layout.tilesWithPadding(roomIndex + 1, MAX_PADDING_HEIGHT);\n                    this.forceUpdate(); // because the layout doesn't trigger a re-render\n                }\n            }, 0);\n        }\n    };\n\n    private applyHeightChange(newHeight: number): void {\n        const heightInTiles = Math.ceil(this.layout.pixelsToTiles(newHeight - this.padding));\n        this.layout.visibleTiles = Math.min(this.numTiles, heightInTiles);\n    }\n\n    private onResize = (\n        e: MouseEvent | TouchEvent,\n        travelDirection: Direction,\n        refToElement: HTMLElement,\n        delta: ResizeDelta,\n    ): void => {\n        const newHeight = this.heightAtStart + delta.height;\n        this.applyHeightChange(newHeight);\n        this.setState({ height: newHeight });\n    };\n\n    private onResizeStart = (): void => {\n        this.heightAtStart = this.state.height;\n        this.setState({ isResizing: true });\n    };\n\n    private onResizeStop = (\n        e: MouseEvent | TouchEvent,\n        travelDirection: Direction,\n        refToElement: HTMLElement,\n        delta: ResizeDelta,\n    ): void => {\n        const newHeight = this.heightAtStart + delta.height;\n        this.applyHeightChange(newHeight);\n        this.setState({ isResizing: false, height: newHeight });\n    };\n\n    private onShowAllClick = async (): Promise<void> => {\n        // read number of visible tiles before we mutate it\n        const numVisibleTiles = this.numVisibleTiles;\n        const newHeight = this.layout.tilesToPixelsWithPadding(this.numTiles, this.padding);\n        this.applyHeightChange(newHeight);\n        this.setState({ height: newHeight }, () => {\n            // focus the top-most new room\n            this.focusRoomTile(numVisibleTiles);\n        });\n    };\n\n    private onShowLessClick = (): void => {\n        const newHeight = this.layout.tilesToPixelsWithPadding(this.layout.defaultVisibleTiles, this.padding);\n        this.applyHeightChange(newHeight);\n        this.setState({ height: newHeight });\n    };\n\n    private focusRoomTile = (index: number): void => {\n        if (!this.sublistRef.current) return;\n        const elements = this.sublistRef.current.querySelectorAll<HTMLDivElement>(\".mx_RoomTile\");\n        const element = elements && elements[index];\n        if (element) {\n            element.focus();\n        }\n    };\n\n    private onOpenMenuClick = (ev: ButtonEvent): void => {\n        ev.preventDefault();\n        ev.stopPropagation();\n        const target = ev.target as HTMLButtonElement;\n        this.setState({ contextMenuPosition: target.getBoundingClientRect() });\n    };\n\n    private onContextMenu = (ev: React.MouseEvent): void => {\n        ev.preventDefault();\n        ev.stopPropagation();\n        this.setState({\n            contextMenuPosition: {\n                left: ev.clientX,\n                top: ev.clientY,\n                height: 0,\n            },\n        });\n    };\n\n    private onCloseMenu = (): void => {\n        this.setState({ contextMenuPosition: undefined });\n    };\n\n    private onUnreadFirstChanged = (): void => {\n        const isUnreadFirst = RoomListStore.instance.getListOrder(this.props.tagId) === ListAlgorithm.Importance;\n        const newAlgorithm = isUnreadFirst ? ListAlgorithm.Natural : ListAlgorithm.Importance;\n        RoomListStore.instance.setListOrder(this.props.tagId, newAlgorithm);\n        this.forceUpdate(); // because if the sublist doesn't have any changes then we will miss the list order change\n    };\n\n    private onTagSortChanged = async (sort: SortAlgorithm): Promise<void> => {\n        RoomListStore.instance.setTagSorting(this.props.tagId, sort);\n        this.forceUpdate();\n    };\n\n    private onMessagePreviewChanged = (): void => {\n        this.layout.showPreviews = !this.layout.showPreviews;\n        this.forceUpdate(); // because the layout doesn't trigger a re-render\n    };\n\n    private onBadgeClick = (ev: React.MouseEvent): void => {\n        ev.preventDefault();\n        ev.stopPropagation();\n\n        let room;\n        if (this.props.tagId === DefaultTagID.Invite) {\n            // switch to first room as that'll be the top of the list for the user\n            room = this.state.rooms && this.state.rooms[0];\n        } else {\n            // find the first room with a count of the same colour as the badge count\n            room = RoomListStore.instance.orderedLists[this.props.tagId].find((r: Room) => {\n                const notifState = this.notificationState.getForRoom(r);\n                return notifState.count > 0 && notifState.level === this.notificationState.level;\n            });\n        }\n\n        if (room) {\n            defaultDispatcher.dispatch<ViewRoomPayload>({\n                action: Action.ViewRoom,\n                room_id: room.roomId,\n                show_room_tile: true, // to make sure the room gets scrolled into view\n                metricsTrigger: \"WebRoomListNotificationBadge\",\n                metricsViaKeyboard: ev.type !== \"click\",\n            });\n        }\n    };\n\n    private onHeaderClick = (): void => {\n        const possibleSticky = this.headerButton.current?.parentElement;\n        const sublist = possibleSticky?.parentElement?.parentElement;\n        const list = sublist?.parentElement?.parentElement;\n        if (!possibleSticky || !list) return;\n\n        // the scrollTop is capped at the height of the header in LeftPanel, the top header is always sticky\n        const listScrollTop = Math.round(list.scrollTop);\n        const isAtTop = listScrollTop <= Math.round(HEADER_HEIGHT);\n        const isAtBottom = listScrollTop >= Math.round(list.scrollHeight - list.offsetHeight);\n        const isStickyTop = possibleSticky.classList.contains(\"mx_RoomSublist_headerContainer_stickyTop\");\n        const isStickyBottom = possibleSticky.classList.contains(\"mx_RoomSublist_headerContainer_stickyBottom\");\n\n        if ((isStickyBottom && !isAtBottom) || (isStickyTop && !isAtTop)) {\n            // is sticky - jump to list\n            sublist.scrollIntoView({ behavior: \"smooth\" });\n        } else {\n            // on screen - toggle collapse\n            const isExpanded = this.state.isExpanded;\n            this.toggleCollapsed();\n            // if the bottom list is collapsed then scroll it in so it doesn't expand off screen\n            if (!isExpanded && isStickyBottom) {\n                setTimeout(() => {\n                    sublist.scrollIntoView({ behavior: \"smooth\" });\n                }, 0);\n            }\n        }\n    };\n\n    private toggleCollapsed = (): void => {\n        if (this.props.forceExpanded) return;\n        this.layout.isCollapsed = this.state.isExpanded;\n        this.setState({ isExpanded: !this.layout.isCollapsed });\n        if (this.props.onListCollapse) {\n            this.props.onListCollapse(!this.layout.isCollapsed);\n        }\n    };\n\n    private onHeaderKeyDown = (ev: React.KeyboardEvent): void => {\n        const action = getKeyBindingsManager().getRoomListAction(ev);\n        switch (action) {\n            case KeyBindingAction.CollapseRoomListSection:\n                ev.stopPropagation();\n                if (this.state.isExpanded) {\n                    // Collapse the room sublist if it isn't already\n                    this.toggleCollapsed();\n                }\n                break;\n            case KeyBindingAction.ExpandRoomListSection: {\n                ev.stopPropagation();\n                if (!this.state.isExpanded) {\n                    // Expand the room sublist if it isn't already\n                    this.toggleCollapsed();\n                } else if (this.sublistRef.current) {\n                    // otherwise focus the first room\n                    const element = this.sublistRef.current.querySelector(\".mx_RoomTile\") as HTMLDivElement;\n                    if (element) {\n                        element.focus();\n                    }\n                }\n                break;\n            }\n        }\n    };\n\n    private onKeyDown = (ev: React.KeyboardEvent): void => {\n        const action = getKeyBindingsManager().getAccessibilityAction(ev);\n        switch (action) {\n            // On ArrowLeft go to the sublist header\n            case KeyBindingAction.ArrowLeft:\n                ev.stopPropagation();\n                this.headerButton.current?.focus();\n                break;\n            // Consume ArrowRight so it doesn't cause focus to get sent to composer\n            case KeyBindingAction.ArrowRight:\n                ev.stopPropagation();\n        }\n    };\n\n    private renderVisibleTiles(): React.ReactElement[] {\n        if (!this.state.isExpanded && !this.props.forceExpanded) {\n            // don't waste time on rendering\n            return [];\n        }\n\n        const tiles: React.ReactElement[] = [];\n\n        if (this.state.rooms) {\n            let visibleRooms = this.state.rooms;\n            if (!this.props.forceExpanded) {\n                visibleRooms = visibleRooms.slice(0, this.numVisibleTiles);\n            }\n\n            for (const room of visibleRooms) {\n                tiles.push(\n                    <RoomTile\n                        room={room}\n                        key={`room-${room.roomId}`}\n                        showMessagePreview={this.layout.showPreviews}\n                        isMinimized={this.props.isMinimized}\n                        tag={this.props.tagId}\n                    />,\n                );\n            }\n        }\n\n        if (this.extraTiles) {\n            // HACK: We break typing here, but this 'extra tiles' property shouldn't exist.\n            (tiles as any[]).push(...this.extraTiles);\n        }\n\n        // We only have to do this because of the extra tiles. We do it conditionally\n        // to avoid spending cycles on slicing. It's generally fine to do this though\n        // as users are unlikely to have more than a handful of tiles when the extra\n        // tiles are used.\n        if (tiles.length > this.numVisibleTiles && !this.props.forceExpanded) {\n            return tiles.slice(0, this.numVisibleTiles);\n        }\n\n        return tiles;\n    }\n\n    private renderMenu(): ReactNode {\n        if (this.props.tagId === DefaultTagID.Suggested) return null; // not sortable\n\n        let contextMenu: JSX.Element | undefined;\n        if (this.state.contextMenuPosition) {\n            const isAlphabetical = RoomListStore.instance.getTagSorting(this.props.tagId) === SortAlgorithm.Alphabetic;\n            const isUnreadFirst = RoomListStore.instance.getListOrder(this.props.tagId) === ListAlgorithm.Importance;\n\n            // Invites don't get some nonsense options, so only add them if we have to.\n            let otherSections: JSX.Element | undefined;\n            if (this.props.tagId !== DefaultTagID.Invite) {\n                otherSections = (\n                    <React.Fragment>\n                        <hr />\n                        <fieldset>\n                            <legend className=\"mx_RoomSublist_contextMenu_title\">{_t(\"common|appearance\")}</legend>\n                            <StyledMenuItemCheckbox\n                                onClose={this.onCloseMenu}\n                                onChange={this.onUnreadFirstChanged}\n                                checked={isUnreadFirst}\n                            >\n                                {_t(\"room_list|sort_unread_first\")}\n                            </StyledMenuItemCheckbox>\n                            <StyledMenuItemCheckbox\n                                onClose={this.onCloseMenu}\n                                onChange={this.onMessagePreviewChanged}\n                                checked={this.layout.showPreviews}\n                            >\n                                {_t(\"room_list|show_previews\")}\n                            </StyledMenuItemCheckbox>\n                        </fieldset>\n                    </React.Fragment>\n                );\n            }\n\n            contextMenu = (\n                <ContextMenu\n                    chevronFace={ChevronFace.None}\n                    left={this.state.contextMenuPosition.left}\n                    top={this.state.contextMenuPosition.top + this.state.contextMenuPosition.height}\n                    onFinished={this.onCloseMenu}\n                >\n                    <div className=\"mx_RoomSublist_contextMenu\">\n                        <fieldset>\n                            <legend className=\"mx_RoomSublist_contextMenu_title\">{_t(\"room_list|sort_by\")}</legend>\n                            <StyledMenuItemRadio\n                                onClose={this.onCloseMenu}\n                                onChange={() => this.onTagSortChanged(SortAlgorithm.Recent)}\n                                checked={!isAlphabetical}\n                                name={`mx_${this.props.tagId}_sortBy`}\n                            >\n                                {_t(\"room_list|sort_by_activity\")}\n                            </StyledMenuItemRadio>\n                            <StyledMenuItemRadio\n                                onClose={this.onCloseMenu}\n                                onChange={() => this.onTagSortChanged(SortAlgorithm.Alphabetic)}\n                                checked={isAlphabetical}\n                                name={`mx_${this.props.tagId}_sortBy`}\n                            >\n                                {_t(\"room_list|sort_by_alphabet\")}\n                            </StyledMenuItemRadio>\n                        </fieldset>\n                        {otherSections}\n                    </div>\n                </ContextMenu>\n            );\n        }\n\n        return (\n            <React.Fragment>\n                <ContextMenuTooltipButton\n                    className=\"mx_RoomSublist_menuButton\"\n                    onClick={this.onOpenMenuClick}\n                    title={_t(\"room_list|sublist_options\")}\n                    isExpanded={!!this.state.contextMenuPosition}\n                >\n                    <OverflowHorizontalIcon />\n                </ContextMenuTooltipButton>\n                {contextMenu}\n            </React.Fragment>\n        );\n    }\n\n    private renderHeader(): React.ReactElement {\n        return (\n            <RovingTabIndexWrapper inputRef={this.headerButton}>\n                {({ onFocus, isActive, ref }) => {\n                    const tabIndex = isActive ? 0 : -1;\n\n                    let ariaLabel = _t(\"a11y_jump_first_unread_room\");\n                    if (this.props.tagId === DefaultTagID.Invite) {\n                        ariaLabel = _t(\"a11y|jump_first_invite\");\n                    }\n\n                    const badge = (\n                        <NotificationBadge\n                            hideIfDot={true}\n                            notification={this.notificationState}\n                            onClick={this.onBadgeClick}\n                            tabIndex={tabIndex}\n                            aria-label={ariaLabel}\n                            showUnsentTooltip={true}\n                        />\n                    );\n\n                    let addRoomButton: JSX.Element | undefined;\n                    if (this.props.AuxButtonComponent) {\n                        const AuxButtonComponent = this.props.AuxButtonComponent;\n                        addRoomButton = <AuxButtonComponent tabIndex={tabIndex} />;\n                    }\n\n                    const collapsed = !this.state.isExpanded && !this.props.forceExpanded;\n                    const classes = classNames({\n                        mx_RoomSublist_headerContainer: true,\n                        mx_RoomSublist_headerContainer_withAux: !!addRoomButton,\n                    });\n\n                    const badgeContainer = <div className=\"mx_RoomSublist_badgeContainer\">{badge}</div>;\n\n                    // Note: the addRoomButton conditionally gets moved around\n                    // the DOM depending on whether or not the list is minimized.\n                    // If we're minimized, we want it below the header so it\n                    // doesn't become sticky.\n                    // The same applies to the notification badge.\n                    return (\n                        <div\n                            className={classes}\n                            onKeyDown={this.onHeaderKeyDown}\n                            onFocus={onFocus}\n                            aria-label={this.props.label}\n                            role=\"treeitem\"\n                            aria-expanded={this.state.isExpanded}\n                            aria-level={1}\n                            aria-selected=\"false\"\n                        >\n                            <div className=\"mx_RoomSublist_stickableContainer\">\n                                <div className=\"mx_RoomSublist_stickable\">\n                                    <AccessibleButton\n                                        onFocus={onFocus}\n                                        ref={ref}\n                                        tabIndex={tabIndex}\n                                        className=\"mx_RoomSublist_headerText\"\n                                        aria-expanded={this.state.isExpanded}\n                                        onClick={this.onHeaderClick}\n                                        onContextMenu={this.onContextMenu}\n                                        title={this.props.isMinimized ? this.props.label : undefined}\n                                    >\n                                        <span className=\"mx_RoomSublist_collapseBtn\">\n                                            {collapsed ? <ChevronRightIcon /> : <ChevronDownIcon />}\n                                        </span>\n                                        <span id={getLabelId(this.props.tagId)}>{this.props.label}</span>\n                                    </AccessibleButton>\n                                    {this.renderMenu()}\n                                    {this.props.isMinimized ? null : badgeContainer}\n                                    {this.props.isMinimized ? null : addRoomButton}\n                                </div>\n                            </div>\n                            {this.props.isMinimized ? badgeContainer : null}\n                            {this.props.isMinimized ? addRoomButton : null}\n                        </div>\n                    );\n                }}\n            </RovingTabIndexWrapper>\n        );\n    }\n\n    private onScrollPrevent(e: Event): void {\n        // the RoomTile calls scrollIntoView and the browser may scroll a div we do not wish to be scrollable\n        // this fixes https://github.com/vector-im/element-web/issues/14413\n        (e.target as HTMLDivElement).scrollTop = 0;\n    }\n\n    public render(): React.ReactElement {\n        const visibleTiles = this.renderVisibleTiles();\n        const hidden = !this.state.rooms.length && !this.props.extraTiles?.length && this.props.alwaysVisible !== true;\n        const classes = classNames({\n            mx_RoomSublist: true,\n            mx_RoomSublist_hasMenuOpen: !!this.state.contextMenuPosition,\n            mx_RoomSublist_minimized: this.props.isMinimized,\n            mx_RoomSublist_hidden: hidden,\n        });\n\n        let content: JSX.Element | undefined;\n        if (this.state.roomsLoading) {\n            content = <div className=\"mx_RoomSublist_skeletonUI\" />;\n        } else if (visibleTiles.length > 0 && this.props.forceExpanded) {\n            content = (\n                <div className=\"mx_RoomSublist_resizeBox mx_RoomSublist_resizeBox_forceExpanded\">\n                    <div className=\"mx_RoomSublist_tiles\" ref={this.tilesRef}>\n                        {visibleTiles}\n                    </div>\n                </div>\n            );\n        } else if (visibleTiles.length > 0) {\n            const layout = this.layout; // to shorten calls\n\n            const minTiles = Math.min(layout.minVisibleTiles, this.numTiles);\n            const showMoreAtMinHeight = minTiles < this.numTiles;\n            const minHeightPadding = RESIZE_HANDLE_HEIGHT + (showMoreAtMinHeight ? SHOW_N_BUTTON_HEIGHT : 0);\n            const minTilesPx = layout.tilesToPixelsWithPadding(minTiles, minHeightPadding);\n            const maxTilesPx = layout.tilesToPixelsWithPadding(this.numTiles, this.padding);\n            const showMoreBtnClasses = classNames({\n                mx_RoomSublist_showNButton: true,\n            });\n\n            // If we're hiding rooms, show a 'show more' button to the user. This button\n            // floats above the resize handle, if we have one present. If the user has all\n            // tiles visible, it becomes 'show less'.\n            let showNButton: JSX.Element | undefined;\n\n            if (maxTilesPx > this.state.height) {\n                // the height of all the tiles is greater than the section height: we need a 'show more' button\n                const nonPaddedHeight = this.state.height - RESIZE_HANDLE_HEIGHT - SHOW_N_BUTTON_HEIGHT;\n                const amountFullyShown = Math.floor(nonPaddedHeight / this.layout.tileHeight);\n                const numMissing = this.numTiles - amountFullyShown;\n                const label = _t(\"room_list|show_n_more\", { count: numMissing });\n                let showMoreText: ReactNode = <span className=\"mx_RoomSublist_showNButtonText\">{label}</span>;\n                if (this.props.isMinimized) showMoreText = null;\n                showNButton = (\n                    <RovingAccessibleButton\n                        role=\"treeitem\"\n                        onClick={this.onShowAllClick}\n                        className={showMoreBtnClasses}\n                        aria-label={label}\n                    >\n                        <ChevronDownIcon className=\"mx_RoomSublist_showNButtonChevron\" />\n                        {showMoreText}\n                    </RovingAccessibleButton>\n                );\n            } else if (this.numTiles > this.layout.defaultVisibleTiles) {\n                // we have all tiles visible - add a button to show less\n                const label = _t(\"room_list|show_less\");\n                let showLessText: ReactNode = <span className=\"mx_RoomSublist_showNButtonText\">{label}</span>;\n                if (this.props.isMinimized) showLessText = null;\n                showNButton = (\n                    <RovingAccessibleButton\n                        role=\"treeitem\"\n                        onClick={this.onShowLessClick}\n                        className={showMoreBtnClasses}\n                        aria-label={label}\n                    >\n                        <ChevronUpIcon className=\"mx_RoomSublist_showNButtonChevron\" />\n                        {showLessText}\n                    </RovingAccessibleButton>\n                );\n            }\n\n            // Figure out if we need a handle\n            const handles: Enable = {\n                bottom: true, // the only one we need, but the others must be explicitly false\n                bottomLeft: false,\n                bottomRight: false,\n                left: false,\n                right: false,\n                top: false,\n                topLeft: false,\n                topRight: false,\n            };\n            if (layout.visibleTiles >= this.numTiles && this.numTiles <= layout.minVisibleTiles) {\n                // we're at a minimum, don't have a bottom handle\n                handles.bottom = false;\n            }\n\n            // We have to account for padding so we can accommodate a 'show more' button and\n            // the resize handle, which are pinned to the bottom of the container. This is the\n            // easiest way to have a resize handle below the button as otherwise we're writing\n            // our own resize handling and that doesn't sound fun.\n            //\n            // The layout class has some helpers for dealing with padding, as we don't want to\n            // apply it in all cases. If we apply it in all cases, the resizing feels like it\n            // goes backwards and can become wildly incorrect (visibleTiles says 18 when there's\n            // only mathematically 7 possible).\n\n            const handleWrapperClasses = classNames({\n                mx_RoomSublist_resizerHandles: true,\n                mx_RoomSublist_resizerHandles_showNButton: !!showNButton,\n            });\n\n            content = (\n                <React.Fragment>\n                    <Resizable\n                        size={{ height: this.state.height } as any}\n                        minHeight={minTilesPx}\n                        maxHeight={maxTilesPx}\n                        onResizeStart={this.onResizeStart}\n                        onResizeStop={this.onResizeStop}\n                        onResize={this.onResize}\n                        handleWrapperClass={handleWrapperClasses}\n                        handleClasses={{ bottom: \"mx_RoomSublist_resizerHandle\" }}\n                        className=\"mx_RoomSublist_resizeBox\"\n                        enable={handles}\n                    >\n                        <div className=\"mx_RoomSublist_tiles\" ref={this.tilesRef}>\n                            {visibleTiles}\n                        </div>\n                        {showNButton}\n                    </Resizable>\n                </React.Fragment>\n            );\n        } else if (this.props.showSkeleton && this.state.isExpanded) {\n            content = <div className=\"mx_RoomSublist_skeletonUI\" />;\n        }\n\n        return (\n            <div\n                ref={this.sublistRef}\n                className={classes}\n                role=\"group\"\n                aria-hidden={hidden}\n                aria-labelledby={getLabelId(this.props.tagId)}\n                onKeyDown={this.onKeyDown}\n            >\n                {this.renderHeader()}\n                {content}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// This is intended to fix re-resizer because of its unguarded `instanceof TouchEvent` checks.\nexport function polyfillTouchEvent(): void {\n    // Firefox doesn't have touch events without touch devices being present, so create a fake\n    // one we can rely on lying about.\n    if (!window.TouchEvent) {\n        // We have no intention of actually using this, so just lie.\n        window.TouchEvent = class TouchEvent extends UIEvent {\n            public get altKey(): boolean {\n                return false;\n            }\n            public get changedTouches(): any {\n                return [];\n            }\n            public get ctrlKey(): boolean {\n                return false;\n            }\n            public get metaKey(): boolean {\n                return false;\n            }\n            public get shiftKey(): boolean {\n                return false;\n            }\n            public get targetTouches(): any {\n                return [];\n            }\n            public get touches(): any {\n                return [];\n            }\n            public get rotation(): number {\n                return 0.0;\n            }\n            public get scale(): number {\n                return 0.0;\n            }\n            public constructor(eventType: string, params?: any) {\n                super(eventType, params);\n            }\n        };\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type FC } from \"react\";\n\nimport type { Call } from \"../../../models/Call\";\nimport { _t } from \"../../../languageHandler\";\nimport { useConnectionState, useParticipantCount } from \"../../../hooks/useCall\";\nimport { ConnectionState } from \"../../../models/Call\";\nimport { LiveContentSummary, LiveContentType } from \"./LiveContentSummary\";\n\ninterface Props {\n    call: Call;\n}\n\nexport const RoomTileCallSummary: FC<Props> = ({ call }) => {\n    let text: string;\n    let active: boolean;\n\n    switch (useConnectionState(call)) {\n        case ConnectionState.Disconnected:\n            text = _t(\"common|video\");\n            active = false;\n            break;\n        case ConnectionState.Connected:\n        case ConnectionState.Disconnecting:\n            text = _t(\"common|joined\");\n            active = true;\n            break;\n    }\n\n    return (\n        <LiveContentSummary\n            type={LiveContentType.Video}\n            text={text}\n            active={active}\n            participantCount={useParticipantCount(call)}\n        />\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport classNames from \"classnames\";\nimport { ThreadsIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { type MessagePreview } from \"../../../stores/room-list/MessagePreviewStore\";\nimport { type Call } from \"../../../models/Call\";\nimport { RoomTileCallSummary } from \"./RoomTileCallSummary\";\n\ninterface Props {\n    call: Call | null;\n    messagePreview: MessagePreview | null;\n    roomId: string;\n    showMessagePreview: boolean;\n}\n\nconst messagePreviewId = (roomId: string): string => `mx_RoomTile_messagePreview_${roomId}`;\n\nexport const RoomTileSubtitle: React.FC<Props> = ({ call, messagePreview, roomId, showMessagePreview }) => {\n    if (call) {\n        return (\n            <div className=\"mx_RoomTile_subtitle\">\n                <RoomTileCallSummary call={call} />\n            </div>\n        );\n    }\n\n    if (showMessagePreview && messagePreview) {\n        const className = classNames(\"mx_RoomTile_subtitle\", {\n            \"mx_RoomTile_subtitle--thread-reply\": messagePreview.isThreadReply,\n        });\n\n        const icon = messagePreview.isThreadReply ? <ThreadsIcon className=\"mx_Icon mx_Icon_12\" /> : null;\n\n        return (\n            <div className={className} id={messagePreviewId(roomId)} title={messagePreview.text}>\n                {icon}\n                <span className=\"mx_RoomTile_subtitle_text\">{messagePreview.text}</span>\n            </div>\n        );\n    }\n\n    return null;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2015-2017 , 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef } from \"react\";\nimport { type Room, RoomEvent } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport classNames from \"classnames\";\nimport { OverflowHorizontalIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport type { Call } from \"../../../models/Call\";\nimport { RovingTabIndexWrapper } from \"../../../accessibility/RovingTabIndex\";\nimport AccessibleButton, { type ButtonEvent } from \"../../views/elements/AccessibleButton\";\nimport defaultDispatcher from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { _t } from \"../../../languageHandler\";\nimport { ChevronFace, ContextMenuTooltipButton, type MenuProps } from \"../../structures/ContextMenu\";\nimport { DefaultTagID, type TagID } from \"../../../stores/room-list/models\";\nimport { type MessagePreview, MessagePreviewStore } from \"../../../stores/room-list/MessagePreviewStore\";\nimport DecoratedRoomAvatar from \"../avatars/DecoratedRoomAvatar\";\nimport { RoomNotifState } from \"../../../RoomNotifs\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { RoomNotificationContextMenu } from \"../context_menus/RoomNotificationContextMenu\";\nimport NotificationBadge from \"./NotificationBadge\";\nimport { type ActionPayload } from \"../../../dispatcher/payloads\";\nimport { RoomNotificationStateStore } from \"../../../stores/notifications/RoomNotificationStateStore\";\nimport { type NotificationState, NotificationStateEvents } from \"../../../stores/notifications/NotificationState\";\nimport { EchoChamber } from \"../../../stores/local-echo/EchoChamber\";\nimport { CachedRoomKey, type RoomEchoChamber } from \"../../../stores/local-echo/RoomEchoChamber\";\nimport { PROPERTY_UPDATED } from \"../../../stores/local-echo/GenericEchoChamber\";\nimport PosthogTrackers from \"../../../PosthogTrackers\";\nimport { type ViewRoomPayload } from \"../../../dispatcher/payloads/ViewRoomPayload\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { RoomGeneralContextMenu } from \"../context_menus/RoomGeneralContextMenu\";\nimport { CallStore, CallStoreEvent } from \"../../../stores/CallStore\";\nimport { SdkContextClass } from \"../../../contexts/SDKContext\";\nimport { RoomTileSubtitle } from \"./RoomTileSubtitle\";\nimport { shouldShowComponent } from \"../../../customisations/helpers/UIComponents\";\nimport { UIComponent } from \"../../../settings/UIFeature\";\nimport { isKnockDenied } from \"../../../utils/membership\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { getNotificationIcon } from \"../dialogs/spotlight/RoomResultContextMenus.tsx\";\n\ninterface Props {\n    room: Room;\n    showMessagePreview: boolean;\n    isMinimized: boolean;\n    tag: TagID;\n}\n\ntype PartialDOMRect = Pick<DOMRect, \"left\" | \"bottom\">;\n\ninterface State {\n    selected: boolean;\n    notificationsMenuPosition: PartialDOMRect | null;\n    generalMenuPosition: PartialDOMRect | null;\n    call: Call | null;\n    messagePreview: MessagePreview | null;\n}\n\nconst messagePreviewId = (roomId: string): string => `mx_RoomTile_messagePreview_${roomId}`;\n\nexport const contextMenuBelow = (elementRect: PartialDOMRect): MenuProps => {\n    // align the context menu's icons with the icon which opened the context menu\n    const left = elementRect.left + window.scrollX - 9;\n    const top = elementRect.bottom + window.scrollY + 17;\n    const chevronFace = ChevronFace.None;\n    return { left, top, chevronFace };\n};\n\nclass RoomTile extends React.PureComponent<Props, State> {\n    private dispatcherRef?: string;\n    private roomTileRef = createRef<HTMLDivElement>();\n    private notificationState: NotificationState;\n    private roomProps: RoomEchoChamber;\n\n    public constructor(props: Props) {\n        super(props);\n\n        this.state = {\n            selected: SdkContextClass.instance.roomViewStore.getRoomId() === this.props.room.roomId,\n            notificationsMenuPosition: null,\n            generalMenuPosition: null,\n            call: CallStore.instance.getCall(this.props.room.roomId),\n            // generatePreview() will return nothing if the user has previews disabled\n            messagePreview: null,\n        };\n\n        this.notificationState = RoomNotificationStateStore.instance.getRoomState(this.props.room);\n        this.roomProps = EchoChamber.forRoom(this.props.room);\n    }\n\n    private onRoomNameUpdate = (room: Room): void => {\n        this.forceUpdate();\n    };\n\n    private onNotificationUpdate = (): void => {\n        this.forceUpdate(); // notification state changed - update\n    };\n\n    private onRoomPropertyUpdate = (property: CachedRoomKey): void => {\n        if (property === CachedRoomKey.NotificationVolume) this.onNotificationUpdate();\n        // else ignore - not important for this tile\n    };\n\n    private get showContextMenu(): boolean {\n        return (\n            this.props.tag !== DefaultTagID.Invite &&\n            this.props.room.getMyMembership() !== KnownMembership.Knock &&\n            !isKnockDenied(this.props.room) &&\n            shouldShowComponent(UIComponent.RoomOptionsMenu)\n        );\n    }\n\n    private get showMessagePreview(): boolean {\n        return !this.props.isMinimized && this.props.showMessagePreview;\n    }\n\n    public componentDidUpdate(prevProps: Readonly<Props>, prevState: Readonly<State>): void {\n        const showMessageChanged = prevProps.showMessagePreview !== this.props.showMessagePreview;\n        const minimizedChanged = prevProps.isMinimized !== this.props.isMinimized;\n        if (showMessageChanged || minimizedChanged) {\n            this.generatePreview();\n        }\n        if (prevProps.room?.roomId !== this.props.room?.roomId) {\n            MessagePreviewStore.instance.off(\n                MessagePreviewStore.getPreviewChangedEventName(prevProps.room),\n                this.onRoomPreviewChanged,\n            );\n            MessagePreviewStore.instance.on(\n                MessagePreviewStore.getPreviewChangedEventName(this.props.room),\n                this.onRoomPreviewChanged,\n            );\n            prevProps.room?.off(RoomEvent.Name, this.onRoomNameUpdate);\n            this.props.room?.on(RoomEvent.Name, this.onRoomNameUpdate);\n        }\n    }\n\n    public componentDidMount(): void {\n        this.generatePreview();\n\n        // when we're first rendered (or our sublist is expanded) make sure we are visible if we're active\n        if (this.state.selected) {\n            this.scrollIntoView();\n        }\n\n        SdkContextClass.instance.roomViewStore.addRoomListener(this.props.room.roomId, this.onActiveRoomUpdate);\n        this.dispatcherRef = defaultDispatcher.register(this.onAction);\n        MessagePreviewStore.instance.on(\n            MessagePreviewStore.getPreviewChangedEventName(this.props.room),\n            this.onRoomPreviewChanged,\n        );\n        this.notificationState.on(NotificationStateEvents.Update, this.onNotificationUpdate);\n        this.roomProps.on(PROPERTY_UPDATED, this.onRoomPropertyUpdate);\n        this.props.room.on(RoomEvent.Name, this.onRoomNameUpdate);\n        CallStore.instance.on(CallStoreEvent.Call, this.onCallChanged);\n\n        // Recalculate the call for this room, since it could've changed between\n        // construction and mounting\n        this.setState({ call: CallStore.instance.getCall(this.props.room.roomId) });\n    }\n\n    public componentWillUnmount(): void {\n        SdkContextClass.instance.roomViewStore.removeRoomListener(this.props.room.roomId, this.onActiveRoomUpdate);\n        MessagePreviewStore.instance.off(\n            MessagePreviewStore.getPreviewChangedEventName(this.props.room),\n            this.onRoomPreviewChanged,\n        );\n        this.props.room.off(RoomEvent.Name, this.onRoomNameUpdate);\n        defaultDispatcher.unregister(this.dispatcherRef);\n        this.notificationState.off(NotificationStateEvents.Update, this.onNotificationUpdate);\n        this.roomProps.off(PROPERTY_UPDATED, this.onRoomPropertyUpdate);\n        CallStore.instance.off(CallStoreEvent.Call, this.onCallChanged);\n    }\n\n    private onAction = (payload: ActionPayload): void => {\n        if (\n            payload.action === Action.ViewRoom &&\n            payload.room_id === this.props.room.roomId &&\n            payload.show_room_tile\n        ) {\n            setTimeout(() => {\n                this.scrollIntoView();\n            });\n        }\n    };\n\n    private onRoomPreviewChanged = (room: Room): void => {\n        if (this.props.room && room.roomId === this.props.room.roomId) {\n            this.generatePreview();\n        }\n    };\n\n    private onCallChanged = (call: Call, roomId: string): void => {\n        if (roomId === this.props.room?.roomId) this.setState({ call });\n    };\n\n    private async generatePreview(): Promise<void> {\n        if (!this.showMessagePreview) {\n            return;\n        }\n\n        const messagePreview =\n            (await MessagePreviewStore.instance.getPreviewForRoom(this.props.room, this.props.tag)) ?? null;\n        this.setState({ messagePreview });\n    }\n\n    private scrollIntoView = (): void => {\n        if (!this.roomTileRef.current) return;\n        this.roomTileRef.current.scrollIntoView({\n            block: \"nearest\",\n            behavior: \"auto\",\n        });\n    };\n\n    private onTileClick = async (ev: ButtonEvent): Promise<void> => {\n        ev.preventDefault();\n        ev.stopPropagation();\n\n        const action = getKeyBindingsManager().getAccessibilityAction(ev as React.KeyboardEvent);\n        const clearSearch = ([KeyBindingAction.Enter, KeyBindingAction.Space] as Array<string | undefined>).includes(\n            action,\n        );\n\n        defaultDispatcher.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            show_room_tile: true, // make sure the room is visible in the list\n            room_id: this.props.room.roomId,\n            clear_search: clearSearch,\n            metricsTrigger: \"RoomList\",\n            metricsViaKeyboard: ev.type !== \"click\",\n        });\n    };\n\n    private onActiveRoomUpdate = (isActive: boolean): void => {\n        this.setState({ selected: isActive });\n    };\n\n    private onNotificationsMenuOpenClick = (ev: ButtonEvent): void => {\n        ev.preventDefault();\n        ev.stopPropagation();\n        const target = ev.target as HTMLButtonElement;\n        this.setState({ notificationsMenuPosition: target.getBoundingClientRect() });\n\n        PosthogTrackers.trackInteraction(\"WebRoomListRoomTileNotificationsMenu\", ev);\n    };\n\n    private onCloseNotificationsMenu = (): void => {\n        this.setState({ notificationsMenuPosition: null });\n    };\n\n    private onGeneralMenuOpenClick = (ev: ButtonEvent): void => {\n        ev.preventDefault();\n        ev.stopPropagation();\n        const target = ev.target as HTMLButtonElement;\n        this.setState({ generalMenuPosition: target.getBoundingClientRect() });\n    };\n\n    private onContextMenu = (ev: React.MouseEvent): void => {\n        // If we don't have a context menu to show, ignore the action.\n        if (!this.showContextMenu) return;\n\n        ev.preventDefault();\n        ev.stopPropagation();\n        this.setState({\n            generalMenuPosition: {\n                left: ev.clientX,\n                bottom: ev.clientY,\n            },\n        });\n    };\n\n    private onCloseGeneralMenu = (): void => {\n        this.setState({ generalMenuPosition: null });\n    };\n\n    private renderNotificationsMenu(isActive: boolean): React.ReactElement | null {\n        if (\n            MatrixClientPeg.safeGet().isGuest() ||\n            this.props.tag === DefaultTagID.Archived ||\n            !this.showContextMenu ||\n            this.props.isMinimized\n        ) {\n            // the menu makes no sense in these cases so do not show one\n            return null;\n        }\n\n        const state = this.roomProps.notificationVolume;\n\n        const classes = classNames(\"mx_RoomTile_notificationsButton\", {\n            // Only show the icon by default if the room is overridden to muted.\n            // TODO: [FTUE Notifications] Probably need to detect global mute state\n            mx_RoomTile_notificationsButton_show: state === RoomNotifState.Mute,\n        });\n\n        return (\n            <React.Fragment>\n                <ContextMenuTooltipButton\n                    className={classes}\n                    onClick={this.onNotificationsMenuOpenClick}\n                    title={_t(\"room_list|notification_options\")}\n                    isExpanded={!!this.state.notificationsMenuPosition}\n                    tabIndex={isActive ? 0 : -1}\n                >\n                    {getNotificationIcon(state!)}\n                </ContextMenuTooltipButton>\n                {this.state.notificationsMenuPosition && (\n                    <RoomNotificationContextMenu\n                        {...contextMenuBelow(this.state.notificationsMenuPosition)}\n                        onFinished={this.onCloseNotificationsMenu}\n                        room={this.props.room}\n                    />\n                )}\n            </React.Fragment>\n        );\n    }\n\n    private renderGeneralMenu(): React.ReactElement | null {\n        if (!this.showContextMenu) return null; // no menu to show\n        return (\n            <React.Fragment>\n                <ContextMenuTooltipButton\n                    className=\"mx_RoomTile_menuButton\"\n                    onClick={this.onGeneralMenuOpenClick}\n                    title={_t(\"room|context_menu|title\")}\n                    isExpanded={!!this.state.generalMenuPosition}\n                >\n                    <OverflowHorizontalIcon />\n                </ContextMenuTooltipButton>\n                {this.state.generalMenuPosition && (\n                    <RoomGeneralContextMenu\n                        {...contextMenuBelow(this.state.generalMenuPosition)}\n                        onFinished={this.onCloseGeneralMenu}\n                        room={this.props.room}\n                        onPostFavoriteClick={(ev: ButtonEvent) =>\n                            PosthogTrackers.trackInteraction(\"WebRoomListRoomTileContextMenuFavouriteToggle\", ev)\n                        }\n                        onPostInviteClick={(ev: ButtonEvent) =>\n                            PosthogTrackers.trackInteraction(\"WebRoomListRoomTileContextMenuInviteItem\", ev)\n                        }\n                        onPostSettingsClick={(ev: ButtonEvent) =>\n                            PosthogTrackers.trackInteraction(\"WebRoomListRoomTileContextMenuSettingsItem\", ev)\n                        }\n                        onPostLeaveClick={(ev: ButtonEvent) =>\n                            PosthogTrackers.trackInteraction(\"WebRoomListRoomTileContextMenuLeaveItem\", ev)\n                        }\n                        onPostMarkAsReadClick={(ev: ButtonEvent) =>\n                            PosthogTrackers.trackInteraction(\"WebRoomListRoomTileContextMenuMarkRead\", ev)\n                        }\n                        onPostMarkAsUnreadClick={(ev: ButtonEvent) =>\n                            PosthogTrackers.trackInteraction(\"WebRoomListRoomTileContextMenuMarkUnread\", ev)\n                        }\n                    />\n                )}\n            </React.Fragment>\n        );\n    }\n\n    /**\n     * RoomTile has a subtile if one of the following applies:\n     * - there is a call\n     * - message previews are enabled and there is a previewable message\n     */\n    private get shouldRenderSubtitle(): boolean {\n        return !!this.state.call || (this.props.showMessagePreview && !!this.state.messagePreview);\n    }\n\n    public render(): React.ReactElement {\n        const classes = classNames({\n            mx_RoomTile: true,\n            mx_RoomTile_sticky:\n                SettingsStore.getValue(\"feature_ask_to_join\") &&\n                (this.props.room.getMyMembership() === KnownMembership.Knock || isKnockDenied(this.props.room)),\n            mx_RoomTile_selected: this.state.selected,\n            mx_RoomTile_hasMenuOpen: !!(this.state.generalMenuPosition || this.state.notificationsMenuPosition),\n            mx_RoomTile_minimized: this.props.isMinimized,\n        });\n\n        let name = this.props.room.name;\n        if (typeof name !== \"string\") name = \"\";\n        name = name.replace(\":\", \":\\u200b\"); // add a zero-width space to allow linewrapping after the colon\n\n        let badge: React.ReactNode;\n        if (!this.props.isMinimized && this.notificationState) {\n            // aria-hidden because we summarise the unread count/highlight status in a manual aria-label below\n            badge = (\n                <div className=\"mx_RoomTile_badgeContainer\" aria-hidden=\"true\">\n                    <NotificationBadge notification={this.notificationState} roomId={this.props.room.roomId} />\n                </div>\n            );\n        }\n\n        const subtitle = this.shouldRenderSubtitle ? (\n            <RoomTileSubtitle\n                call={this.state.call}\n                messagePreview={this.state.messagePreview}\n                roomId={this.props.room.roomId}\n                showMessagePreview={this.props.showMessagePreview}\n            />\n        ) : null;\n\n        const titleClasses = classNames({\n            mx_RoomTile_title: true,\n            mx_RoomTile_titleWithSubtitle: !!subtitle,\n            mx_RoomTile_titleHasUnreadEvents: this.notificationState.isUnread,\n        });\n\n        const titleContainer = this.props.isMinimized ? null : (\n            <div className=\"mx_RoomTile_titleContainer\">\n                <div title={name} className={titleClasses} tabIndex={-1}>\n                    <span dir=\"auto\">{name}</span>\n                </div>\n                {subtitle}\n            </div>\n        );\n\n        let ariaLabel = name;\n        // The following labels are written in such a fashion to increase screen reader efficiency (speed).\n        if (this.props.tag === DefaultTagID.Invite) {\n            // append nothing\n        } else if (this.notificationState.hasMentions) {\n            ariaLabel +=\n                \" \" +\n                _t(\"a11y|n_unread_messages_mentions\", {\n                    count: this.notificationState.count,\n                });\n        } else if (this.notificationState.hasUnreadCount) {\n            ariaLabel +=\n                \" \" +\n                _t(\"a11y|n_unread_messages\", {\n                    count: this.notificationState.count,\n                });\n        } else if (this.notificationState.isUnread) {\n            ariaLabel += \" \" + _t(\"a11y|unread_messages\");\n        }\n\n        let ariaDescribedBy: string;\n        if (this.showMessagePreview) {\n            ariaDescribedBy = messagePreviewId(this.props.room.roomId);\n        }\n\n        return (\n            <React.Fragment>\n                <RovingTabIndexWrapper inputRef={this.roomTileRef}>\n                    {({ onFocus, isActive, ref }) => (\n                        <AccessibleButton\n                            onFocus={onFocus}\n                            tabIndex={isActive ? 0 : -1}\n                            ref={ref}\n                            className={classes}\n                            onClick={this.onTileClick}\n                            onContextMenu={this.onContextMenu}\n                            role=\"treeitem\"\n                            aria-label={ariaLabel}\n                            aria-selected={this.state.selected}\n                            aria-describedby={ariaDescribedBy}\n                            title={this.props.isMinimized && !this.state.generalMenuPosition ? name : undefined}\n                        >\n                            <DecoratedRoomAvatar\n                                room={this.props.room}\n                                size=\"32px\"\n                                displayBadge={this.props.isMinimized}\n                                tooltipProps={{ tabIndex: isActive ? 0 : -1 }}\n                            />\n                            {titleContainer}\n                            {badge}\n                            {this.renderGeneralMenu()}\n                            {this.renderNotificationsMenu(isActive)}\n                        </AccessibleButton>\n                    )}\n                </RovingTabIndexWrapper>\n            </React.Fragment>\n        );\n    }\n}\n\nexport default RoomTile;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ComponentProps, lazy, Suspense } from \"react\";\nimport { type ISendEventResponse } from \"matrix-js-sdk/src/matrix\";\n\n// we need to import the types for TS, but do not import the sendMessage\n// function to avoid importing from \"@vector-im/matrix-wysiwyg\"\nimport { type SendMessageParams } from \"./utils/message\";\n\nconst SendComposer = lazy(() => import(\"./SendWysiwygComposer\"));\nconst EditComposer = lazy(() => import(\"./EditWysiwygComposer\"));\n\nexport const dynamicImportSendMessage = async (\n    message: string,\n    isHTML: boolean,\n    params: SendMessageParams,\n): Promise<ISendEventResponse | undefined> => {\n    const { sendMessage } = await import(\"./utils/message\");\n\n    return sendMessage(message, isHTML, params);\n};\n\nexport const dynamicImportConversionFunctions = async (): Promise<{\n    /**\n     * Creates a rust model from rich text input (html) and uses it to generate the plain text equivalent (which may\n     * contain markdown). The return value must be used to set `.innerHTML` (rather than `.innerText`) to\n     * ensure that HTML entities are correctly interpreted, and to prevent newline characters being turned into `<br>`.\n     *\n     * @param rich - html to convert\n     * @param inMessageFormat - `true` to format the return value for use as a message `formatted_body`.\n     * `false` to format it for writing to an editor element.\n     * @returns a string of plain text that may contain markdown\n     */\n    richToPlain(rich: string, inMessageFormat: boolean): Promise<string>;\n\n    /**\n     * Creates a rust model from plain text input (interpreted as markdown) and uses it to generate the rich text\n     * equivalent. Output can be formatted for display in the composer or for sending in a Matrix message.\n     *\n     * @param plain - plain text to convert. Note: when reading the plain text from the editor element, be sure to\n     * use `.innerHTML` (rather than `.innerText`) to ensure that punctuation characters are correctly HTML-encoded.\n     * @param inMessageFormat - `true` to format the return value for use as a message `formatted_body`.\n     * `false` to format it for writing to an editor element.\n     * @returns a string of html\n     */\n    plainToRich(plain: string, inMessageFormat: boolean): Promise<string>;\n}> => {\n    const { richToPlain, plainToRich } = await import(\"@vector-im/matrix-wysiwyg\");\n\n    return { richToPlain, plainToRich };\n};\n\nexport function DynamicImportSendWysiwygComposer(props: ComponentProps<typeof SendComposer>): JSX.Element {\n    return (\n        <Suspense fallback={<div />}>\n            <SendComposer {...props} />\n        </Suspense>\n    );\n}\n\nexport function DynamicImportEditWysiwygComposer(props: ComponentProps<typeof EditComposer>): JSX.Element {\n    return (\n        <Suspense fallback={<div />}>\n            <EditComposer {...props} />\n        </Suspense>\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode, createRef, useCallback, useEffect, useState } from \"react\";\nimport EditIcon from \"@vector-im/compound-design-tokens/assets/web/icons/edit\";\nimport UploadIcon from \"@vector-im/compound-design-tokens/assets/web/icons/share\";\nimport DeleteIcon from \"@vector-im/compound-design-tokens/assets/web/icons/delete\";\nimport { Menu, MenuItem } from \"@vector-im/compound-web\";\nimport classNames from \"classnames\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { mediaFromMxc } from \"../../../customisations/Media\";\nimport { chromeFileInputFix } from \"../../../utils/BrowserWorkarounds\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport BaseAvatar from \"../avatars/BaseAvatar\";\nimport Modal from \"../../../Modal.tsx\";\nimport ErrorDialog from \"../dialogs/ErrorDialog.tsx\";\n\ninterface MenuProps {\n    trigger: ReactNode;\n    onUploadSelect: () => void;\n    onRemoveSelect?: () => void;\n    menuOpen: boolean;\n    onOpenChange: (newOpen: boolean) => void;\n}\n\nconst AvatarSettingContextMenu: React.FC<MenuProps> = ({\n    trigger,\n    onUploadSelect,\n    onRemoveSelect,\n    menuOpen,\n    onOpenChange,\n}) => {\n    return (\n        <Menu\n            trigger={trigger}\n            title={_t(\"action|set_avatar\")}\n            showTitle={false}\n            open={menuOpen}\n            onOpenChange={onOpenChange}\n        >\n            <MenuItem\n                as=\"div\"\n                Icon={<UploadIcon width=\"24px\" height=\"24px\" />}\n                label={_t(\"action|upload_file\")}\n                onSelect={onUploadSelect}\n            />\n            {onRemoveSelect && (\n                <MenuItem\n                    as=\"div\"\n                    Icon={<DeleteIcon width=\"24px\" height=\"24px\" />}\n                    className=\"mx_AvatarSetting_removeMenuItem\"\n                    label={_t(\"action|remove\")}\n                    onSelect={onRemoveSelect}\n                />\n            )}\n        </Menu>\n    );\n};\n\ninterface IProps {\n    /**\n     * The current value of the avatar URL, as an mxc URL or a File.\n     * Generally, an mxc URL would be specified until the user selects a file, then\n     * the file supplied by the onChange callback would be supplied here until it's\n     * saved.\n     */\n    avatar?: string | File;\n\n    /**\n     * If true, the user cannot change the avatar\n     */\n    disabled?: boolean;\n\n    /**\n     * Called when the user has selected a new avatar\n     * The callback is passed a File object for the new avatar data\n     */\n    onChange?: (f: File) => void;\n\n    /**\n     * Called when the user wishes to remove the avatar\n     */\n    removeAvatar?: () => void;\n\n    /**\n     * The accessible name for the avatar, eg: \"Foo's Profile Picture\"\n     */\n    avatarAccessibleName: string;\n\n    /**\n     * String to use for computing the colour of the placeholder avatar if no avatar is set\n     */\n    placeholderId: string;\n\n    /**\n     * String to use for the placeholder display if no avatar is set\n     */\n    placeholderName: string;\n}\n\nexport function getFileChanged(e: React.ChangeEvent<HTMLInputElement>): File | null {\n    if (!e.target.files?.length) return null;\n    const file = e.target.files[0];\n    if (file.type.startsWith(\"image/\")) return file;\n\n    Modal.createDialog(ErrorDialog, {\n        title: _t(\"upload_failed_title\"),\n        description: _t(\"upload_file|not_image\"),\n    });\n    return null;\n}\n\n/**\n * Component for setting or removing an avatar on something (eg. a user or a room)\n */\nconst AvatarSetting: React.FC<IProps> = ({\n    avatar,\n    avatarAccessibleName,\n    onChange,\n    removeAvatar,\n    disabled,\n    placeholderId,\n    placeholderName,\n}) => {\n    const fileInputRef = createRef<HTMLInputElement>();\n\n    // Real URL that we can supply to the img element, either a data URL or whatever mediaFromMxc gives\n    // This represents whatever avatar the user has chosen at the time\n    const [avatarURL, setAvatarURL] = useState<string | undefined>(undefined);\n    useEffect(() => {\n        if (avatar instanceof File) {\n            const reader = new FileReader();\n            reader.onload = () => {\n                setAvatarURL(reader.result as string);\n            };\n            reader.readAsDataURL(avatar);\n        } else if (avatar) {\n            setAvatarURL(mediaFromMxc(avatar).getSquareThumbnailHttp(96) ?? undefined);\n        } else {\n            setAvatarURL(undefined);\n        }\n    }, [avatar]);\n\n    const onFileChanged = useCallback(\n        (e: React.ChangeEvent<HTMLInputElement>) => {\n            const file = getFileChanged(e);\n            if (file) {\n                onChange?.(file);\n            }\n        },\n        [onChange],\n    );\n\n    const uploadAvatar = useCallback((): void => {\n        fileInputRef.current?.click();\n    }, [fileInputRef]);\n\n    const [menuOpen, setMenuOpen] = useState(false);\n\n    const onOpenChange = useCallback((newOpen: boolean) => {\n        setMenuOpen(newOpen);\n    }, []);\n\n    const avatarElement = (\n        <AccessibleButton\n            element=\"div\"\n            /**\n             * This button will open a menu. That is done by passing this element as trigger\n             * to the menu component, hence the empty onClick.\n             */\n            onClick={() => {}}\n            className=\"mx_AvatarSetting_avatarDisplay\"\n            disabled={disabled}\n        >\n            <BaseAvatar\n                idName={placeholderId}\n                name={placeholderName}\n                size=\"90px\"\n                url={avatarURL}\n                altText={avatarAccessibleName}\n            />\n        </AccessibleButton>\n    );\n\n    let uploadAvatarBtn: JSX.Element | undefined;\n    if (!disabled) {\n        const uploadButtonClasses = classNames(\"mx_AvatarSetting_uploadButton\", {\n            mx_AvatarSetting_uploadButton_active: menuOpen,\n        });\n        uploadAvatarBtn = (\n            <div\n                className={uploadButtonClasses}\n                role=\"button\"\n                aria-label={_t(\"settings|general|avatar_open_menu\")}\n                tabIndex={0}\n                aria-haspopup=\"menu\"\n            >\n                <EditIcon aria-hidden={true} width=\"20px\" height=\"20px\" />\n            </div>\n        );\n    }\n\n    const content = (\n        <div className=\"mx_AvatarSetting_avatar\" role=\"group\" aria-label={avatarAccessibleName}>\n            {avatarElement}\n            {uploadAvatarBtn}\n        </div>\n    );\n\n    if (disabled) {\n        return content;\n    }\n\n    return (\n        <>\n            <AvatarSettingContextMenu\n                trigger={content}\n                onUploadSelect={uploadAvatar}\n                onRemoveSelect={removeAvatar}\n                menuOpen={menuOpen}\n                onOpenChange={onOpenChange}\n            />\n            <input\n                type=\"file\"\n                style={{ display: \"none\" }}\n                ref={fileInputRef}\n                onClick={chromeFileInputFix}\n                onChange={onFileChanged}\n                accept=\"image/*\"\n                alt={_t(\"action|upload\")}\n            />\n        </>\n    );\n};\n\nexport default AvatarSetting;\n","/*\nCopyright 2024,2025 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useMemo, useState } from \"react\";\nimport { Room } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { InfoSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport BaseDialog from \"./BaseDialog\";\nimport SearchBox from \"../../structures/SearchBox\";\nimport SpaceStore from \"../../../stores/spaces/SpaceStore\";\nimport RoomAvatar from \"../avatars/RoomAvatar\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport AutoHideScrollbar from \"../../structures/AutoHideScrollbar\";\nimport StyledCheckbox from \"../elements/StyledCheckbox\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { filterBoolean } from \"../../../utils/arrays\";\n\ninterface IProps {\n    room: Room;\n    selected?: string[];\n    onFinished(rooms?: string[]): void;\n}\n\nconst Entry: React.FC<{\n    room: Room;\n    checked: boolean;\n    onChange(value: boolean): void;\n}> = ({ room, checked, onChange }) => {\n    const localRoom = room instanceof Room;\n\n    let description;\n    if (localRoom) {\n        description = _t(\"common|n_members\", { count: room.getJoinedMemberCount() });\n        const numChildRooms = SpaceStore.instance.getChildRooms(room.roomId).length;\n        if (numChildRooms > 0) {\n            description += \" · \" + _t(\"common|n_rooms\", { count: numChildRooms });\n        }\n    }\n\n    return (\n        <div className=\"mx_ManageRestrictedJoinRuleDialog_entry\">\n            <StyledCheckbox\n                onChange={onChange ? (e) => onChange(e.target.checked) : undefined}\n                checked={checked}\n                disabled={!onChange}\n                description={description}\n            >\n                <div>\n                    {localRoom ? (\n                        <RoomAvatar role=\"none\" room={room} size=\"20px\" />\n                    ) : (\n                        <RoomAvatar oobData={room} size=\"20px\" />\n                    )}\n                    <span className=\"mx_ManageRestrictedJoinRuleDialog_entry_name\">{room.name}</span>\n                </div>\n            </StyledCheckbox>\n        </div>\n    );\n};\n\nconst addAllParents = (set: Set<Room>, room: Room): void => {\n    const cli = room.client;\n    const parents = Array.from(SpaceStore.instance.getKnownParents(room.roomId)).map((parentId) =>\n        cli.getRoom(parentId),\n    );\n\n    parents.forEach((parent) => {\n        if (!parent || set.has(parent)) return;\n        set.add(parent);\n        addAllParents(set, parent);\n    });\n};\n\nconst ManageRestrictedJoinRuleDialog: React.FC<IProps> = ({ room, selected = [], onFinished }) => {\n    const cli = room.client;\n    const [newSelected, setNewSelected] = useState(new Set<string>(selected));\n    const [query, setQuery] = useState(\"\");\n    const lcQuery = query.toLowerCase().trim();\n\n    const [spacesContainingRoom, otherJoinedSpaces, otherEntries] = useMemo(() => {\n        const parents = new Set<Room>();\n        addAllParents(parents, room);\n\n        return [\n            Array.from(parents),\n            SpaceStore.instance.spacePanelSpaces.filter((s) => !parents.has(s)),\n            filterBoolean(\n                selected.map((roomId) => {\n                    const room = cli.getRoom(roomId);\n                    if (!room) {\n                        return { roomId, name: roomId } as Room;\n                    }\n                    if (room.getMyMembership() !== KnownMembership.Join || !room.isSpaceRoom()) {\n                        return room;\n                    }\n                }),\n            ),\n        ];\n    }, [cli, selected, room]);\n\n    const [filteredSpacesContainingRoom, filteredOtherJoinedSpaces, filteredOtherEntries] = useMemo(\n        () => [\n            spacesContainingRoom.filter((r) => r.name.toLowerCase().includes(lcQuery)),\n            otherJoinedSpaces.filter((r) => r.name.toLowerCase().includes(lcQuery)),\n            otherEntries.filter((r) => r.name.toLowerCase().includes(lcQuery)),\n        ],\n        [spacesContainingRoom, otherJoinedSpaces, otherEntries, lcQuery],\n    );\n\n    const onChange = (checked: boolean, room: Room): void => {\n        if (checked) {\n            newSelected.add(room.roomId);\n        } else {\n            newSelected.delete(room.roomId);\n        }\n        setNewSelected(new Set(newSelected));\n    };\n\n    let inviteOnlyWarning;\n    if (newSelected.size < 1) {\n        inviteOnlyWarning = (\n            <div className=\"mx_ManageRestrictedJoinRuleDialog_section_info\">\n                <InfoSolidIcon />\n                {_t(\"room_settings|security|join_rule_restricted_dialog_empty_warning\")}\n            </div>\n        );\n    }\n\n    const totalResults =\n        filteredSpacesContainingRoom.length + filteredOtherJoinedSpaces.length + filteredOtherEntries.length;\n    return (\n        <BaseDialog\n            title={_t(\"room_settings|security|join_rule_restricted_dialog_title\")}\n            className=\"mx_ManageRestrictedJoinRuleDialog\"\n            onFinished={onFinished}\n            fixedWidth={false}\n        >\n            <p>\n                {_t(\n                    \"room_settings|security|join_rule_restricted_dialog_description\",\n                    {},\n                    {\n                        RoomName: () => <strong>{room.name}</strong>,\n                    },\n                )}\n            </p>\n            <MatrixClientContext.Provider value={cli}>\n                <SearchBox\n                    className=\"mx_textinput_icon mx_textinput_search\"\n                    placeholder={_t(\"room_settings|security|join_rule_restricted_dialog_filter_placeholder\")}\n                    onSearch={setQuery}\n                    autoFocus={true}\n                />\n                <AutoHideScrollbar className=\"mx_ManageRestrictedJoinRuleDialog_content\">\n                    {filteredSpacesContainingRoom.length > 0 ? (\n                        <div className=\"mx_ManageRestrictedJoinRuleDialog_section\">\n                            <h3>\n                                {room.isSpaceRoom()\n                                    ? _t(\"room_settings|security|join_rule_restricted_dialog_heading_space\")\n                                    : _t(\"room_settings|security|join_rule_restricted_dialog_heading_room\")}\n                            </h3>\n                            {filteredSpacesContainingRoom.map((space) => {\n                                return (\n                                    <Entry\n                                        key={space.roomId}\n                                        room={space}\n                                        checked={newSelected.has(space.roomId)}\n                                        onChange={(checked: boolean) => {\n                                            onChange(checked, space);\n                                        }}\n                                    />\n                                );\n                            })}\n                        </div>\n                    ) : undefined}\n\n                    {filteredOtherEntries.length > 0 ? (\n                        <div className=\"mx_ManageRestrictedJoinRuleDialog_section\">\n                            <h3>{_t(\"room_settings|security|join_rule_restricted_dialog_heading_other\")}</h3>\n                            <div className=\"mx_ManageRestrictedJoinRuleDialog_section_info\">\n                                <InfoSolidIcon />\n                                {_t(\"room_settings|security|join_rule_restricted_dialog_heading_unknown\")}\n                            </div>\n                            {filteredOtherEntries.map((space) => {\n                                return (\n                                    <Entry\n                                        key={space.roomId}\n                                        room={space}\n                                        checked={newSelected.has(space.roomId)}\n                                        onChange={(checked: boolean) => {\n                                            onChange(checked, space);\n                                        }}\n                                    />\n                                );\n                            })}\n                        </div>\n                    ) : null}\n\n                    {filteredOtherJoinedSpaces.length > 0 ? (\n                        <div className=\"mx_ManageRestrictedJoinRuleDialog_section\">\n                            <h3>{_t(\"room_settings|security|join_rule_restricted_dialog_heading_known\")}</h3>\n                            {filteredOtherJoinedSpaces.map((space) => {\n                                return (\n                                    <Entry\n                                        key={space.roomId}\n                                        room={space}\n                                        checked={newSelected.has(space.roomId)}\n                                        onChange={(checked: boolean) => {\n                                            onChange(checked, space);\n                                        }}\n                                    />\n                                );\n                            })}\n                        </div>\n                    ) : null}\n\n                    {totalResults < 1 ? (\n                        <span className=\"mx_ManageRestrictedJoinRuleDialog_noResults\">{_t(\"common|no_results\")}</span>\n                    ) : undefined}\n                </AutoHideScrollbar>\n\n                <div className=\"mx_ManageRestrictedJoinRuleDialog_footer\">\n                    {inviteOnlyWarning}\n                    <div className=\"mx_ManageRestrictedJoinRuleDialog_footer_buttons\">\n                        <AccessibleButton kind=\"primary_outline\" onClick={() => onFinished()}>\n                            {_t(\"action|cancel\")}\n                        </AccessibleButton>\n                        <AccessibleButton kind=\"primary\" onClick={() => onFinished(Array.from(newSelected))}>\n                            {_t(\"action|confirm\")}\n                        </AccessibleButton>\n                    </div>\n                </div>\n            </MatrixClientContext.Provider>\n        </BaseDialog>\n    );\n};\n\nexport default ManageRestrictedJoinRuleDialog;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode, useEffect, useState } from \"react\";\nimport { JoinRule, RestrictedAllowType, type Room, EventType, Visibility } from \"matrix-js-sdk/src/matrix\";\nimport { type RoomJoinRulesEventContent } from \"matrix-js-sdk/src/types\";\n\nimport StyledRadioGroup, { type IDefinition } from \"../elements/StyledRadioGroup\";\nimport { _t } from \"../../../languageHandler\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport RoomAvatar from \"../avatars/RoomAvatar\";\nimport SpaceStore from \"../../../stores/spaces/SpaceStore\";\nimport Modal from \"../../../Modal\";\nimport ManageRestrictedJoinRuleDialog from \"../dialogs/ManageRestrictedJoinRuleDialog\";\nimport RoomUpgradeWarningDialog, { type IFinishedOpts } from \"../dialogs/RoomUpgradeWarningDialog\";\nimport { type RoomUpgradeProgress, upgradeRoom } from \"../../../utils/RoomUpgrade\";\nimport { arrayHasDiff } from \"../../../utils/arrays\";\nimport { useLocalEcho } from \"../../../hooks/useLocalEcho\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { RoomSettingsTab } from \"../dialogs/RoomSettingsDialog\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { type ViewRoomPayload } from \"../../../dispatcher/payloads/ViewRoomPayload\";\nimport { doesRoomVersionSupport, PreferredRoomVersions } from \"../../../utils/PreferredRoomVersions\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport LabelledCheckbox from \"../elements/LabelledCheckbox\";\n\nexport interface JoinRuleSettingsProps {\n    room: Room;\n    promptUpgrade?: boolean;\n    closeSettingsFn(): void;\n    onError(error: unknown): void;\n    beforeChange?(joinRule: JoinRule): Promise<boolean>; // if returns false then aborts the change\n    disabledOptions?: Set<JoinRule>;\n    hiddenOptions?: Set<JoinRule>;\n    recommendedOption?: JoinRule;\n}\n\nconst JoinRuleSettings: React.FC<JoinRuleSettingsProps> = ({\n    room,\n    promptUpgrade,\n    onError,\n    beforeChange,\n    closeSettingsFn,\n    disabledOptions,\n    hiddenOptions,\n    recommendedOption,\n}) => {\n    const cli = room.client;\n\n    const askToJoinEnabled = SettingsStore.getValue(\"feature_ask_to_join\");\n    const roomSupportsKnock = doesRoomVersionSupport(room.getVersion(), PreferredRoomVersions.KnockRooms);\n    const preferredKnockVersion = !roomSupportsKnock && promptUpgrade ? PreferredRoomVersions.KnockRooms : undefined;\n\n    const roomSupportsRestricted = doesRoomVersionSupport(room.getVersion(), PreferredRoomVersions.RestrictedRooms);\n    const preferredRestrictionVersion =\n        !roomSupportsRestricted && promptUpgrade ? PreferredRoomVersions.RestrictedRooms : undefined;\n\n    const disabled = !room.currentState.mayClientSendStateEvent(EventType.RoomJoinRules, cli);\n\n    const [content, setContent] = useLocalEcho<RoomJoinRulesEventContent | undefined, RoomJoinRulesEventContent>(\n        () => room.currentState.getStateEvents(EventType.RoomJoinRules, \"\")?.getContent(),\n        (content) => cli.sendStateEvent(room.roomId, EventType.RoomJoinRules, content, \"\"),\n        onError,\n    );\n\n    const { join_rule: joinRule = JoinRule.Invite } = content || {};\n    const restrictedAllowRoomIds =\n        joinRule === JoinRule.Restricted\n            ? content?.allow?.filter((o) => o.type === RestrictedAllowType.RoomMembership).map((o) => o.room_id)\n            : undefined;\n\n    const [isPublicKnockRoom, setIsPublicKnockRoom] = useState(false);\n\n    useEffect(() => {\n        if (joinRule === JoinRule.Knock) {\n            cli.getRoomDirectoryVisibility(room.roomId)\n                .then(({ visibility }) => setIsPublicKnockRoom(visibility === Visibility.Public))\n                .catch(onError);\n        }\n    }, [cli, joinRule, onError, room.roomId]);\n\n    const onIsPublicKnockRoomChange = (checked: boolean): void => {\n        cli.setRoomDirectoryVisibility(room.roomId, checked ? Visibility.Public : Visibility.Private)\n            .then(() => setIsPublicKnockRoom(checked))\n            .catch(onError);\n    };\n\n    const editRestrictedRoomIds = async (): Promise<string[] | undefined> => {\n        let selected = restrictedAllowRoomIds;\n        if (!selected?.length && SpaceStore.instance.activeSpaceRoom) {\n            selected = [SpaceStore.instance.activeSpaceRoom.roomId];\n        }\n\n        const { finished } = Modal.createDialog(\n            ManageRestrictedJoinRuleDialog,\n            {\n                room,\n                selected,\n            },\n            \"mx_ManageRestrictedJoinRuleDialog_wrapper\",\n        );\n\n        const [roomIds] = await finished;\n        return roomIds;\n    };\n\n    const upgradeRequiredDialog = (targetVersion: string, description?: ReactNode): void => {\n        Modal.createDialog(RoomUpgradeWarningDialog, {\n            roomId: room.roomId,\n            targetVersion,\n            description,\n            doUpgrade: async (\n                opts: IFinishedOpts,\n                fn: (progressText: string, progress: number, total: number) => void,\n            ): Promise<void> => {\n                const progressCallback = (progress: RoomUpgradeProgress): void => {\n                    const total = 2 + progress.updateSpacesTotal + progress.inviteUsersTotal;\n                    if (!progress.roomUpgraded) {\n                        fn(_t(\"room_settings|security|join_rule_upgrade_upgrading_room\"), 0, total);\n                    } else if (!progress.roomSynced) {\n                        fn(_t(\"room_settings|security|join_rule_upgrade_awaiting_room\"), 1, total);\n                    } else if (\n                        progress.inviteUsersProgress !== undefined &&\n                        progress.inviteUsersProgress < progress.inviteUsersTotal\n                    ) {\n                        fn(\n                            _t(\"room_settings|security|join_rule_upgrade_sending_invites\", {\n                                progress: progress.inviteUsersProgress,\n                                count: progress.inviteUsersTotal,\n                            }),\n                            2 + progress.inviteUsersProgress,\n                            total,\n                        );\n                    } else if (\n                        progress.updateSpacesProgress !== undefined &&\n                        progress.updateSpacesProgress < progress.updateSpacesTotal\n                    ) {\n                        fn(\n                            _t(\"room_settings|security|join_rule_upgrade_updating_spaces\", {\n                                progress: progress.updateSpacesProgress,\n                                count: progress.updateSpacesTotal,\n                            }),\n                            2 + (progress.inviteUsersProgress ?? 0) + progress.updateSpacesProgress,\n                            total,\n                        );\n                    }\n                };\n                const roomId = await upgradeRoom(\n                    room,\n                    targetVersion,\n                    opts.invite,\n                    true,\n                    true,\n                    true,\n                    progressCallback,\n\n                    // We want to keep the RoomUpgradeDialog open during the upgrade, so don't replace it with the\n                    // invite progress dialog.\n                    /* inhibitInviteProgressDialog: */ true,\n                );\n\n                closeSettingsFn?.();\n\n                // switch to the new room in the background\n                dis.dispatch<ViewRoomPayload>({\n                    action: Action.ViewRoom,\n                    room_id: roomId,\n                    metricsTrigger: undefined, // other\n                });\n\n                // open new settings on this tab\n                dis.dispatch({\n                    action: \"open_room_settings\",\n                    initial_tab_id: RoomSettingsTab.Security,\n                });\n            },\n        });\n    };\n\n    const upgradeRequiredPill = (\n        <span className=\"mx_JoinRuleSettings_upgradeRequired\">\n            {_t(\"room_settings|security|join_rule_upgrade_required\")}\n        </span>\n    );\n    const withRecommendLabel = (label: string, rule: JoinRule): React.ReactNode =>\n        rule === recommendedOption ? (\n            <>\n                {label} (<span className=\"mx_JoinRuleSettings_recommended\">{_t(\"common|recommended\")}</span>)\n            </>\n        ) : (\n            label\n        );\n\n    const definitions: IDefinition<JoinRule>[] = [\n        {\n            value: JoinRule.Invite,\n            label: withRecommendLabel(_t(\"room_settings|security|join_rule_invite\"), JoinRule.Invite),\n            description: _t(\"room_settings|security|join_rule_invite_description\"),\n            checked:\n                joinRule === JoinRule.Invite || (joinRule === JoinRule.Restricted && !restrictedAllowRoomIds?.length),\n        },\n        {\n            value: JoinRule.Public,\n            label: withRecommendLabel(_t(\"common|public\"), JoinRule.Public),\n            description: <>{_t(\"room_settings|security|join_rule_public_description\")}</>,\n        },\n    ];\n\n    if (roomSupportsRestricted || preferredRestrictionVersion || joinRule === JoinRule.Restricted) {\n        let description;\n        if (joinRule === JoinRule.Restricted && restrictedAllowRoomIds?.length) {\n            // only show the first 4 spaces we know about, so that the UI doesn't grow out of proportion there are lots.\n            const shownSpaces = restrictedAllowRoomIds\n                .map((roomId) => cli.getRoom(roomId))\n                .filter((room) => room?.isSpaceRoom())\n                .slice(0, 4) as Room[];\n\n            let moreText;\n            if (shownSpaces.length < restrictedAllowRoomIds.length) {\n                if (shownSpaces.length > 0) {\n                    moreText = _t(\"room_settings|security|join_rule_restricted_n_more\", {\n                        count: restrictedAllowRoomIds.length - shownSpaces.length,\n                    });\n                } else {\n                    moreText = _t(\"room_settings|security|join_rule_restricted_summary\", {\n                        count: restrictedAllowRoomIds.length,\n                    });\n                }\n            }\n\n            const onRestrictedRoomIdsChange = (newAllowRoomIds: string[]): void => {\n                if (!arrayHasDiff(restrictedAllowRoomIds || [], newAllowRoomIds)) return;\n\n                if (!newAllowRoomIds.length) {\n                    setContent({\n                        join_rule: JoinRule.Invite,\n                    });\n                    return;\n                }\n\n                setContent({\n                    join_rule: JoinRule.Restricted,\n                    allow: newAllowRoomIds.map((roomId) => ({\n                        type: RestrictedAllowType.RoomMembership,\n                        room_id: roomId,\n                    })),\n                });\n            };\n\n            const onEditRestrictedClick = async (): Promise<void> => {\n                const restrictedAllowRoomIds = await editRestrictedRoomIds();\n                if (!Array.isArray(restrictedAllowRoomIds)) return;\n                if (restrictedAllowRoomIds.length > 0) {\n                    onRestrictedRoomIdsChange(restrictedAllowRoomIds);\n                } else {\n                    onChange(JoinRule.Invite);\n                }\n            };\n\n            description = (\n                <div>\n                    <span>\n                        {_t(\n                            \"room_settings|security|join_rule_restricted_description\",\n                            {},\n                            {\n                                a: (sub) => (\n                                    <AccessibleButton\n                                        disabled={disabled}\n                                        onClick={onEditRestrictedClick}\n                                        kind=\"link_inline\"\n                                    >\n                                        {sub}\n                                    </AccessibleButton>\n                                ),\n                            },\n                        )}\n                    </span>\n\n                    <div className=\"mx_JoinRuleSettings_spacesWithAccess\">\n                        <h4>{_t(\"room_settings|security|join_rule_restricted_description_spaces\")}</h4>\n                        {shownSpaces.map((room) => {\n                            return (\n                                <span key={room.roomId}>\n                                    <RoomAvatar room={room} size=\"32px\" />\n                                    {room.name}\n                                </span>\n                            );\n                        })}\n                        {moreText && <span>{moreText}</span>}\n                    </div>\n                </div>\n            );\n        } else if (SpaceStore.instance.activeSpaceRoom) {\n            description = _t(\n                \"room_settings|security|join_rule_restricted_description_active_space\",\n                {},\n                {\n                    spaceName: () => <strong>{SpaceStore.instance.activeSpaceRoom!.name}</strong>,\n                },\n            );\n        } else {\n            description = _t(\"room_settings|security|join_rule_restricted_description_prompt\");\n        }\n\n        definitions.splice(1, 0, {\n            value: JoinRule.Restricted,\n            label: (\n                <>\n                    {withRecommendLabel(_t(\"room_settings|security|join_rule_restricted\"), JoinRule.Restricted)}\n                    {preferredRestrictionVersion && upgradeRequiredPill}\n                </>\n            ),\n            description,\n            // if there are 0 allowed spaces then render it as invite only instead\n            checked: joinRule === JoinRule.Restricted && !!restrictedAllowRoomIds?.length,\n        });\n    }\n\n    if (askToJoinEnabled && (roomSupportsKnock || preferredKnockVersion)) {\n        definitions.splice(Math.max(0, definitions.length - 1), 0, {\n            value: JoinRule.Knock,\n            label: (\n                <>\n                    {withRecommendLabel(_t(\"room_settings|security|join_rule_knock\"), JoinRule.Knock)}\n                    {preferredKnockVersion && upgradeRequiredPill}\n                </>\n            ),\n            description: (\n                <>\n                    {_t(\"room_settings|security|join_rule_knock_description\")}\n                    <LabelledCheckbox\n                        className=\"mx_JoinRuleSettings_labelledCheckbox\"\n                        disabled={joinRule !== JoinRule.Knock}\n                        label={\n                            room.isSpaceRoom()\n                                ? _t(\"room_settings|security|publish_space\")\n                                : _t(\"room_settings|security|publish_room\")\n                        }\n                        onChange={onIsPublicKnockRoomChange}\n                        value={isPublicKnockRoom}\n                    />\n                </>\n            ),\n        });\n    }\n\n    const onChange = async (joinRule: JoinRule): Promise<void> => {\n        const beforeJoinRule = content?.join_rule;\n\n        let restrictedAllowRoomIds: string[] | undefined;\n        if (joinRule === JoinRule.Restricted) {\n            if (beforeJoinRule === JoinRule.Restricted || roomSupportsRestricted) {\n                // Have the user pick which spaces to allow joins from\n                restrictedAllowRoomIds = await editRestrictedRoomIds();\n                if (!Array.isArray(restrictedAllowRoomIds)) return;\n            } else if (preferredRestrictionVersion) {\n                // Block this action on a room upgrade otherwise it'd make their room unjoinable\n                const targetVersion = preferredRestrictionVersion;\n\n                let warning: JSX.Element | undefined;\n                const userId = cli.getUserId()!;\n                const unableToUpdateSomeParents = Array.from(SpaceStore.instance.getKnownParents(room.roomId)).some(\n                    (roomId) => !cli.getRoom(roomId)?.currentState.maySendStateEvent(EventType.SpaceChild, userId),\n                );\n                if (unableToUpdateSomeParents) {\n                    warning = <strong>{_t(\"room_settings|security|join_rule_restricted_upgrade_warning\")}</strong>;\n                }\n\n                upgradeRequiredDialog(\n                    targetVersion,\n                    <>\n                        {_t(\"room_settings|security|join_rule_restricted_upgrade_description\")}\n                        {warning}\n                    </>,\n                );\n\n                return;\n            }\n\n            // when setting to 0 allowed rooms/spaces set to invite only instead as per the note\n            if (!restrictedAllowRoomIds?.length) {\n                joinRule = JoinRule.Invite;\n            }\n        } else if (joinRule === JoinRule.Knock) {\n            if (preferredKnockVersion) {\n                upgradeRequiredDialog(preferredKnockVersion);\n                return;\n            }\n        }\n\n        if (beforeJoinRule === joinRule && !restrictedAllowRoomIds) return;\n        if (beforeChange && !(await beforeChange(joinRule))) return;\n\n        const newContent: RoomJoinRulesEventContent = {\n            join_rule: joinRule,\n        };\n\n        // pre-set the accepted spaces with the currently viewed one as per the microcopy\n        if (joinRule === JoinRule.Restricted) {\n            newContent.allow = restrictedAllowRoomIds?.map((roomId) => ({\n                type: RestrictedAllowType.RoomMembership,\n                room_id: roomId,\n            }));\n        }\n\n        setContent(newContent);\n    };\n\n    return (\n        <StyledRadioGroup\n            name=\"joinRule\"\n            value={joinRule}\n            onChange={onChange}\n            definitions={definitions\n                .map((d) => (disabledOptions?.has(d.value) ? { ...d, disabled: true } : d))\n                .filter((d) => !hiddenOptions?.has(d.value))}\n            disabled={disabled}\n            className=\"mx_JoinRuleSettings_radioButton\"\n        />\n    );\n};\n\nexport default JoinRuleSettings;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode, type HTMLAttributes } from \"react\";\nimport classNames from \"classnames\";\n\nimport { SettingsSubsectionText } from \"./shared/SettingsSubsection\";\n\ninterface Props extends HTMLAttributes<HTMLFieldSetElement> {\n    // section title\n    legend: string | ReactNode;\n    description?: string | ReactNode;\n}\n\nconst SettingsFieldset: React.FC<Props> = ({ legend, className, children, description, ...rest }) => (\n    <fieldset {...rest} className={classNames(\"mx_SettingsFieldset\", className)}>\n        <legend className=\"mx_SettingsFieldset_legend\">{legend}</legend>\n        {description && (\n            <div className=\"mx_SettingsFieldset_description\">\n                <SettingsSubsectionText>{description}</SettingsSubsectionText>\n            </div>\n        )}\n        <div className=\"mx_SettingsFieldset_content\">{children}</div>\n    </fieldset>\n);\n\nexport default SettingsFieldset;\n","/*\n * Copyright 2024 New Vector Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport React, { type JSX } from \"react\";\nimport classNames from \"classnames\";\nimport { Heading } from \"@vector-im/compound-web\";\n\n/**\n * The heading for a settings section.\n */\ninterface SettingsHeaderProps {\n    /**\n     * Whether the user has a recommended tag.\n     */\n    hasRecommendedTag?: boolean;\n    /**\n     * The label for the header.\n     */\n    label: string;\n}\n\nexport function SettingsHeader({ hasRecommendedTag = false, label }: SettingsHeaderProps): JSX.Element {\n    const classes = classNames(\"mx_SettingsHeader\", {\n        mx_SettingsHeader_recommended: hasRecommendedTag,\n    });\n    return (\n        <Heading className={classes} as=\"h2\" size=\"sm\" weight=\"semibold\">\n            {label}\n        </Heading>\n    );\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport React, { type JSX, type PropsWithChildren, type ComponentType, type SVGAttributes } from \"react\";\nimport { BigIcon, Heading } from \"@vector-im/compound-web\";\nimport classNames from \"classnames\";\n\ninterface EncryptionCardProps {\n    /**\n     * CSS class name to apply to the card.\n     */\n    className?: string;\n    /**\n     * The title of the card.\n     */\n    title: string;\n    /**\n     * The description of the card.\n     */\n    description?: string;\n    /**\n     * Whether this icon shows a destructive action.\n     */\n    destructive?: boolean;\n    /**\n     * The icon to display.\n     */\n    Icon: ComponentType<SVGAttributes<SVGElement>>;\n}\n\n/**\n * A styled card for encryption settings.\n */\nexport function EncryptionCard({\n    title,\n    description,\n    className,\n    destructive = false,\n    Icon,\n    children,\n}: PropsWithChildren<EncryptionCardProps>): JSX.Element {\n    return (\n        <div className={classNames(\"mx_EncryptionCard\", className)}>\n            <div className=\"mx_EncryptionCard_header\">\n                <BigIcon destructive={destructive}>\n                    <Icon />\n                </BigIcon>\n                <Heading as=\"h2\" size=\"sm\" weight=\"semibold\">\n                    {title}\n                </Heading>\n                {description && <span>{description}</span>}\n            </div>\n            {children}\n        </div>\n    );\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport React, { type JSX, type PropsWithChildren } from \"react\";\n\n/**\n * A component to present action buttons at the bottom of an {@link EncryptionCard}\n * (mostly as somewhere for the common CSS to live).\n */\nexport function EncryptionCardButtons({ children }: PropsWithChildren): JSX.Element {\n    return <div className=\"mx_EncryptionCard_buttons\">{children}</div>;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022, 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport classnames from \"classnames\";\nimport React, { type HTMLAttributes } from \"react\";\n\nimport Heading from \"../../typography/Heading\";\nimport { SettingsHeader } from \"../SettingsHeader\";\n\nexport interface SettingsSectionProps extends HTMLAttributes<HTMLDivElement> {\n    heading?: string | React.ReactNode;\n    subHeading?: string | React.ReactNode;\n    children?: React.ReactNode;\n    legacy?: boolean;\n}\n\nfunction renderHeading(heading: string | React.ReactNode | undefined, legacy: boolean): React.ReactNode | undefined {\n    switch (typeof heading) {\n        case \"string\":\n            return legacy ? (\n                <Heading as=\"h2\" size=\"3\">\n                    {heading}\n                </Heading>\n            ) : (\n                <SettingsHeader label={heading} />\n            );\n        case \"undefined\":\n            return undefined;\n        default:\n            return heading;\n    }\n}\n\n/**\n * A section of settings content\n * A SettingsTab may contain one or more SettingsSections\n * Eg:\n * ```\n * <SettingsTab>\n *      <SettingsSection heading=\"General\">\n *           <SettingsSubsection heading=\"Profile\">\n *              // profile settings form\n *          <SettingsSubsection>\n *          <SettingsSubsection heading=\"Account\">\n *              // account settings\n *          <SettingsSubsection>\n *      </SettingsSection>\n * </SettingsTab>\n * ```\n */\nexport const SettingsSection: React.FC<SettingsSectionProps> = ({\n    className,\n    heading,\n    subHeading,\n    legacy = true,\n    children,\n    ...rest\n}) => (\n    <div\n        {...rest}\n        className={classnames(\"mx_SettingsSection\", className, {\n            mx_SettingsSection_newUi: !legacy,\n        })}\n    >\n        {heading &&\n            (subHeading ? (\n                <div className=\"mx_SettingsSection_header\">\n                    {renderHeading(heading, legacy)}\n                    {subHeading}\n                </div>\n            ) : (\n                renderHeading(heading, legacy)\n            ))}\n        {legacy ? <div className=\"mx_SettingsSection_subSections\">{children}</div> : children}\n    </div>\n);\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport classNames from \"classnames\";\nimport React, { type HTMLAttributes } from \"react\";\nimport { Form, Separator } from \"@vector-im/compound-web\";\n\nimport { SettingsSubsectionHeading } from \"./SettingsSubsectionHeading\";\n\nexport interface SettingsSubsectionProps extends HTMLAttributes<HTMLDivElement> {\n    heading?: string | React.ReactNode;\n    description?: string | React.ReactNode;\n    children?: React.ReactNode;\n    // when true content will be justify-items: stretch, which will make items within the section stretch to full width.\n    stretchContent?: boolean;\n    /*\n     * When true, the legacy UI style will be applied to the subsection.\n     * @default true\n     */\n    legacy?: boolean;\n\n    /**\n     * Wrap in a Form Root component, for compatibility with compound components.\n     */\n    formWrap?: boolean;\n}\n\nexport const SettingsSubsectionText: React.FC<HTMLAttributes<HTMLDivElement>> = ({ children, ...rest }) => (\n    <div {...rest} className=\"mx_SettingsSubsection_text\">\n        {children}\n    </div>\n);\n\nexport const SettingsSubsection: React.FC<SettingsSubsectionProps> = ({\n    heading,\n    description,\n    children,\n    stretchContent,\n    legacy = true,\n    formWrap,\n    ...rest\n}) => {\n    const content = (\n        <div\n            {...rest}\n            className={classNames(\"mx_SettingsSubsection\", {\n                mx_SettingsSubsection_newUi: !legacy,\n            })}\n        >\n            {typeof heading === \"string\" ? <SettingsSubsectionHeading heading={heading} /> : <>{heading}</>}\n            {!!description && (\n                <div className=\"mx_SettingsSubsection_description\">\n                    <SettingsSubsectionText>{description}</SettingsSubsectionText>\n                </div>\n            )}\n            {!!children && (\n                <div\n                    className={classNames(\"mx_SettingsSubsection_content\", {\n                        mx_SettingsSubsection_contentStretch: !!stretchContent,\n                        mx_SettingsSubsection_noHeading: !heading && !description,\n                        mx_SettingsSubsection_content_newUi: !legacy,\n                    })}\n                >\n                    {children}\n                </div>\n            )}\n            {!legacy && <Separator />}\n        </div>\n    );\n\n    if (formWrap) {\n        return (\n            <Form.Root\n                onSubmit={(evt) => {\n                    evt.preventDefault();\n                    evt.stopPropagation();\n                }}\n            >\n                {content}\n            </Form.Root>\n        );\n    }\n    return content;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type HTMLAttributes } from \"react\";\n\nimport Heading from \"../../typography/Heading\";\n\nexport interface SettingsSubsectionHeadingProps extends HTMLAttributes<HTMLDivElement> {\n    heading: string;\n    as?: React.ComponentProps<typeof Heading>[\"as\"];\n    children?: React.ReactNode;\n}\n\nexport const SettingsSubsectionHeading: React.FC<SettingsSubsectionHeadingProps> = ({\n    heading,\n    as = \"h3\",\n    children,\n    ...rest\n}) => {\n    return (\n        <div {...rest} className=\"mx_SettingsSubsectionHeading\">\n            <Heading className=\"mx_SettingsSubsectionHeading_heading\" size=\"4\" as={as}>\n                {heading}\n            </Heading>\n            {children}\n        </div>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\nimport React, { type HTMLAttributes } from \"react\";\nimport classNames from \"classnames\";\n\nexport interface SettingsTabProps extends HTMLAttributes<HTMLDivElement> {\n    children?: React.ReactNode;\n    /**\n     * Added to the classList of the root element\n     */\n    className?: string;\n}\n\n/**\n * Container for a tab of settings panel content\n * Should contain one or more SettingsSection\n * Settings width, padding and spacing between sections\n * Eg:\n * ```\n * <SettingsTab>\n *      <SettingsSection heading=\"General\">\n *           <SettingsSubsection heading=\"Profile\">\n *              // profile settings form\n *          <SettingsSubsection>\n *          <SettingsSubsection heading=\"Account\">\n *              // account settings\n *          <SettingsSubsection>\n *      </SettingsSection>\n * </SettingsTab>\n * ```\n */\nconst SettingsTab: React.FC<SettingsTabProps> = ({ children, className, ...rest }) => (\n    <div {...rest} className={classNames(\"mx_SettingsTab\", className)}>\n        <div className=\"mx_SettingsTab_sections\">{children}</div>\n    </div>\n);\n\nexport default SettingsTab;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { EventType, type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../../../languageHandler\";\nimport AccessibleButton, { type ButtonEvent } from \"../../../elements/AccessibleButton\";\nimport RoomUpgradeDialog from \"../../../dialogs/RoomUpgradeDialog\";\nimport Modal from \"../../../../../Modal\";\nimport dis from \"../../../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../../../dispatcher/actions\";\nimport CopyableText from \"../../../elements/CopyableText\";\nimport { type ViewRoomPayload } from \"../../../../../dispatcher/payloads/ViewRoomPayload\";\nimport SettingsStore from \"../../../../../settings/SettingsStore\";\nimport SettingsTab from \"../SettingsTab\";\nimport { SettingsSection } from \"../../shared/SettingsSection\";\nimport { SettingsSubsection } from \"../../shared/SettingsSubsection\";\n\ninterface IProps {\n    room: Room;\n    closeSettingsFn(): void;\n}\n\ninterface IRecommendedVersion {\n    version: string;\n    needsUpgrade: boolean;\n    urgent: boolean;\n}\n\ninterface IState {\n    // This is eventually set to the value of room.getRecommendedVersion()\n    upgradeRecommendation?: IRecommendedVersion;\n\n    /** The room ID of this room's predecessor, if it exists. */\n    oldRoomId?: string;\n\n    /** The ID of tombstone event in this room's predecessor, if it exists. */\n    oldEventId?: string;\n\n    /** The via servers to use to find this room's predecessor, if it exists. */\n    oldViaServers?: string[];\n\n    upgraded?: boolean;\n}\n\nexport default class AdvancedRoomSettingsTab extends React.Component<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {};\n    }\n\n    public componentDidMount(): void {\n        const msc3946ProcessDynamicPredecessor = SettingsStore.getValue(\"feature_dynamic_room_predecessors\");\n\n        // we handle lack of this object gracefully later, so don't worry about it failing here.\n        const room = this.props.room;\n        room.getRecommendedVersion().then((v) => {\n            const tombstone = room.currentState.getStateEvents(EventType.RoomTombstone, \"\");\n\n            const additionalStateChanges: Partial<IState> = {};\n            const predecessor = room.findPredecessor(msc3946ProcessDynamicPredecessor);\n            if (predecessor) {\n                additionalStateChanges.oldRoomId = predecessor.roomId;\n                additionalStateChanges.oldEventId = predecessor.eventId;\n                additionalStateChanges.oldViaServers = predecessor.viaServers;\n            }\n\n            this.setState({\n                upgraded: !!tombstone?.getContent().replacement_room,\n                upgradeRecommendation: v,\n                ...additionalStateChanges,\n            });\n        });\n    }\n\n    private upgradeRoom = (): void => {\n        Modal.createDialog(RoomUpgradeDialog, { room: this.props.room });\n    };\n\n    private onOldRoomClicked = (e: ButtonEvent): void => {\n        e.preventDefault();\n        e.stopPropagation();\n\n        dis.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            room_id: this.state.oldRoomId,\n            event_id: this.state.oldEventId,\n            via_servers: this.state.oldViaServers,\n            metricsTrigger: \"WebPredecessorSettings\",\n            metricsViaKeyboard: e.type !== \"click\",\n        });\n        this.props.closeSettingsFn();\n    };\n\n    public render(): React.ReactNode {\n        const room = this.props.room;\n        const isSpace = room.isSpaceRoom();\n\n        let unfederatableSection: JSX.Element | undefined;\n        if (room.currentState.getStateEvents(EventType.RoomCreate, \"\")?.getContent()[\"m.federate\"] === false) {\n            unfederatableSection = <div>{_t(\"room_settings|advanced|unfederated\")}</div>;\n        }\n\n        let roomUpgradeButton;\n        if (this.state.upgradeRecommendation && this.state.upgradeRecommendation.needsUpgrade && !this.state.upgraded) {\n            roomUpgradeButton = (\n                <div>\n                    <p className=\"mx_SettingsTab_warningText\">\n                        {_t(\n                            \"room_settings|advanced|room_upgrade_warning\",\n                            {},\n                            {\n                                b: (sub) => <strong>{sub}</strong>,\n                                i: (sub) => <i>{sub}</i>,\n                            },\n                        )}\n                    </p>\n                    <AccessibleButton onClick={this.upgradeRoom} kind=\"primary\">\n                        {isSpace\n                            ? _t(\"room_settings|advanced|space_upgrade_button\")\n                            : _t(\"room_settings|advanced|room_upgrade_button\")}\n                    </AccessibleButton>\n                </div>\n            );\n        }\n\n        let oldRoomLink: JSX.Element | undefined;\n        if (this.state.oldRoomId) {\n            let copy: string;\n            if (isSpace) {\n                copy = _t(\"room_settings|advanced|space_predecessor\", { spaceName: room.name ?? this.state.oldRoomId });\n            } else {\n                copy = _t(\"room_settings|advanced|room_predecessor\", { roomName: room.name ?? this.state.oldRoomId });\n            }\n\n            oldRoomLink = (\n                <AccessibleButton element=\"a\" onClick={this.onOldRoomClicked}>\n                    {copy}\n                </AccessibleButton>\n            );\n        }\n\n        return (\n            <SettingsTab>\n                <SettingsSection heading={_t(\"common|advanced\")}>\n                    <SettingsSubsection\n                        heading={\n                            room.isSpaceRoom()\n                                ? _t(\"room_settings|advanced|information_section_space\")\n                                : _t(\"room_settings|advanced|information_section_room\")\n                        }\n                    >\n                        <div>\n                            <span>{_t(\"room_settings|advanced|room_id\")}</span>\n                            <CopyableText getTextToCopy={() => this.props.room.roomId}>\n                                {this.props.room.roomId}\n                            </CopyableText>\n                        </div>\n                        {unfederatableSection}\n                    </SettingsSubsection>\n                    <SettingsSubsection heading={_t(\"room_settings|advanced|room_version_section\")}>\n                        <div>\n                            <span>{_t(\"room_settings|advanced|room_version\")}</span>&nbsp;\n                            {room.getVersion()}\n                        </div>\n                        {oldRoomLink}\n                        {roomUpgradeButton}\n                    </SettingsSubsection>\n                </SettingsSection>\n            </SettingsTab>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, {\n    useState,\n    type ReactNode,\n    type ChangeEvent,\n    type KeyboardEvent,\n    useRef,\n    type ReactElement,\n} from \"react\";\nimport classNames from \"classnames\";\nimport { SearchIcon, CloseIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport type Autocompleter from \"../../autocomplete/AutocompleteProvider\";\nimport { Key } from \"../../Keyboard\";\nimport { type ICompletion } from \"../../autocomplete/Autocompleter\";\nimport AccessibleButton from \"../../components/views/elements/AccessibleButton\";\nimport useFocus from \"../../hooks/useFocus\";\n\ninterface AutocompleteInputProps {\n    provider: Autocompleter;\n    placeholder: string;\n    selection: ICompletion[];\n    onSelectionChange: (selection: ICompletion[]) => void;\n    maxSuggestions?: number;\n    renderSuggestion?: (s: ICompletion) => ReactElement;\n    renderSelection?: (m: ICompletion) => ReactElement;\n    additionalFilter?: (suggestion: ICompletion) => boolean;\n}\n\nexport const AutocompleteInput: React.FC<AutocompleteInputProps> = ({\n    provider,\n    renderSuggestion,\n    renderSelection,\n    maxSuggestions = 5,\n    placeholder,\n    onSelectionChange,\n    selection,\n    additionalFilter,\n}) => {\n    const [query, setQuery] = useState<string>(\"\");\n    const [suggestions, setSuggestions] = useState<ICompletion[]>([]);\n    const [isFocused, onFocusChangeHandlerFunctions] = useFocus();\n    const editorContainerRef = useRef<HTMLDivElement>(null);\n    const editorRef = useRef<HTMLInputElement>(null);\n\n    const focusEditor = (): void => {\n        editorRef?.current?.focus();\n    };\n\n    const onQueryChange = async (e: ChangeEvent<HTMLInputElement>): Promise<void> => {\n        const value = e.target.value.trim();\n        setQuery(value);\n\n        let matches = await provider.getCompletions(\n            query,\n            { start: query.length, end: query.length },\n            true,\n            maxSuggestions,\n        );\n\n        if (additionalFilter) {\n            matches = matches.filter(additionalFilter);\n        }\n\n        setSuggestions(matches);\n    };\n\n    const onClickInputArea = (): void => {\n        focusEditor();\n    };\n\n    const onKeyDown = (e: KeyboardEvent): void => {\n        const hasModifiers = e.ctrlKey || e.shiftKey || e.metaKey;\n\n        // when the field is empty and the user hits backspace remove the right-most target\n        if (!query && selection.length > 0 && e.key === Key.BACKSPACE && !hasModifiers) {\n            removeSelection(selection[selection.length - 1]);\n        }\n    };\n\n    const toggleSelection = (completion: ICompletion): void => {\n        const newSelection = [...selection];\n        const index = selection.findIndex((selection) => selection.completionId === completion.completionId);\n\n        if (index >= 0) {\n            newSelection.splice(index, 1);\n        } else {\n            newSelection.push(completion);\n        }\n\n        onSelectionChange(newSelection);\n        focusEditor();\n        setQuery(\"\");\n        setSuggestions([]);\n    };\n\n    const removeSelection = (completion: ICompletion): void => {\n        const newSelection = [...selection];\n        const index = selection.findIndex((selection) => selection.completionId === completion.completionId);\n\n        if (index >= 0) {\n            newSelection.splice(index, 1);\n            onSelectionChange(newSelection);\n        }\n    };\n\n    const hasPlaceholder = (): boolean => selection.length === 0 && query.length === 0;\n\n    return (\n        <div className=\"mx_AutocompleteInput\">\n            <div\n                ref={editorContainerRef}\n                className={classNames({\n                    \"mx_AutocompleteInput_editor\": true,\n                    \"mx_AutocompleteInput_editor--focused\": isFocused,\n                    \"mx_AutocompleteInput_editor--has-suggestions\": suggestions.length > 0,\n                })}\n                onClick={onClickInputArea}\n                data-testid=\"autocomplete-editor\"\n            >\n                <SearchIcon className=\"mx_AutocompleteInput_search_icon\" width=\"18px\" height=\"18px\" />\n                {selection.map((item) => (\n                    <SelectionItem\n                        key={item.completionId}\n                        item={item}\n                        onClick={removeSelection}\n                        render={renderSelection}\n                    />\n                ))}\n                <input\n                    ref={editorRef}\n                    type=\"text\"\n                    onKeyDown={onKeyDown}\n                    onChange={onQueryChange}\n                    value={query}\n                    autoComplete=\"off\"\n                    placeholder={hasPlaceholder() ? placeholder : undefined}\n                    data-testid=\"autocomplete-input\"\n                    {...onFocusChangeHandlerFunctions}\n                />\n            </div>\n            {isFocused && suggestions.length ? (\n                <div\n                    className=\"mx_AutocompleteInput_matches\"\n                    // eslint-disable-next-line react-compiler/react-compiler\n                    style={{ top: editorContainerRef.current?.clientHeight }}\n                    data-testid=\"autocomplete-matches\"\n                >\n                    {suggestions.map((item) => (\n                        <SuggestionItem\n                            key={item.completionId}\n                            item={item}\n                            selection={selection}\n                            onClick={toggleSelection}\n                            render={renderSuggestion}\n                        />\n                    ))}\n                </div>\n            ) : null}\n        </div>\n    );\n};\n\ntype SelectionItemProps = {\n    item: ICompletion;\n    onClick: (completion: ICompletion) => void;\n    render?: (completion: ICompletion) => ReactElement;\n};\n\nconst SelectionItem: React.FC<SelectionItemProps> = ({ item, onClick, render }) => {\n    const withContainer = (children: ReactNode): ReactElement => (\n        <span\n            className=\"mx_AutocompleteInput_editor_selection\"\n            data-testid={`autocomplete-selection-item-${item.completionId}`}\n        >\n            <span className=\"mx_AutocompleteInput_editor_selection_pill\">{children}</span>\n            <AccessibleButton\n                className=\"mx_AutocompleteInput_editor_selection_remove_button\"\n                onClick={() => onClick(item)}\n                data-testid={`autocomplete-selection-remove-button-${item.completionId}`}\n            >\n                <CloseIcon width=\"16px\" height=\"16px\" />\n            </AccessibleButton>\n        </span>\n    );\n\n    if (render) {\n        return withContainer(render(item));\n    }\n\n    return withContainer(<span className=\"mx_AutocompleteInput_editor_selection_text\">{item.completion}</span>);\n};\n\ntype SuggestionItemProps = {\n    item: ICompletion;\n    selection: ICompletion[];\n    onClick: (completion: ICompletion) => void;\n    render?: (completion: ICompletion) => ReactElement;\n};\n\nconst SuggestionItem: React.FC<SuggestionItemProps> = ({ item, selection, onClick, render }) => {\n    const isSelected = selection.some((selection) => selection.completionId === item.completionId);\n    const classes = classNames({\n        \"mx_AutocompleteInput_suggestion\": true,\n        \"mx_AutocompleteInput_suggestion--selected\": isSelected,\n    });\n\n    const withContainer = (children: ReactNode): ReactElement => (\n        <div\n            className={classes}\n            // `onClick` cannot be used here as it would lead to focus loss and closing the suggestion list.\n            onMouseDown={(event) => {\n                event.preventDefault();\n                onClick(item);\n            }}\n            data-testid={`autocomplete-suggestion-item-${item.completionId}`}\n        >\n            {children}\n        </div>\n    );\n\n    if (render) {\n        return withContainer(render(item));\n    }\n\n    return withContainer(\n        <>\n            <span className=\"mx_AutocompleteInput_suggestion_title\">{item.completion}</span>\n            <span className=\"mx_AutocompleteInput_suggestion_description\">{item.completionId}</span>\n        </>,\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type FormEvent, useCallback, useContext, useRef, useState } from \"react\";\nimport { type Room, EventType } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { type ICompletion } from \"../../../autocomplete/Autocompleter\";\nimport UserProvider from \"../../../autocomplete/UserProvider\";\nimport { AutocompleteInput } from \"../../structures/AutocompleteInput\";\nimport PowerSelector from \"../elements/PowerSelector\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport Modal from \"../../../Modal\";\nimport ErrorDialog from \"../dialogs/ErrorDialog\";\nimport SettingsFieldset from \"./SettingsFieldset\";\n\ninterface AddPrivilegedUsersProps {\n    room: Room;\n    defaultUserLevel: number;\n}\n\nexport const AddPrivilegedUsers: React.FC<AddPrivilegedUsersProps> = ({ room, defaultUserLevel }) => {\n    const client = useContext(MatrixClientContext);\n    const userProvider = useRef(new UserProvider(room));\n    const [isLoading, setIsLoading] = useState<boolean>(false);\n    const [powerLevel, setPowerLevel] = useState<number>(defaultUserLevel);\n    const [selectedUsers, setSelectedUsers] = useState<ICompletion[]>([]);\n    const hasLowerOrEqualLevelThanDefaultLevelFilter = useCallback(\n        (user: ICompletion) => hasLowerOrEqualLevelThanDefaultLevel(room, user, defaultUserLevel),\n        [room, defaultUserLevel],\n    );\n\n    const onSubmit = async (event: FormEvent): Promise<void> => {\n        event.preventDefault();\n        setIsLoading(true);\n\n        const userIds = getUserIdsFromCompletions(selectedUsers);\n        const powerLevelEvent = room.currentState.getStateEvents(EventType.RoomPowerLevels, \"\");\n\n        // `RoomPowerLevels` event should exist, but technically it is not guaranteed.\n        if (powerLevelEvent === null) {\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"common|error\"),\n                description: _t(\"error|update_power_level\"),\n            });\n\n            return;\n        }\n\n        try {\n            await client.setPowerLevel(room.roomId, userIds, powerLevel);\n            setSelectedUsers([]);\n            setPowerLevel(defaultUserLevel);\n        } catch {\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"common|error\"),\n                description: _t(\"error|update_power_level\"),\n            });\n        } finally {\n            setIsLoading(false);\n        }\n    };\n\n    return (\n        <form style={{ display: \"flex\" }} onSubmit={onSubmit}>\n            <SettingsFieldset\n                legend={_t(\"room_settings|permissions|add_privileged_user_heading\")}\n                description={_t(\"room_settings|permissions|add_privileged_user_description\")}\n                style={{ flexGrow: 1 }}\n            >\n                <AutocompleteInput\n                    provider={userProvider.current}\n                    placeholder={_t(\"room_settings|permissions|add_privileged_user_filter_placeholder\")}\n                    onSelectionChange={setSelectedUsers}\n                    selection={selectedUsers}\n                    additionalFilter={hasLowerOrEqualLevelThanDefaultLevelFilter}\n                />\n                <PowerSelector value={powerLevel} onChange={setPowerLevel} />\n                <AccessibleButton\n                    type=\"submit\"\n                    element=\"button\"\n                    kind=\"primary\"\n                    disabled={!selectedUsers.length || isLoading}\n                    onClick={null}\n                    data-testid=\"add-privileged-users-submit-button\"\n                >\n                    {_t(\"action|apply\")}\n                </AccessibleButton>\n            </SettingsFieldset>\n        </form>\n    );\n};\n\nexport const hasLowerOrEqualLevelThanDefaultLevel = (\n    room: Room,\n    user: ICompletion,\n    defaultUserLevel: number,\n): boolean => {\n    if (user.completionId === undefined) {\n        return false;\n    }\n\n    const member = room.getMember(user.completionId);\n\n    if (member === null) {\n        return false;\n    }\n\n    return member.powerLevel <= defaultUserLevel;\n};\n\nexport const getUserIdsFromCompletions = (completions: ICompletion[]): string[] => {\n    const completionsWithId = completions.filter((completion) => completion.completionId !== undefined);\n\n    // undefined completionId's are filtered out above but TypeScript does not seem to understand.\n    return completionsWithId.map((completion) => completion.completionId!);\n};\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2024 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport React, { useState, type JSX, type PropsWithChildren } from \"react\";\nimport { Button } from \"@vector-im/compound-web\";\n\nimport { useMatrixClientContext } from \"../../../contexts/MatrixClientContext\";\nimport PowerSelector from \"../elements/PowerSelector\";\nimport { _t } from \"../../../languageHandler\";\nimport SettingsFieldset from \"./SettingsFieldset\";\nimport Modal from \"../../../Modal\";\nimport QuestionDialog from \"../dialogs/QuestionDialog\";\n\n/**\n * Display in a fieldset, the power level of the users and allow to change them.\n * The apply button is disabled until the power level of an user is changed.\n * If there is no user to display, the children is displayed instead.\n */\ninterface PowerLevelSelectorProps {\n    /**\n     * The power levels of the users\n     * The key is the user id and the value is the power level\n     */\n    userLevels: Record<string, number>;\n    /**\n     * Whether the user can change the power levels of other users\n     */\n    canChangeLevels: boolean;\n    /**\n     * The current user's own power level\n     */\n    currentUserLevel: number;\n    /**\n     * The callback when the apply button is clicked\n     * @param value - new power level for the user\n     * @param userId - the user id\n     */\n    onClick: (value: number, userId: string) => void;\n    /**\n     * Filter the users to display\n     * @param user\n     */\n    filter: (user: string) => boolean;\n    /**\n     * The title of the fieldset\n     */\n    title: string;\n}\n\nexport function PowerLevelSelector({\n    userLevels,\n    canChangeLevels,\n    currentUserLevel,\n    onClick,\n    filter,\n    title,\n    children,\n}: PropsWithChildren<PowerLevelSelectorProps>): JSX.Element | null {\n    const matrixClient = useMatrixClientContext();\n    const [currentPowerLevel, setCurrentPowerLevel] = useState<{ value: number; userId: string } | null>(null);\n\n    // If the power level has changed, we need to enable the apply button\n    const powerLevelChanged = Boolean(\n        currentPowerLevel && currentPowerLevel.value !== userLevels[currentPowerLevel?.userId],\n    );\n\n    const collator = new Intl.Collator();\n\n    // We sort the users by power level, then we filter them\n    const users = Object.keys(userLevels)\n        .sort((userA, userB) => sortUser(collator, userA, userB, userLevels))\n        .filter(filter);\n\n    // No user to display, we return the children into fragment to convert it to JSX.Element type\n    if (!users.length) return <>{children}</>;\n\n    // check at least one admin in the list\n    const roomHasAtLeastOneAdmin = (usersLevels: Record<string, number>): boolean => {\n        const userLevelValues = Object.values(usersLevels);\n        // At least one user as the pL 100 which means he is admin\n        return userLevelValues.some((uL) => uL === 100);\n    };\n\n    return (\n        <SettingsFieldset legend={title}>\n            {users.map((userId) => {\n                // We only want to display users with a valid power level aka an integer\n                if (!Number.isInteger(userLevels[userId])) return;\n\n                const isMe = userId === matrixClient.getUserId();\n                // If I can change levels, I can change the level of anyone with a lower level than mine\n                const canChange = canChangeLevels && (userLevels[userId] < currentUserLevel || isMe);\n\n                // When the new power level is selected, the fields are rerendered and we need to keep the current value\n                const userLevel = currentPowerLevel?.userId === userId ? currentPowerLevel?.value : userLevels[userId];\n\n                return (\n                    <PowerSelector\n                        value={userLevel}\n                        disabled={!canChange}\n                        label={userId}\n                        key={userId}\n                        maxValue={currentUserLevel}\n                        onChange={async (value) => {\n                            const userLevelsTmp = Object.assign({}, userLevels);\n                            userLevelsTmp[userId] = value;\n                            if (!roomHasAtLeastOneAdmin(userLevelsTmp)) {\n                                const { finished } = Modal.createDialog(QuestionDialog, {\n                                    title: _t(\"common|warning\"),\n                                    description: <div>{_t(\"user_info|demote_self_confirm_room\")}</div>,\n                                    button: _t(\"action|continue\"),\n                                });\n                                const [confirmed] = await finished;\n                                if (!confirmed) {\n                                    // if cancel, we reput initial value\n                                    setCurrentPowerLevel({ value: userLevels[userId], userId });\n                                    return;\n                                }\n                            }\n                            setCurrentPowerLevel({ value, userId });\n                        }}\n                    />\n                );\n            })}\n\n            <Button\n                size=\"sm\"\n                kind=\"primary\"\n                // mx_Dialog_nonDialogButton is necessary to avoid the Dialog CSS to override the button style\n                className=\"mx_Dialog_nonDialogButton mx_PowerLevelSelector_Button\"\n                onClick={() => {\n                    if (currentPowerLevel !== null) {\n                        onClick(currentPowerLevel.value, currentPowerLevel.userId);\n                        setCurrentPowerLevel(null);\n                    }\n                }}\n                disabled={!powerLevelChanged}\n                aria-label={_t(\"action|apply\")}\n            >\n                {_t(\"action|apply\")}\n            </Button>\n        </SettingsFieldset>\n    );\n}\n\n/**\n * Sort the users by power level, then by name\n * @param userA\n * @param userB\n * @param userLevels\n */\nfunction sortUser(\n    collator: Intl.Collator,\n    userA: string,\n    userB: string,\n    userLevels: PowerLevelSelectorProps[\"userLevels\"],\n): number {\n    const powerLevelDiff = userLevels[userA] - userLevels[userB];\n    return powerLevelDiff !== 0\n        ? powerLevelDiff\n        : collator.compare(userA.toLocaleLowerCase(), userB.toLocaleLowerCase());\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { EventType, type RoomMember, type RoomState, RoomStateEvent, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { throttle, get, set } from \"lodash\";\nimport { KnownMembership, type RoomPowerLevelsEventContent } from \"matrix-js-sdk/src/types\";\n\nimport { _t, _td } from \"../../../../../languageHandler\";\nimport AccessibleButton from \"../../../elements/AccessibleButton\";\nimport Modal from \"../../../../../Modal\";\nimport ErrorDialog from \"../../../dialogs/ErrorDialog\";\nimport PowerSelector from \"../../../elements/PowerSelector\";\nimport SettingsFieldset from \"../../SettingsFieldset\";\nimport SettingsStore from \"../../../../../settings/SettingsStore\";\nimport SdkConfig, { DEFAULTS } from \"../../../../../SdkConfig\";\nimport { AddPrivilegedUsers } from \"../../AddPrivilegedUsers\";\nimport SettingsTab from \"../SettingsTab\";\nimport { SettingsSection } from \"../../shared/SettingsSection\";\nimport MatrixClientContext from \"../../../../../contexts/MatrixClientContext\";\nimport { PowerLevelSelector } from \"../../PowerLevelSelector\";\nimport { ElementCallEventType, ElementCallMemberEventType } from \"../../../../../call-types\";\nimport { objectClone } from \"../../../../../utils/objects.ts\";\n\ninterface IEventShowOpts {\n    isState?: boolean;\n    hideForSpace?: boolean;\n    hideForRoom?: boolean;\n}\n\ninterface IPowerLevelDescriptor {\n    desc: string;\n    defaultValue: number;\n    hideForSpace?: boolean;\n}\n\nconst plEventsToShow: Record<string, IEventShowOpts> = {\n    // If an event is listed here, it will be shown in the PL settings. Defaults will be calculated.\n    [EventType.RoomAvatar]: { isState: true },\n    [EventType.RoomName]: { isState: true },\n    [EventType.RoomCanonicalAlias]: { isState: true },\n    [EventType.SpaceChild]: { isState: true, hideForRoom: true },\n    [EventType.RoomHistoryVisibility]: { isState: true, hideForSpace: true },\n    [EventType.RoomPowerLevels]: { isState: true },\n    [EventType.RoomTopic]: { isState: true },\n    [EventType.RoomTombstone]: { isState: true, hideForSpace: true },\n    [EventType.RoomEncryption]: { isState: true, hideForSpace: true },\n    [EventType.RoomServerAcl]: { isState: true, hideForSpace: true },\n    [EventType.RoomPinnedEvents]: { isState: true, hideForSpace: true },\n    [EventType.Reaction]: { isState: false, hideForSpace: true },\n    [EventType.RoomRedaction]: { isState: false, hideForSpace: true },\n\n    // MSC3401: Native Group VoIP signaling\n    [ElementCallEventType.name]: { isState: true, hideForSpace: true },\n    [ElementCallMemberEventType.name]: { isState: true, hideForSpace: true },\n\n    // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n    \"im.vector.modular.widgets\": { isState: true, hideForSpace: true },\n};\n\n// parse a string as an integer; if the input is undefined, or cannot be parsed\n// as an integer, return a default.\nfunction parseIntWithDefault(val: string, def: number): number {\n    const res = parseInt(val);\n    return isNaN(res) ? def : res;\n}\n\ninterface IBannedUserProps {\n    canUnban?: boolean;\n    member: RoomMember;\n    by: string;\n    reason?: string;\n}\n\nexport class BannedUser extends React.Component<IBannedUserProps> {\n    public static contextType = MatrixClientContext;\n    declare public context: React.ContextType<typeof MatrixClientContext>;\n\n    private onUnbanClick = (): void => {\n        this.context.unban(this.props.member.roomId, this.props.member.userId).catch((err) => {\n            logger.error(\"Failed to unban: \" + err);\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"common|error\"),\n                description: _t(\"room_settings|permissions|error_unbanning\"),\n            });\n        });\n    };\n\n    public render(): React.ReactNode {\n        let unbanButton;\n\n        if (this.props.canUnban) {\n            unbanButton = (\n                <AccessibleButton\n                    className=\"mx_RolesRoomSettingsTab_unbanBtn\"\n                    kind=\"danger_sm\"\n                    onClick={this.onUnbanClick}\n                >\n                    {_t(\"action|unban\")}\n                </AccessibleButton>\n            );\n        }\n\n        const userId = this.props.member.name === this.props.member.userId ? null : this.props.member.userId;\n        return (\n            <li>\n                {unbanButton}\n                <span title={_t(\"room_settings|permissions|banned_by\", { displayName: this.props.by })}>\n                    <strong>{this.props.member.name}</strong> {userId}\n                    {this.props.reason\n                        ? \" \" + _t(\"room_settings|permissions|ban_reason\") + \": \" + this.props.reason\n                        : \"\"}\n                </span>\n            </li>\n        );\n    }\n}\n\ninterface IProps {\n    room: Room;\n}\n\ninterface RolesRoomSettingsTabState {\n    isRoomEncrypted: boolean;\n    isReady: boolean;\n}\n\nconst EVENTS_LEVEL_PREFIX = \"event_levels_\";\n\nexport default class RolesRoomSettingsTab extends React.Component<IProps, RolesRoomSettingsTabState> {\n    public static contextType = MatrixClientContext;\n    declare public context: React.ContextType<typeof MatrixClientContext>;\n\n    public constructor(props: IProps) {\n        super(props);\n        this.state = {\n            isReady: false,\n            isRoomEncrypted: false,\n        };\n    }\n\n    public async componentDidMount(): Promise<void> {\n        this.context.on(RoomStateEvent.Update, this.onRoomStateUpdate);\n        this.setState({\n            isRoomEncrypted:\n                (await this.context.getCrypto()?.isEncryptionEnabledInRoom(this.props.room.roomId)) || false,\n            isReady: true,\n        });\n    }\n\n    public componentWillUnmount(): void {\n        const client = this.context;\n        if (client) {\n            client.removeListener(RoomStateEvent.Update, this.onRoomStateUpdate);\n        }\n    }\n\n    private onRoomStateUpdate = (state: RoomState): void => {\n        if (state.roomId !== this.props.room.roomId) return;\n        this.onThisRoomMembership();\n    };\n\n    private onThisRoomMembership = throttle(\n        () => {\n            this.forceUpdate();\n        },\n        200,\n        { leading: true, trailing: true },\n    );\n\n    private populateDefaultPlEvents(\n        eventsSection: Record<string, number>,\n        stateLevel: number,\n        eventsLevel: number,\n    ): void {\n        for (const desiredEvent of Object.keys(plEventsToShow)) {\n            if (!(desiredEvent in eventsSection)) {\n                eventsSection[desiredEvent] = plEventsToShow[desiredEvent].isState ? stateLevel : eventsLevel;\n            }\n        }\n    }\n\n    private onPowerLevelsChanged = async (value: number, powerLevelKey: string): Promise<void> => {\n        const client = this.context;\n        const room = this.props.room;\n        const plEvent = room.currentState.getStateEvents(EventType.RoomPowerLevels, \"\");\n        let plContent = plEvent?.getContent<RoomPowerLevelsEventContent>() ?? {};\n\n        // Clone the power levels just in case\n        plContent = Object.assign({}, plContent);\n\n        if (powerLevelKey.startsWith(EVENTS_LEVEL_PREFIX)) {\n            set(plContent, [\"events\", powerLevelKey.slice(EVENTS_LEVEL_PREFIX.length)], value);\n        } else {\n            set(plContent, powerLevelKey.split(\".\"), value);\n        }\n\n        try {\n            await client.sendStateEvent(this.props.room.roomId, EventType.RoomPowerLevels, plContent);\n        } catch (e) {\n            logger.error(e);\n\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"room_settings|permissions|error_changing_pl_reqs_title\"),\n                description: _t(\"room_settings|permissions|error_changing_pl_reqs_description\"),\n            });\n\n            // Rethrow so that the PowerSelector can roll back\n            throw e;\n        }\n    };\n\n    private onUserPowerLevelChanged = async (value: number, powerLevelKey: string): Promise<void> => {\n        const client = this.context;\n        const room = this.props.room;\n        const plEvent = room.currentState.getStateEvents(EventType.RoomPowerLevels, \"\");\n        let plContent = plEvent?.getContent<RoomPowerLevelsEventContent>() ?? {};\n\n        // Clone the power levels so we can modify it without clobbering the js-sdk\n        plContent = objectClone({ users: {}, ...plContent });\n        plContent[\"users\"]![powerLevelKey] = value;\n\n        try {\n            await client.sendStateEvent(this.props.room.roomId, EventType.RoomPowerLevels, plContent);\n        } catch (e) {\n            logger.error(e);\n\n            Modal.createDialog(ErrorDialog, {\n                title: _t(\"room_settings|permissions|error_changing_pl_title\"),\n                description: _t(\"room_settings|permissions|error_changing_pl_description\"),\n            });\n        }\n    };\n\n    public render(): React.ReactNode {\n        const client = this.context;\n        const room = this.props.room;\n        const isSpaceRoom = room.isSpaceRoom();\n\n        const plEvent = room.currentState.getStateEvents(EventType.RoomPowerLevels, \"\");\n        const plContent = plEvent ? plEvent.getContent() || {} : {};\n        const canChangeLevels = room.currentState.mayClientSendStateEvent(EventType.RoomPowerLevels, client);\n\n        const plEventsToLabels: Record<EventType | string, TranslationKey | null> = {\n            // These will be translated for us later.\n            [EventType.RoomAvatar]: isSpaceRoom\n                ? _td(\"room_settings|permissions|m.room.avatar_space\")\n                : _td(\"room_settings|permissions|m.room.avatar\"),\n            [EventType.RoomName]: isSpaceRoom\n                ? _td(\"room_settings|permissions|m.room.name_space\")\n                : _td(\"room_settings|permissions|m.room.name\"),\n            [EventType.RoomCanonicalAlias]: isSpaceRoom\n                ? _td(\"room_settings|permissions|m.room.canonical_alias_space\")\n                : _td(\"room_settings|permissions|m.room.canonical_alias\"),\n            [EventType.SpaceChild]: _td(\"room_settings|permissions|m.space.child\"),\n            [EventType.RoomHistoryVisibility]: _td(\"room_settings|permissions|m.room.history_visibility\"),\n            [EventType.RoomPowerLevels]: _td(\"room_settings|permissions|m.room.power_levels\"),\n            [EventType.RoomTopic]: isSpaceRoom\n                ? _td(\"room_settings|permissions|m.room.topic_space\")\n                : _td(\"room_settings|permissions|m.room.topic\"),\n            [EventType.RoomTombstone]: _td(\"room_settings|permissions|m.room.tombstone\"),\n            [EventType.RoomEncryption]: _td(\"room_settings|permissions|m.room.encryption\"),\n            [EventType.RoomServerAcl]: _td(\"room_settings|permissions|m.room.server_acl\"),\n            [EventType.Reaction]: _td(\"room_settings|permissions|m.reaction\"),\n            [EventType.RoomRedaction]: _td(\"room_settings|permissions|m.room.redaction\"),\n            [EventType.RoomPinnedEvents]: _td(\"room_settings|permissions|m.room.pinned_events\"),\n\n            // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n            \"im.vector.modular.widgets\": isSpaceRoom ? null : _td(\"room_settings|permissions|m.widget\"),\n        };\n\n        // MSC3401: Native Group VoIP signaling\n        if (SettingsStore.getValue(\"feature_group_calls\")) {\n            plEventsToLabels[ElementCallEventType.name] = _td(\"room_settings|permissions|m.call\");\n            plEventsToLabels[ElementCallMemberEventType.name] = _td(\"room_settings|permissions|m.call.member\");\n        }\n\n        const powerLevelDescriptors: Record<string, IPowerLevelDescriptor> = {\n            \"users_default\": {\n                desc: _t(\"room_settings|permissions|users_default\"),\n                defaultValue: 0,\n            },\n            \"events_default\": {\n                desc: _t(\"room_settings|permissions|events_default\"),\n                defaultValue: 0,\n                hideForSpace: true,\n            },\n            \"invite\": {\n                desc: _t(\"room_settings|permissions|invite\"),\n                defaultValue: 0,\n            },\n            \"state_default\": {\n                desc: _t(\"room_settings|permissions|state_default\"),\n                defaultValue: 50,\n            },\n            \"kick\": {\n                desc: _t(\"room_settings|permissions|kick\"),\n                defaultValue: 50,\n            },\n            \"ban\": {\n                desc: _t(\"room_settings|permissions|ban\"),\n                defaultValue: 50,\n            },\n            \"redact\": {\n                desc: _t(\"room_settings|permissions|redact\"),\n                defaultValue: 50,\n                hideForSpace: true,\n            },\n            \"notifications.room\": {\n                desc: _t(\"room_settings|permissions|notifications.room\"),\n                defaultValue: 50,\n                hideForSpace: true,\n            },\n        };\n\n        const eventsLevels = plContent.events || {};\n        const userLevels = plContent.users || {};\n        const banLevel = parseIntWithDefault(plContent.ban, powerLevelDescriptors.ban.defaultValue);\n        const defaultUserLevel = parseIntWithDefault(\n            plContent.users_default,\n            powerLevelDescriptors.users_default.defaultValue,\n        );\n\n        const currentUserLevel = room.getMember(client.getSafeUserId())?.powerLevel ?? defaultUserLevel;\n\n        this.populateDefaultPlEvents(\n            eventsLevels,\n            parseIntWithDefault(plContent.state_default, powerLevelDescriptors.state_default.defaultValue),\n            parseIntWithDefault(plContent.events_default, powerLevelDescriptors.events_default.defaultValue),\n        );\n\n        let privilegedUsersSection = <div>{_t(\"room_settings|permissions|no_privileged_users\")}</div>;\n        let mutedUsersSection;\n        if (Object.keys(userLevels).length) {\n            privilegedUsersSection = (\n                <PowerLevelSelector\n                    title={_t(\"room_settings|permissions|privileged_users_section\")}\n                    userLevels={userLevels}\n                    canChangeLevels={canChangeLevels}\n                    currentUserLevel={currentUserLevel}\n                    onClick={this.onUserPowerLevelChanged}\n                    filter={(user) => userLevels[user] > defaultUserLevel}\n                >\n                    <div>{_t(\"room_settings|permissions|no_privileged_users\")}</div>\n                </PowerLevelSelector>\n            );\n\n            mutedUsersSection = (\n                <PowerLevelSelector\n                    title={_t(\"room_settings|permissions|muted_users_section\")}\n                    userLevels={userLevels}\n                    canChangeLevels={canChangeLevels}\n                    currentUserLevel={currentUserLevel}\n                    onClick={this.onUserPowerLevelChanged}\n                    filter={(user) => userLevels[user] < defaultUserLevel}\n                />\n            );\n        }\n\n        const banned = room.getMembersWithMembership(KnownMembership.Ban);\n        let bannedUsersSection: JSX.Element | undefined;\n        if (banned?.length) {\n            const canBanUsers = currentUserLevel >= banLevel;\n            bannedUsersSection = (\n                <SettingsFieldset legend={_t(\"room_settings|permissions|banned_users_section\")}>\n                    <ul className=\"mx_RolesRoomSettingsTab_bannedList\">\n                        {banned.map((member) => {\n                            const banEvent = member.events.member?.getContent();\n                            const bannedById = member.events.member?.getSender();\n                            const sender = bannedById ? room.getMember(bannedById) : undefined;\n                            const bannedBy = sender?.name || bannedById; // fallback to mxid\n                            return (\n                                <BannedUser\n                                    key={member.userId}\n                                    canUnban={canBanUsers}\n                                    member={member}\n                                    reason={banEvent?.reason}\n                                    by={bannedBy!}\n                                />\n                            );\n                        })}\n                    </ul>\n                </SettingsFieldset>\n            );\n        }\n\n        const powerSelectors = Object.keys(powerLevelDescriptors)\n            .map((key, index) => {\n                const descriptor = powerLevelDescriptors[key];\n                if (isSpaceRoom && descriptor.hideForSpace) {\n                    return null;\n                }\n\n                const value = parseIntWithDefault(get(plContent, key), descriptor.defaultValue);\n                return (\n                    <div key={index} className=\"\">\n                        <PowerSelector\n                            label={descriptor.desc}\n                            value={value}\n                            usersDefault={defaultUserLevel}\n                            disabled={!canChangeLevels || currentUserLevel < value}\n                            powerLevelKey={key} // Will be sent as the second parameter to `onChange`\n                            onChange={this.onPowerLevelsChanged}\n                        />\n                    </div>\n                );\n            })\n            .filter(Boolean);\n\n        // hide the power level selector for enabling E2EE if it the room is already encrypted\n        if (this.state.isRoomEncrypted) {\n            delete eventsLevels[EventType.RoomEncryption];\n        }\n\n        const eventPowerSelectors = Object.keys(eventsLevels)\n            .map((eventType, i) => {\n                if (isSpaceRoom && plEventsToShow[eventType]?.hideForSpace) {\n                    return null;\n                } else if (!isSpaceRoom && plEventsToShow[eventType]?.hideForRoom) {\n                    return null;\n                }\n\n                const translationKeyForEvent = plEventsToLabels[eventType];\n                let label: string;\n                if (translationKeyForEvent) {\n                    const brand = SdkConfig.get(\"element_call\").brand ?? DEFAULTS.element_call.brand;\n                    label = _t(translationKeyForEvent, { brand });\n                } else {\n                    label = _t(\"room_settings|permissions|send_event_type\", { eventType });\n                }\n                return (\n                    <div key={eventType}>\n                        <PowerSelector\n                            label={label}\n                            value={eventsLevels[eventType]}\n                            usersDefault={defaultUserLevel}\n                            disabled={!canChangeLevels || currentUserLevel < eventsLevels[eventType]}\n                            powerLevelKey={EVENTS_LEVEL_PREFIX + eventType}\n                            onChange={this.onPowerLevelsChanged}\n                        />\n                    </div>\n                );\n            })\n            .filter(Boolean);\n\n        return (\n            <SettingsTab>\n                <SettingsSection heading={_t(\"room_settings|permissions|title\")}>\n                    {privilegedUsersSection}\n                    {canChangeLevels && <AddPrivilegedUsers room={room} defaultUserLevel={defaultUserLevel} />}\n                    {mutedUsersSection}\n                    {bannedUsersSection}\n                    {this.state.isReady && (\n                        <SettingsFieldset\n                            legend={_t(\"room_settings|permissions|permissions_section\")}\n                            description={\n                                isSpaceRoom\n                                    ? _t(\"room_settings|permissions|permissions_section_description_space\")\n                                    : _t(\"room_settings|permissions|permissions_section_description_room\")\n                            }\n                        >\n                            {powerSelectors}\n                            {eventPowerSelectors}\n                        </SettingsFieldset>\n                    )}\n                </SettingsSection>\n            </SettingsTab>\n        );\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEventHandler, useCallback } from \"react\";\nimport { Field, HelpMessage, InlineField, Label, RadioInput, Root, SettingsToggleInput } from \"@vector-im/compound-web\";\n\nimport { type MediaPreviewConfig, MediaPreviewValue } from \"../../../../../@types/media_preview\";\nimport { _t } from \"../../../../../languageHandler\";\nimport { useSettingValue } from \"../../../../../hooks/useSettings\";\nimport SettingsStore from \"../../../../../settings/SettingsStore\";\nimport { SettingLevel } from \"../../../../../settings/SettingLevel\";\n\nexport const MediaPreviewAccountSettings: React.FC<{ roomId?: string }> = ({ roomId }) => {\n    const currentMediaPreview = useSettingValue(\"mediaPreviewConfig\", roomId);\n\n    const changeSetting = useCallback(\n        (newValue: MediaPreviewConfig) => {\n            SettingsStore.setValue(\n                \"mediaPreviewConfig\",\n                roomId ?? null,\n                roomId ? SettingLevel.ROOM_ACCOUNT : SettingLevel.ACCOUNT,\n                newValue,\n            );\n        },\n        [roomId],\n    );\n\n    const avatarOnChange = useCallback<ChangeEventHandler<HTMLInputElement>>(\n        (evt) => {\n            changeSetting({\n                ...currentMediaPreview,\n                // Switch is inverted. \"Hide avatars...\"\n                invite_avatars: evt.target.checked ? MediaPreviewValue.Off : MediaPreviewValue.On,\n            });\n        },\n        [changeSetting, currentMediaPreview],\n    );\n\n    const mediaPreviewOnChangeOff = useCallback<ChangeEventHandler<HTMLInputElement>>(\n        (event) => {\n            if (!event.target.checked) {\n                return;\n            }\n            changeSetting({\n                ...currentMediaPreview,\n                media_previews: MediaPreviewValue.Off,\n            });\n        },\n        [changeSetting, currentMediaPreview],\n    );\n\n    const mediaPreviewOnChangePrivate = useCallback<ChangeEventHandler<HTMLInputElement>>(\n        (event) => {\n            if (!event.target.checked) {\n                return;\n            }\n            changeSetting({\n                ...currentMediaPreview,\n                media_previews: MediaPreviewValue.Private,\n            });\n        },\n        [changeSetting, currentMediaPreview],\n    );\n\n    const mediaPreviewOnChangeOn = useCallback<ChangeEventHandler<HTMLInputElement>>(\n        (event) => {\n            if (!event.target.checked) {\n                return;\n            }\n            changeSetting({\n                ...currentMediaPreview,\n                media_previews: MediaPreviewValue.On,\n            });\n        },\n        [changeSetting, currentMediaPreview],\n    );\n\n    return (\n        <Root className=\"mx_MediaPreviewAccountSetting_Form\">\n            {!roomId && (\n                <SettingsToggleInput\n                    name=\"hide_avatars\"\n                    label={_t(\"settings|media_preview|hide_avatars\")}\n                    checked={currentMediaPreview.invite_avatars === MediaPreviewValue.Off}\n                    onChange={avatarOnChange}\n                />\n            )}\n            {/* Explict label here because htmlFor is not supported for linking to radiogroups */}\n            <Field\n                id=\"mx_media_previews\"\n                role=\"radiogroup\"\n                name=\"media_previews\"\n                aria-label={_t(\"settings|media_preview|media_preview_label\")}\n            >\n                <Label>{_t(\"settings|media_preview|media_preview_label\")}</Label>\n                <HelpMessage className=\"mx_MediaPreviewAccountSetting_RadioHelp\">\n                    {_t(\"settings|media_preview|media_preview_description\")}\n                </HelpMessage>\n                <InlineField\n                    name=\"media_preview_off\"\n                    className=\"mx_MediaPreviewAccountSetting_Radio\"\n                    control={\n                        <RadioInput\n                            id=\"mx_media_previews_off\"\n                            checked={currentMediaPreview.media_previews === MediaPreviewValue.Off}\n                            onChange={mediaPreviewOnChangeOff}\n                        />\n                    }\n                >\n                    <Label htmlFor=\"mx_media_previews_off\">{_t(\"settings|media_preview|hide_media\")}</Label>\n                </InlineField>\n                {!roomId && (\n                    <InlineField\n                        name=\"mx_media_previews_private\"\n                        className=\"mx_MediaPreviewAccountSetting_Radio\"\n                        control={\n                            <RadioInput\n                                id=\"mx_media_previews_private\"\n                                checked={currentMediaPreview.media_previews === MediaPreviewValue.Private}\n                                onChange={mediaPreviewOnChangePrivate}\n                            />\n                        }\n                    >\n                        <Label htmlFor=\"mx_media_previews_private\">\n                            {_t(\"settings|media_preview|show_in_private\")}\n                        </Label>\n                    </InlineField>\n                )}\n                <InlineField\n                    name=\"media_preview_on\"\n                    className=\"mx_MediaPreviewAccountSetting_Radio\"\n                    control={\n                        <RadioInput\n                            id=\"mx_media_previews_on\"\n                            checked={currentMediaPreview.media_previews === MediaPreviewValue.On}\n                            onChange={mediaPreviewOnChangeOn}\n                        />\n                    }\n                >\n                    <Label htmlFor=\"mx_media_previews_on\">{_t(\"settings|media_preview|show_media\")}</Label>\n                </InlineField>\n            </Field>\n        </Root>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEvent, useRef, useState } from \"react\";\nimport { TakePhotoSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport Field from \"../elements/Field\";\nimport { chromeFileInputFix } from \"../../../utils/BrowserWorkarounds\";\n\ninterface IProps {\n    avatarUrl?: string;\n    avatarDisabled?: boolean;\n    name: string;\n    nameDisabled?: boolean;\n    topic?: string;\n    topicDisabled?: boolean;\n    setAvatar(avatar?: File): void;\n    setName(name: string): void;\n    setTopic(topic: string): void;\n}\n\nexport const SpaceAvatar: React.FC<Pick<IProps, \"avatarUrl\" | \"avatarDisabled\" | \"setAvatar\">> = ({\n    avatarUrl,\n    avatarDisabled = false,\n    setAvatar,\n}) => {\n    const avatarUploadRef = useRef<HTMLInputElement>(null);\n    const [avatar, setAvatarDataUrl] = useState(avatarUrl); // avatar data url cache\n\n    let avatarSection;\n    if (avatarDisabled) {\n        if (avatar) {\n            avatarSection = <img className=\"mx_SpaceBasicSettings_avatar\" src={avatar} alt=\"\" />;\n        } else {\n            avatarSection = <div className=\"mx_SpaceBasicSettings_avatar\" />;\n        }\n    } else {\n        if (avatar) {\n            avatarSection = (\n                <React.Fragment>\n                    <AccessibleButton\n                        className=\"mx_SpaceBasicSettings_avatar\"\n                        onClick={() => avatarUploadRef.current?.click()}\n                        element=\"img\"\n                        src={avatar}\n                        alt=\"\"\n                    />\n                    <AccessibleButton\n                        onClick={() => {\n                            if (avatarUploadRef.current) avatarUploadRef.current.value = \"\";\n                            setAvatarDataUrl(undefined);\n                            setAvatar(undefined);\n                        }}\n                        kind=\"link\"\n                        className=\"mx_SpaceBasicSettings_avatar_remove\"\n                        aria-label={_t(\"room_settings|delete_avatar_label\")}\n                    >\n                        {_t(\"action|delete\")}\n                    </AccessibleButton>\n                </React.Fragment>\n            );\n        } else {\n            avatarSection = (\n                <React.Fragment>\n                    <AccessibleButton\n                        className=\"mx_SpaceBasicSettings_avatar\"\n                        onClick={() => avatarUploadRef.current?.click()}\n                    >\n                        <TakePhotoSolidIcon />\n                    </AccessibleButton>\n                    <AccessibleButton\n                        onClick={() => avatarUploadRef.current?.click()}\n                        kind=\"link\"\n                        aria-label={_t(\"room_settings|upload_avatar_label\")}\n                    >\n                        {_t(\"action|upload\")}\n                    </AccessibleButton>\n                </React.Fragment>\n            );\n        }\n    }\n\n    return (\n        <div className=\"mx_SpaceBasicSettings_avatarContainer\">\n            {avatarSection}\n            <input\n                type=\"file\"\n                ref={avatarUploadRef}\n                onClick={chromeFileInputFix}\n                onChange={(e) => {\n                    if (!e.target.files?.length) return;\n                    const file = e.target.files[0];\n                    setAvatar(file);\n                    const reader = new FileReader();\n                    reader.onload = (ev) => {\n                        setAvatarDataUrl(ev.target?.result as string);\n                    };\n                    reader.readAsDataURL(file);\n                }}\n                accept=\"image/*\"\n            />\n        </div>\n    );\n};\n\nconst SpaceBasicSettings: React.FC<IProps> = ({\n    avatarUrl,\n    avatarDisabled = false,\n    setAvatar,\n    name = \"\",\n    nameDisabled = false,\n    setName,\n    topic = \"\",\n    topicDisabled = false,\n    setTopic,\n}) => {\n    return (\n        <div className=\"mx_SpaceBasicSettings\">\n            <SpaceAvatar avatarUrl={avatarUrl} avatarDisabled={avatarDisabled} setAvatar={setAvatar} />\n\n            <Field\n                name=\"spaceName\"\n                label={_t(\"common|name\")}\n                autoFocus={true}\n                value={name}\n                onChange={(ev: ChangeEvent<HTMLInputElement>) => setName(ev.target.value)}\n                disabled={nameDisabled}\n            />\n\n            <Field\n                name=\"spaceTopic\"\n                element=\"textarea\"\n                label={_t(\"common|description\")}\n                value={topic}\n                onChange={(ev: ChangeEvent<HTMLTextAreaElement>) => setTopic(ev.target.value)}\n                rows={3}\n                disabled={topicDisabled}\n            />\n        </div>\n    );\n};\n\nexport default SpaceBasicSettings;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useEffect, useMemo, useState } from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../languageHandler\";\nimport StyledRadioGroup from \"../elements/StyledRadioGroup\";\nimport QueryMatcher from \"../../../autocomplete/QueryMatcher\";\nimport SearchBox from \"../../structures/SearchBox\";\nimport AutoHideScrollbar from \"../../structures/AutoHideScrollbar\";\nimport { Entry } from \"../dialogs/AddExistingToSpaceDialog\";\nimport { filterBoolean } from \"../../../utils/arrays\";\n\nenum Target {\n    All = \"All\",\n    Specific = \"Specific\",\n    None = \"None\",\n}\n\ninterface ISpecificChildrenPickerProps {\n    filterPlaceholder: string;\n    rooms: Room[];\n    selected: Set<Room>;\n    onChange(selected: boolean, room: Room): void;\n}\n\nconst SpecificChildrenPicker: React.FC<ISpecificChildrenPickerProps> = ({\n    filterPlaceholder,\n    rooms,\n    selected,\n    onChange,\n}) => {\n    const [query, setQuery] = useState(\"\");\n    const lcQuery = query.toLowerCase().trim();\n\n    const filteredRooms = useMemo(() => {\n        if (!lcQuery) {\n            return rooms;\n        }\n\n        const matcher = new QueryMatcher<Room>(rooms, {\n            keys: [\"name\"],\n            funcs: [(r) => filterBoolean([r.getCanonicalAlias(), ...r.getAltAliases()])],\n            shouldMatchWordsOnly: false,\n        });\n\n        return matcher.match(lcQuery);\n    }, [rooms, lcQuery]);\n\n    return (\n        <div className=\"mx_SpaceChildrenPicker\">\n            <SearchBox\n                className=\"mx_textinput_icon mx_textinput_search\"\n                placeholder={filterPlaceholder}\n                onSearch={setQuery}\n                autoFocus={true}\n            />\n            <AutoHideScrollbar>\n                {filteredRooms.map((room) => {\n                    return (\n                        <Entry\n                            key={room.roomId}\n                            room={room}\n                            checked={selected.has(room)}\n                            onChange={(checked) => {\n                                onChange(checked, room);\n                            }}\n                        />\n                    );\n                })}\n                {filteredRooms.length < 1 ? (\n                    <span className=\"mx_SpaceChildrenPicker_noResults\">{_t(\"common|no_results\")}</span>\n                ) : undefined}\n            </AutoHideScrollbar>\n        </div>\n    );\n};\n\ninterface IProps {\n    space: Room;\n    spaceChildren: Room[];\n    selected: Set<Room>;\n    noneLabel?: string;\n    allLabel: string;\n    specificLabel: string;\n    onChange(rooms: Room[]): void;\n}\n\nconst SpaceChildrenPicker: React.FC<IProps> = ({\n    space,\n    spaceChildren,\n    selected,\n    onChange,\n    noneLabel,\n    allLabel,\n    specificLabel,\n}) => {\n    const [state, setState] = useState<string>(noneLabel ? Target.None : Target.All);\n\n    useEffect(() => {\n        if (state === Target.All) {\n            onChange(spaceChildren);\n        } else {\n            onChange([]);\n        }\n    }, [onChange, state, spaceChildren]);\n\n    return (\n        <>\n            <div className=\"mx_SpaceChildrenPicker\">\n                <StyledRadioGroup\n                    name=\"roomsToLeave\"\n                    value={state}\n                    onChange={setState}\n                    definitions={[\n                        {\n                            value: Target.None,\n                            label: noneLabel,\n                        },\n                        {\n                            value: Target.All,\n                            label: allLabel,\n                        },\n                        {\n                            value: Target.Specific,\n                            label: specificLabel,\n                        },\n                    ].filter((d) => d.label)}\n                />\n            </div>\n\n            {state === Target.Specific && (\n                <SpecificChildrenPicker\n                    filterPlaceholder={_t(\"space|search_children\", { spaceName: space.name })}\n                    rooms={spaceChildren}\n                    selected={selected}\n                    onChange={(isSelected: boolean, room: Room) => {\n                        if (isSelected) {\n                            onChange([room, ...selected]);\n                        } else {\n                            onChange([...selected].filter((r) => r !== room));\n                        }\n                    }}\n                />\n            )}\n        </>\n    );\n};\n\nexport default SpaceChildrenPicker;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, {\n    type ComponentProps,\n    type RefObject,\n    type SyntheticEvent,\n    type KeyboardEvent,\n    useContext,\n    useRef,\n    useState,\n    type ChangeEvent,\n    type ReactNode,\n    useEffect,\n} from \"react\";\nimport {\n    RoomType,\n    HistoryVisibility,\n    Preset,\n    Visibility,\n    type MatrixClient,\n    type ICreateRoomOpts,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { LockSolidIcon, PublicIcon, ChevronLeftIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport ContextMenu, { ChevronFace } from \"../../structures/ContextMenu\";\nimport createRoom, { type IOpts as ICreateOpts } from \"../../../createRoom\";\nimport MatrixClientContext, { useMatrixClientContext } from \"../../../contexts/MatrixClientContext\";\nimport type SpaceBasicSettings from \"./SpaceBasicSettings\";\nimport { SpaceAvatar } from \"./SpaceBasicSettings\";\nimport AccessibleButton, { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport Field from \"../elements/Field\";\nimport withValidation from \"../elements/Validation\";\nimport RoomAliasField from \"../elements/RoomAliasField\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport defaultDispatcher from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { Filter } from \"../dialogs/spotlight/Filter\";\nimport { type OpenSpotlightPayload } from \"../../../dispatcher/payloads/OpenSpotlightPayload.ts\";\nimport { useSettingValue } from \"../../../hooks/useSettings.ts\";\nimport { UIFeature } from \"../../../settings/UIFeature.ts\";\nimport SpacePillButton from \"../../structures/SpacePillButton.tsx\";\n\nexport const createSpace = async (\n    client: MatrixClient,\n    name: string,\n    isPublic: boolean,\n    alias?: string,\n    topic?: string,\n    avatar?: string | File,\n    createOpts: Partial<ICreateRoomOpts> = {},\n    otherOpts: Partial<Omit<ICreateOpts, \"createOpts\">> = {},\n): Promise<string | null> => {\n    return createRoom(client, {\n        createOpts: {\n            name,\n            preset: isPublic ? Preset.PublicChat : Preset.PrivateChat,\n            visibility:\n                isPublic && (await client.doesServerSupportUnstableFeature(\"org.matrix.msc3827.stable\"))\n                    ? Visibility.Public\n                    : Visibility.Private,\n            power_level_content_override: {\n                // Only allow Admins to write to the timeline to prevent hidden sync spam\n                events_default: 100,\n                invite: isPublic ? 0 : 50,\n            },\n            room_alias_name: isPublic && alias ? alias.substring(1, alias.indexOf(\":\")) : undefined,\n            topic,\n            ...createOpts,\n        },\n        avatar,\n        roomType: RoomType.Space,\n        historyVisibility: isPublic ? HistoryVisibility.WorldReadable : HistoryVisibility.Invited,\n        spinner: false,\n        encryption: false,\n        andView: true,\n        inlineErrors: true,\n        ...otherOpts,\n    });\n};\n\nconst spaceNameValidator = withValidation({\n    rules: [\n        {\n            key: \"required\",\n            test: async ({ value }) => !!value,\n            invalid: () => _t(\"create_space|name_required\"),\n        },\n    ],\n});\n\nconst nameToLocalpart = (name: string): string => {\n    return name\n        .trim()\n        .toLowerCase()\n        .replace(/\\s+/g, \"-\")\n        .replace(/[^a-z0-9_-]+/gi, \"\");\n};\n\ntype BProps = Omit<ComponentProps<typeof SpaceBasicSettings>, \"nameDisabled\" | \"topicDisabled\" | \"avatarDisabled\">;\ninterface ISpaceCreateFormProps extends BProps {\n    busy: boolean;\n    alias: string;\n    nameFieldRef: RefObject<Field | null>;\n    aliasFieldRef: RefObject<RoomAliasField | null>;\n    showAliasField?: boolean;\n    children?: ReactNode;\n    onSubmit(e: SyntheticEvent): void;\n    setAlias(alias: string): void;\n}\n\nexport const SpaceCreateForm: React.FC<ISpaceCreateFormProps> = ({\n    busy,\n    onSubmit,\n    avatarUrl,\n    setAvatar,\n    name,\n    setName,\n    nameFieldRef,\n    alias,\n    aliasFieldRef,\n    setAlias,\n    showAliasField,\n    topic,\n    setTopic,\n    children,\n}) => {\n    const cli = useContext(MatrixClientContext);\n    const domain = cli.getDomain() ?? undefined;\n\n    const onKeyDown = (ev: KeyboardEvent): void => {\n        const action = getKeyBindingsManager().getAccessibilityAction(ev);\n        switch (action) {\n            case KeyBindingAction.Enter:\n                onSubmit(ev);\n                break;\n        }\n    };\n\n    return (\n        <form className=\"mx_SpaceBasicSettings\" onSubmit={onSubmit}>\n            <SpaceAvatar avatarUrl={avatarUrl} setAvatar={setAvatar} avatarDisabled={busy} />\n\n            <Field\n                name=\"spaceName\"\n                label={_t(\"common|name\")}\n                autoFocus={true}\n                value={name}\n                onChange={(ev: ChangeEvent<HTMLInputElement>) => {\n                    const newName = ev.target.value;\n                    if (!alias || alias === `#${nameToLocalpart(name)}:${domain}`) {\n                        setAlias(`#${nameToLocalpart(newName)}:${domain}`);\n                        aliasFieldRef.current?.validate({ allowEmpty: true });\n                    }\n                    setName(newName);\n                }}\n                onKeyDown={onKeyDown}\n                ref={nameFieldRef}\n                onValidate={spaceNameValidator}\n                disabled={busy}\n                autoComplete=\"off\"\n            />\n\n            {showAliasField ? (\n                <RoomAliasField\n                    ref={aliasFieldRef}\n                    onChange={setAlias}\n                    domain={domain}\n                    value={alias}\n                    placeholder={name ? nameToLocalpart(name) : _t(\"create_space|address_placeholder\")}\n                    label={_t(\"create_space|address_label\")}\n                    disabled={busy}\n                    onKeyDown={onKeyDown}\n                />\n            ) : null}\n\n            <Field\n                name=\"spaceTopic\"\n                element=\"textarea\"\n                label={_t(\"common|description\")}\n                value={topic ?? \"\"}\n                onChange={(ev) => setTopic(ev.target.value)}\n                rows={3}\n                disabled={busy}\n            />\n\n            {children}\n        </form>\n    );\n};\n\nconst SpaceCreateMenu: React.FC<{\n    onFinished(): void;\n}> = ({ onFinished }) => {\n    const cli = useMatrixClientContext();\n    const settingAllowPublicSpaces = useSettingValue(UIFeature.AllowCreatingPublicSpaces);\n    const [visibility, setVisibility] = useState<Visibility | null>(\n        settingAllowPublicSpaces === false ? Visibility.Private : null,\n    );\n    const [busy, setBusy] = useState<boolean>(false);\n\n    const [name, setName] = useState(\"\");\n    const spaceNameField = useRef<Field>(null);\n    const [alias, setAlias] = useState(\"\");\n    const spaceAliasField = useRef<RoomAliasField>(null);\n    const [avatar, setAvatar] = useState<File | undefined>(undefined);\n    const [topic, setTopic] = useState<string>(\"\");\n\n    const [supportsSpaceFiltering, setSupportsSpaceFiltering] = useState(true); // assume it does until we find out it doesn't\n    useEffect(() => {\n        cli.isVersionSupported(\"v1.4\")\n            .then((supported) => {\n                return supported || cli.doesServerSupportUnstableFeature(\"org.matrix.msc3827.stable\");\n            })\n            .then((supported) => {\n                setSupportsSpaceFiltering(supported);\n            });\n    }, [cli]);\n\n    const onSpaceCreateClick = async (e: ButtonEvent): Promise<void> => {\n        e.preventDefault();\n        if (busy) return;\n\n        setBusy(true);\n        // require & validate the space name field\n        if (spaceNameField.current && !(await spaceNameField.current.validate({ allowEmpty: false }))) {\n            spaceNameField.current.focus();\n            spaceNameField.current.validate({ allowEmpty: false, focused: true });\n            setBusy(false);\n            return;\n        }\n\n        if (\n            spaceAliasField.current &&\n            visibility === Visibility.Public &&\n            !(await spaceAliasField.current.validate({ allowEmpty: false }))\n        ) {\n            spaceAliasField.current.focus();\n            spaceAliasField.current.validate({ allowEmpty: false, focused: true });\n            setBusy(false);\n            return;\n        }\n\n        try {\n            await createSpace(cli, name, visibility === Visibility.Public, alias, topic, avatar);\n\n            onFinished();\n        } catch (e) {\n            logger.error(e);\n        }\n    };\n\n    const onSearchClick = (): void => {\n        defaultDispatcher.dispatch<OpenSpotlightPayload>({\n            action: Action.OpenSpotlight,\n            initialFilter: Filter.PublicSpaces,\n        });\n    };\n\n    let body;\n    if (visibility === null) {\n        body = (\n            <React.Fragment>\n                <h2>{_t(\"create_space|label\")}</h2>\n                <p>{_t(\"create_space|explainer\")}</p>\n\n                <SpacePillButton\n                    icon={<PublicIcon />}\n                    title={_t(\"common|public\")}\n                    description={_t(\"create_space|public_description\")}\n                    onClick={() => setVisibility(Visibility.Public)}\n                />\n                <SpacePillButton\n                    icon={<LockSolidIcon />}\n                    title={_t(\"common|private\")}\n                    description={_t(\"create_space|private_description\")}\n                    onClick={() => setVisibility(Visibility.Private)}\n                />\n\n                {supportsSpaceFiltering && (\n                    <AccessibleButton kind=\"primary_outline\" onClick={onSearchClick}>\n                        {_t(\"create_space|search_public_button\")}\n                    </AccessibleButton>\n                )}\n            </React.Fragment>\n        );\n    } else {\n        body = (\n            <React.Fragment>\n                {settingAllowPublicSpaces && (\n                    <AccessibleButton\n                        className=\"mx_SpaceCreateMenu_back\"\n                        onClick={() => setVisibility(null)}\n                        title={_t(\"action|go_back\")}\n                    >\n                        <ChevronLeftIcon />\n                    </AccessibleButton>\n                )}\n\n                <h2>\n                    {visibility === Visibility.Public\n                        ? _t(\"create_space|public_heading\")\n                        : settingAllowPublicSpaces\n                          ? _t(\"create_space|private_heading\")\n                          : _t(\"create_space|private_only_heading\")}\n                </h2>\n                <p>\n                    {_t(\"create_space|add_details_prompt\")} {_t(\"create_space|add_details_prompt_2\")}\n                </p>\n\n                <SpaceCreateForm\n                    busy={busy}\n                    onSubmit={onSpaceCreateClick}\n                    setAvatar={setAvatar}\n                    name={name}\n                    setName={setName}\n                    nameFieldRef={spaceNameField}\n                    topic={topic}\n                    setTopic={setTopic}\n                    alias={alias}\n                    setAlias={setAlias}\n                    showAliasField={visibility === Visibility.Public}\n                    aliasFieldRef={spaceAliasField}\n                />\n\n                <AccessibleButton kind=\"primary\" onClick={onSpaceCreateClick} disabled={busy}>\n                    {busy ? _t(\"create_space|creating\") : _t(\"action|create\")}\n                </AccessibleButton>\n            </React.Fragment>\n        );\n    }\n\n    return (\n        <ContextMenu\n            left={72}\n            top={62}\n            chevronOffset={0}\n            chevronFace={ChevronFace.None}\n            onFinished={onFinished}\n            wrapperClassName=\"mx_SpaceCreateMenu_wrapper\"\n            managed={false}\n            focusLock={true}\n        >\n            {body}\n        </ContextMenu>\n    );\n};\n\nexport default SpaceCreateMenu;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useState } from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { sleep } from \"matrix-js-sdk/src/utils\";\nimport { LinkIcon, UserAddIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { copyPlaintext } from \"../../../utils/strings\";\nimport { RoomPermalinkCreator } from \"../../../utils/permalinks/Permalinks\";\nimport { showRoomInviteDialog } from \"../../../RoomInvite\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { shouldShowComponent } from \"../../../customisations/helpers/UIComponents\";\nimport { UIComponent } from \"../../../settings/UIFeature\";\nimport SpacePillButton from \"../../structures/SpacePillButton.tsx\";\n\ninterface IProps {\n    space: Room;\n    onFinished?(): void;\n}\n\nconst SpacePublicShare: React.FC<IProps> = ({ space, onFinished }) => {\n    const [copiedText, setCopiedText] = useState(_t(\"action|click_to_copy\"));\n\n    return (\n        <div className=\"mx_SpacePublicShare\">\n            <SpacePillButton\n                icon={<LinkIcon />}\n                title={_t(\"space|invite_link\")}\n                description={copiedText}\n                onClick={async (): Promise<void> => {\n                    const permalinkCreator = new RoomPermalinkCreator(space);\n                    permalinkCreator.load();\n                    const success = await copyPlaintext(permalinkCreator.forShareableRoom());\n                    const text = success ? _t(\"common|copied\") : _t(\"error|failed_copy\");\n                    setCopiedText(text);\n                    await sleep(5000);\n                    if (copiedText === text) {\n                        // if the text hasn't changed by another click then clear it after some time\n                        setCopiedText(_t(\"action|click_to_copy\"));\n                    }\n                }}\n            />\n            {space.canInvite(MatrixClientPeg.safeGet().getSafeUserId()) &&\n            shouldShowComponent(UIComponent.InviteUsers) ? (\n                <SpacePillButton\n                    icon={<UserAddIcon />}\n                    title={_t(\"space|invite\")}\n                    description={_t(\"space|invite_description\")}\n                    onClick={() => {\n                        if (onFinished) onFinished();\n                        showRoomInviteDialog(space.roomId);\n                    }}\n                />\n            ) : null}\n        </div>\n    );\n};\n\nexport default SpacePublicShare;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ComponentType, type ReactNode } from \"react\";\nimport { Button } from \"@vector-im/compound-web\";\n\nimport { type XOR } from \"../../../@types/common\";\n\nexport interface IProps {\n    description: ReactNode;\n    detail?: ReactNode;\n    primaryLabel: string;\n    PrimaryIcon?: ComponentType<React.SVGAttributes<SVGElement>>;\n\n    onPrimaryClick(): void;\n}\n\ninterface IPropsExtended extends IProps {\n    secondaryLabel: string;\n    SecondaryIcon?: ComponentType<React.SVGAttributes<SVGElement>>;\n    destructive?: \"primary\" | \"secondary\";\n    onSecondaryClick(): void;\n\n    // If set, this will override the max-width (of the description) making the toast wider or narrower than standard\n    overrideWidth?: string;\n}\n\nconst GenericToast: React.FC<XOR<IPropsExtended, IProps>> = ({\n    description,\n    detail,\n    primaryLabel,\n    PrimaryIcon,\n    secondaryLabel,\n    SecondaryIcon,\n    destructive,\n    onPrimaryClick,\n    onSecondaryClick,\n    overrideWidth,\n}) => {\n    const detailContent = detail ? <div className=\"mx_Toast_detail\">{detail}</div> : null;\n\n    return (\n        <div>\n            <div className=\"mx_Toast_description\" style={{ maxWidth: overrideWidth }}>\n                {description}\n                {detailContent}\n            </div>\n            <div className=\"mx_Toast_buttons\" aria-live=\"off\">\n                {onSecondaryClick && secondaryLabel && (\n                    <Button\n                        onClick={onSecondaryClick}\n                        kind={destructive === \"secondary\" ? \"destructive\" : \"secondary\"}\n                        Icon={SecondaryIcon}\n                        size=\"sm\"\n                    >\n                        {secondaryLabel}\n                    </Button>\n                )}\n                <Button\n                    onClick={onPrimaryClick}\n                    kind={destructive === \"primary\" ? \"destructive\" : \"primary\"}\n                    Icon={PrimaryIcon}\n                    size=\"sm\"\n                >\n                    {primaryLabel}\n                </Button>\n            </div>\n        </div>\n    );\n};\n\nexport default GenericToast;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport classNames from \"classnames\";\nimport React, { type HTMLAttributes } from \"react\";\n\ninterface Props extends Omit<HTMLAttributes<HTMLSpanElement>, \"className\"> {\n    children: React.ReactNode;\n    isError?: boolean;\n}\n\nexport const Caption: React.FC<Props> = ({ children, isError, ...rest }) => {\n    return (\n        <span\n            className={classNames(\"mx_Caption\", {\n                mx_Caption_error: isError,\n            })}\n            {...rest}\n        >\n            {children}\n        </span>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type HTMLAttributes } from \"react\";\nimport classNames from \"classnames\";\n\ntype Size = \"1\" | \"2\" | \"3\" | \"4\";\n\ntype HTMLHeadingTags = \"h1\" | \"h2\" | \"h3\" | \"h4\" | \"h5\" | \"h6\";\n\ninterface HeadingProps extends HTMLAttributes<HTMLHeadingElement> {\n    /**\n     * Defines the type of heading used\n     */\n    as?: HTMLHeadingTags;\n    /**\n     * Defines the appearance of the heading\n     * Falls back to the type of heading used if `as` is not provided\n     */\n    size: Size;\n}\n\nconst Heading: React.FC<HeadingProps> = ({ as, size = \"1\", className, children, ...rest }) =>\n    React.createElement(as || `h${size}`, {\n        ...rest,\n        className: classNames(`mx_Heading_h${size}`, className),\n        children,\n    });\n\nexport default Heading;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 Vector Creations Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ComponentProps } from \"react\";\nimport { type Device } from \"matrix-js-sdk/src/matrix\";\nimport { type GeneratedSas } from \"matrix-js-sdk/src/crypto-api\";\nimport { SasEmoji } from \"@element-hq/web-shared-components\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { PendingActionSpinner } from \"../right_panel/EncryptionInfo\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\n\ninterface IProps {\n    pending?: boolean;\n    displayName?: string; // required if pending is true\n\n    /** Details of the other device involved in the verification, if known */\n    otherDeviceDetails?: Device;\n\n    onDone: () => void;\n    onCancel: () => void;\n    sas: GeneratedSas;\n    isSelf?: boolean;\n    inDialog?: boolean; // whether this component is being shown in a dialog and to use DialogButtons\n}\n\ninterface IState {\n    pending: boolean;\n    cancelling?: boolean;\n}\n\nexport default class VerificationShowSas extends React.Component<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            pending: false,\n        };\n    }\n\n    private onMatchClick = (): void => {\n        this.setState({ pending: true });\n        this.props.onDone();\n    };\n\n    private onDontMatchClick = (): void => {\n        this.setState({ cancelling: true });\n        this.props.onCancel();\n    };\n\n    public render(): React.ReactNode {\n        let sasDisplay;\n        let sasCaption;\n        if (this.props.sas.emoji) {\n            sasDisplay = (\n                <SasEmoji\n                    className=\"mx_VerificationShowSas_emojiSas\"\n                    emoji={this.props.sas.emoji.map((e) => e[0]) as ComponentProps<typeof SasEmoji>[\"emoji\"]}\n                />\n            );\n            sasCaption = this.props.isSelf\n                ? _t(\"encryption|verification|confirm_the_emojis\")\n                : _t(\"encryption|verification|sas_emoji_caption_user\");\n        } else if (this.props.sas.decimal) {\n            const numberBlocks = this.props.sas.decimal.map((num, i) => <span key={i}>{num}</span>);\n            sasDisplay = <div className=\"mx_VerificationShowSas_decimalSas\">{numberBlocks}</div>;\n            sasCaption = this.props.isSelf\n                ? _t(\"encryption|verification|sas_caption_self\")\n                : _t(\"encryption|verification|sas_caption_user\");\n        } else {\n            return (\n                <div>\n                    {_t(\"encryption|verification|unsupported_method\")}\n                    <AccessibleButton kind=\"primary\" onClick={this.props.onCancel}>\n                        {_t(\"action|cancel\")}\n                    </AccessibleButton>\n                </div>\n            );\n        }\n\n        let confirm;\n        if (this.state.pending && this.props.isSelf) {\n            let text;\n            // device shouldn't be null in this situation but it can be, eg. if the device is\n            // logged out during verification\n            const otherDevice = this.props.otherDeviceDetails;\n            if (otherDevice) {\n                text = _t(\"encryption|verification|waiting_other_device_details\", {\n                    deviceName: otherDevice.displayName,\n                    deviceId: otherDevice.deviceId,\n                });\n            } else {\n                text = _t(\"encryption|verification|waiting_other_device\");\n            }\n            confirm = <p>{text}</p>;\n        } else if (this.state.pending || this.state.cancelling) {\n            let text;\n            if (this.state.pending) {\n                const { displayName } = this.props;\n                text = _t(\"encryption|verification|waiting_other_user\", { displayName });\n            } else {\n                text = _t(\"encryption|verification|cancelling\");\n            }\n            confirm = <PendingActionSpinner text={text} />;\n        } else {\n            confirm = (\n                <div className=\"mx_VerificationShowSas_buttonRow\">\n                    <AccessibleButton onClick={this.onMatchClick} kind=\"primary\">\n                        {_t(\"encryption|verification|sas_match\")}\n                    </AccessibleButton>\n                    <AccessibleButton onClick={this.onDontMatchClick} kind=\"secondary\">\n                        {_t(\"encryption|verification|sas_no_match\")}\n                    </AccessibleButton>\n                </div>\n            );\n        }\n\n        return (\n            <div className=\"mx_VerificationShowSas\">\n                <p>{sasCaption}</p>\n                {sasDisplay}\n                <p>{this.props.isSelf ? \"\" : _t(\"encryption|verification|in_person\")}</p>\n                {confirm}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { VoiceCallSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport AccessibleButton, { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport { _t } from \"../../../languageHandler\";\nimport { type XOR } from \"../../../@types/common\";\n\nexport const BUTTONS = [\"1\", \"2\", \"3\", \"4\", \"5\", \"6\", \"7\", \"8\", \"9\", \"*\", \"0\", \"#\"];\nexport const BUTTON_LETTERS = [\"\", \"ABC\", \"DEF\", \"GHI\", \"JKL\", \"MNO\", \"PQRS\", \"TUV\", \"WXYZ\", \"\", \"+\", \"\"];\n\nenum DialPadButtonKind {\n    Digit,\n    Dial,\n}\n\ntype DigitButtonProps = {\n    kind: DialPadButtonKind.Digit;\n    digit: string;\n    digitSubtext: string;\n    onButtonPress: (digit: string, ev: ButtonEvent) => void;\n};\n\ntype DialButtonProps = {\n    kind: DialPadButtonKind.Dial;\n    onButtonPress: () => void;\n};\n\nclass DialPadButton extends React.PureComponent<DigitButtonProps | DialButtonProps> {\n    public onClick = (ev: ButtonEvent): void => {\n        switch (this.props.kind) {\n            case DialPadButtonKind.Digit:\n                this.props.onButtonPress(this.props.digit, ev);\n                break;\n            case DialPadButtonKind.Dial:\n                this.props.onButtonPress();\n                break;\n        }\n    };\n\n    public render(): React.ReactNode {\n        switch (this.props.kind) {\n            case DialPadButtonKind.Digit:\n                return (\n                    <AccessibleButton className=\"mx_DialPad_button\" onClick={this.onClick}>\n                        {this.props.digit}\n                        <div className=\"mx_DialPad_buttonSubText\">{this.props.digitSubtext}</div>\n                    </AccessibleButton>\n                );\n            case DialPadButtonKind.Dial:\n                return (\n                    <AccessibleButton\n                        className=\"mx_DialPad_button mx_DialPad_dialButton\"\n                        onClick={this.onClick}\n                        aria-label={_t(\"voip|dial\")}\n                    >\n                        <VoiceCallSolidIcon />\n                    </AccessibleButton>\n                );\n        }\n    }\n}\n\ninterface IBaseProps {\n    onDigitPress: (digit: string, ev: ButtonEvent) => void;\n    onDeletePress?: (ev: ButtonEvent) => void;\n    hasDial: boolean;\n}\n\ninterface IProps extends IBaseProps {\n    hasDial: false;\n}\n\ninterface IDialProps extends IBaseProps {\n    hasDial: true;\n    onDialPress: () => void;\n}\n\nexport default class DialPad extends React.PureComponent<XOR<IProps, IDialProps>> {\n    public render(): React.ReactNode {\n        const buttonNodes: JSX.Element[] = [];\n\n        for (let i = 0; i < BUTTONS.length; i++) {\n            const button = BUTTONS[i];\n            const digitSubtext = BUTTON_LETTERS[i];\n            buttonNodes.push(\n                <DialPadButton\n                    key={button}\n                    kind={DialPadButtonKind.Digit}\n                    digit={button}\n                    digitSubtext={digitSubtext}\n                    onButtonPress={this.props.onDigitPress}\n                />,\n            );\n        }\n\n        if (this.props.hasDial) {\n            buttonNodes.push(\n                <DialPadButton key=\"dial\" kind={DialPadButtonKind.Dial} onButtonPress={this.props.onDialPress} />,\n            );\n        }\n\n        return <div className=\"mx_DialPad\">{buttonNodes}</div>;\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createContext } from \"react\";\n\nimport { useCurrentPhase } from \"../hooks/right-panel/useCurrentPhase\";\nimport { type RightPanelPhases } from \"../stores/right-panel/RightPanelStorePhases\";\n\ntype Context = {\n    isPanelOpen: boolean;\n    currentPhase: RightPanelPhases | null;\n};\n\nexport const CurrentRightPanelPhaseContext = createContext<Context | null>(null);\n\ntype Props = {\n    roomId: string;\n};\n\nexport const CurrentRightPanelPhaseContextProvider: React.FC<React.PropsWithChildren<Props>> = ({\n    roomId,\n    children,\n}) => {\n    const { currentPhase, isOpen } = useCurrentPhase(roomId);\n    return (\n        <CurrentRightPanelPhaseContext.Provider value={{ currentPhase, isPanelOpen: isOpen }}>\n            {children}\n        </CurrentRightPanelPhaseContext.Provider>\n    );\n};\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useContext, useState } from \"react\";\n\nimport { SDKContext } from \"../../contexts/SDKContext\";\nimport { type RightPanelPhases } from \"../../stores/right-panel/RightPanelStorePhases\";\nimport { useEventEmitter } from \"../useEventEmitter\";\nimport { UPDATE_EVENT } from \"../../stores/AsyncStore\";\n\n/**\n * Returns:\n * - state which will always reflect the currently active right panel phase or null.\n * - boolean state representing whether any panel is open or not.\n * @param roomId room id if available.\n */\nexport function useCurrentPhase(roomId?: string): { currentPhase: RightPanelPhases | null; isOpen: boolean } {\n    const sdkContext = useContext(SDKContext);\n\n    const getCurrentPhase = (): RightPanelPhases | null => {\n        const card = roomId\n            ? sdkContext.rightPanelStore.currentCardForRoom(roomId)\n            : sdkContext.rightPanelStore.currentCard;\n        return card.phase;\n    };\n\n    const getIsOpen = (): boolean => {\n        const isOpen = roomId ? sdkContext.rightPanelStore.isOpenForRoom(roomId) : sdkContext.rightPanelStore.isOpen;\n        return isOpen;\n    };\n\n    const [currentPhase, setCurrentPhase] = useState<RightPanelPhases | null>(getCurrentPhase());\n    const [isOpen, setIsOpen] = useState<boolean>(getIsOpen());\n\n    useEventEmitter(sdkContext.rightPanelStore, UPDATE_EVENT, () => {\n        setCurrentPhase(getCurrentPhase());\n        setIsOpen(getIsOpen());\n    });\n\n    return { currentPhase, isOpen };\n}\n","/*\n * Copyright 2026 Element Creations Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { createContext } from \"react\";\n\n/**\n * React context whose value is whether the local device has been verified.\n *\n * (Specifically, this is true if we have done enough verification to confirm that the published public cross-signing\n * keys are genuine -- which normally means that we or another device will have published a signature of this device.)\n */\nexport const LocalDeviceVerificationStateContext = createContext(false);\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ComponentClass, createContext, useContext } from \"react\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\n// This context is available to components under LoggedInView,\n// the context must not be used by components outside a MatrixClientContext tree.\n// This assertion allows us to make the type not nullable.\nconst MatrixClientContext = createContext<MatrixClient>(null as any);\nMatrixClientContext.displayName = \"MatrixClientContext\";\nexport default MatrixClientContext;\n\nexport interface MatrixClientProps {\n    mxClient: MatrixClient;\n}\n\nexport function useMatrixClientContext(): MatrixClient {\n    return useContext(MatrixClientContext);\n}\n\nconst matrixHOC =\n    <ComposedComponentProps extends object>(\n        ComposedComponent: ComponentClass<ComposedComponentProps>,\n    ): ((\n        props: Omit<ComposedComponentProps, \"mxClient\"> & React.RefAttributes<InstanceType<typeof ComposedComponent>>,\n    ) => React.ReactElement | null) =>\n    (props) => {\n        const client = useContext(MatrixClientContext);\n\n        // @ts-ignore\n        return <ComposedComponent {...props} mxClient={client} />;\n    };\nexport const withMatrixClientHOC = matrixHOC;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { createContext } from \"react\";\n\nimport { type IRoomState } from \"../components/structures/RoomView\";\nimport { Layout } from \"../settings/enums/Layout\";\nimport { type RoomViewStore } from \"../stores/RoomViewStore\";\n\nexport enum TimelineRenderingType {\n    Room = \"Room\",\n    Thread = \"Thread\",\n    ThreadsList = \"ThreadsList\",\n    File = \"File\",\n    Notification = \"Notification\",\n    Search = \"Search\",\n    Pinned = \"Pinned\",\n}\n\n// This defines the content of the mainSplit.\n// If the mainSplit does not contain the Timeline, the chat is shown in the right panel.\nexport enum MainSplitContentType {\n    Timeline,\n    MaximisedWidget,\n    Call,\n}\n\nexport interface RoomContextType extends IRoomState {\n    threadId?: string;\n    roomViewStore: RoomViewStore;\n}\n\nconst RoomContext = createContext<RoomContextType>({\n    roomLoading: true,\n    peekLoading: false,\n    shouldPeek: true,\n    membersLoaded: false,\n    numUnreadMessages: 0,\n    canPeek: false,\n    showApps: false,\n    isPeeking: false,\n    showRightPanel: true,\n    joining: false,\n    showTopUnreadMessagesBar: false,\n    statusBarVisible: false,\n    canReact: false,\n    canSelfRedact: false,\n    canSendMessages: false,\n    resizing: false,\n    layout: Layout.Group,\n    lowBandwidth: false,\n    alwaysShowTimestamps: false,\n    showTwelveHourTimestamps: false,\n    userTimezone: undefined,\n    readMarkerInViewThresholdMs: 3000,\n    readMarkerOutOfViewThresholdMs: 30000,\n    showHiddenEvents: false,\n    showReadReceipts: true,\n    showRedactions: true,\n    showJoinLeaves: true,\n    showAvatarChanges: true,\n    showDisplaynameChanges: true,\n    matrixClientIsReady: false,\n    showUrlPreview: false,\n    timelineRenderingType: TimelineRenderingType.Room,\n    mainSplitContentType: MainSplitContentType.Timeline,\n    threadId: undefined,\n    liveTimeline: undefined,\n    narrow: false,\n    msc3946ProcessDynamicPredecessor: false,\n    canAskToJoin: false,\n    promptAskToJoin: false,\n    viewRoomOpts: { buttons: [] },\n    isRoomEncrypted: null,\n    // roomViewStore should always be present as it is passed to RoomView constructor.\n    // In time when we migrate the RoomView to MVVM it will cease to exist(become a ViewModel).\n    roomViewStore: undefined!,\n});\nRoomContext.displayName = \"RoomContext\";\nexport default RoomContext;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room, type RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { type SdkContextClass } from \"../contexts/SDKContext\";\nimport SdkConfig from \"../SdkConfig\";\n\n// Regex applied to filter our punctuation in member names before applying sort, to fuzzy it a little\n// matches all ASCII punctuation: !\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~\nconst SORT_REGEX = /[\\x21-\\x2F\\x3A-\\x40\\x5B-\\x60\\x7B-\\x7E]+/g;\n\n/**\n * A class for storing application state for MemberList.\n */\nexport class MemberListStore {\n    // cache of Display Name -> name to sort based on. This strips out special symbols like @.\n    private readonly sortNames = new Map<string, string>();\n    // list of room IDs that have been lazy loaded\n    private readonly loadedRooms = new Set<string>();\n\n    private collator?: Intl.Collator;\n\n    public constructor(private readonly stores: SdkContextClass) {}\n\n    /**\n     * Load the member list. Call this whenever the list may have changed.\n     * @param roomId The room to load the member list in\n     * @param searchQuery Optional search query to filter the list.\n     * @returns A list of filtered and sorted room members, grouped by membership.\n     */\n    public async loadMemberList(\n        roomId: string,\n        searchQuery?: string,\n    ): Promise<Record<\"joined\" | \"invited\", RoomMember[]>> {\n        if (!this.stores.client) {\n            return {\n                joined: [],\n                invited: [],\n            };\n        }\n        const language = SettingsStore.getValue(\"language\");\n        this.collator = new Intl.Collator(language, { sensitivity: \"base\", ignorePunctuation: false });\n        const members = await this.loadMembers(roomId);\n        // Filter then sort as it's more efficient than sorting tons of members we will just filter out later.\n        // Also sort each group, as there's no point comparing invited/joined users when they aren't in the same list!\n        const membersByMembership = this.filterMembers(members, searchQuery);\n        membersByMembership.joined.sort((a: RoomMember, b: RoomMember) => {\n            return this.sortMembers(a, b);\n        });\n        membersByMembership.invited.sort((a: RoomMember, b: RoomMember) => {\n            return this.sortMembers(a, b);\n        });\n        return {\n            joined: membersByMembership.joined,\n            invited: membersByMembership.invited,\n        };\n    }\n\n    private async loadMembers(roomId: string): Promise<Array<RoomMember>> {\n        const room = this.stores.client!.getRoom(roomId);\n        if (!room) {\n            return [];\n        }\n\n        if (this.loadedRooms.has(roomId) || !(await this.isLazyLoadingEnabled(roomId))) {\n            // nice and easy, we must already have all the members so just return them.\n            return this.loadMembersInRoom(room);\n        }\n        // lazy loading is enabled. There are two kinds of lazy loading:\n        // - With storage: most members are in indexedDB, we just need a small delta via /members.\n        //   Valid for normal sync in normal windows.\n        // - Without storage: nothing in indexedDB, we need to load all via /members. Valid for\n        //   Sliding Sync and incognito windows (non-Sliding Sync).\n        if (!this.isLazyMemberStorageEnabled()) {\n            // pull straight from the server. Don't use a since token as we don't have earlier deltas\n            // accumulated.\n            room.currentState.markOutOfBandMembersStarted();\n            const response = await this.stores.client!.members(roomId, undefined, KnownMembership.Leave);\n            const memberEvents = response.chunk.map(this.stores.client!.getEventMapper());\n            room.currentState.setOutOfBandMembers(memberEvents);\n        } else {\n            // load using traditional lazy loading\n            try {\n                await room.loadMembersIfNeeded();\n            } catch {\n                /* already logged in RoomView */\n            }\n        }\n        // remember that we have loaded the members so we don't hit /members all the time. We\n        // will forget this on refresh which is fine as we only store the data in-memory.\n        this.loadedRooms.add(roomId);\n        return this.loadMembersInRoom(room);\n    }\n\n    private loadMembersInRoom(room: Room): Array<RoomMember> {\n        const allMembers = Object.values(room.currentState.members);\n        allMembers.forEach((member) => {\n            // work around a race where you might have a room member object\n            // before the user object exists. This may or may not cause\n            // https://github.com/vector-im/vector-web/issues/186\n            if (!member.user) {\n                member.user = this.stores.client!.getUser(member.userId) || undefined;\n            }\n            // XXX: this user may have no lastPresenceTs value!\n            // the right solution here is to fix the race rather than leave it as 0\n        });\n        return allMembers;\n    }\n\n    /**\n     * Check if this room should be lazy loaded. Lazy loading means fetching the member list in\n     * a delayed or incremental fashion. It means the `Room` object doesn't have all the members.\n     * @param roomId The room to check if lazy loading is enabled\n     * @returns True if enabled\n     */\n    private async isLazyLoadingEnabled(roomId: string): Promise<boolean> {\n        if (SettingsStore.getValue(\"feature_simplified_sliding_sync\")) {\n            // only unencrypted rooms use lazy loading\n            return !(await this.stores.client?.getCrypto()?.isEncryptionEnabledInRoom(roomId));\n        }\n        return this.stores.client!.hasLazyLoadMembersEnabled();\n    }\n\n    /**\n     * Check if lazy member storage is supported.\n     * @returns True if there is storage for lazy loading members\n     */\n    private isLazyMemberStorageEnabled(): boolean {\n        if (SettingsStore.getValue(\"feature_simplified_sliding_sync\")) {\n            return false;\n        }\n        return this.stores.client!.hasLazyLoadMembersEnabled();\n    }\n\n    public isPresenceEnabled(): boolean {\n        if (!this.stores.client) {\n            return true;\n        }\n        const enablePresenceByHsUrl = SdkConfig.get(\"enable_presence_by_hs_url\");\n        return enablePresenceByHsUrl?.[this.stores.client!.baseUrl] ?? true;\n    }\n\n    /**\n     * Filter out members based on an optional search query. Groups by membership state.\n     * @param members The list of members to filter.\n     * @param query The textual query to filter based on.\n     * @returns An object with a list of joined and invited users respectively.\n     */\n    private filterMembers(members: Array<RoomMember>, query?: string): Record<\"joined\" | \"invited\", RoomMember[]> {\n        const result: Record<\"joined\" | \"invited\", RoomMember[]> = {\n            joined: [],\n            invited: [],\n        };\n        members.forEach((m) => {\n            if (m.membership !== KnownMembership.Join && m.membership !== KnownMembership.Invite) {\n                return; // bail early for left/banned users\n            }\n            if (query) {\n                query = query.toLowerCase();\n                const matchesName = m.name.toLowerCase().includes(query);\n                const matchesId = m.userId.toLowerCase().includes(query);\n                if (!matchesName && !matchesId) {\n                    return;\n                }\n            }\n            switch (m.membership) {\n                case KnownMembership.Join:\n                    result.joined.push(m);\n                    break;\n                case KnownMembership.Invite:\n                    result.invited.push(m);\n                    break;\n            }\n        });\n        return result;\n    }\n\n    /**\n     * Sort algorithm for room members.\n     * @param memberA\n     * @param memberB\n     * @returns Negative if A comes before B, 0 if A and B are equivalent, Positive is A comes after B.\n     */\n    private sortMembers(memberA: RoomMember, memberB: RoomMember): number {\n        // order by presence, with \"active now\" first.\n        // ...and then by power level\n        // ...and then by last active\n        // ...and then alphabetically.\n        // We could tiebreak instead by \"last recently spoken in this room\" if we wanted to.\n\n        const userA = memberA.user;\n        const userB = memberB.user;\n\n        if (!userA && !userB) return 0;\n        if (userA && !userB) return -1;\n        if (!userA && userB) return 1;\n\n        const showPresence = this.isPresenceEnabled();\n\n        // First by presence\n        if (showPresence) {\n            const convertPresence = (p: string): string => (p === \"unavailable\" ? \"online\" : p);\n            const presenceIndex = (p: string): number => {\n                const order = [\"active\", \"online\", \"offline\"];\n                const idx = order.indexOf(convertPresence(p));\n                return idx === -1 ? order.length : idx; // unknown states at the end\n            };\n\n            const idxA = presenceIndex(userA!.currentlyActive ? \"active\" : userA!.presence);\n            const idxB = presenceIndex(userB!.currentlyActive ? \"active\" : userB!.presence);\n            if (idxA !== idxB) {\n                return idxA - idxB;\n            }\n        }\n\n        // Second by power level\n        if (memberA.powerLevel !== memberB.powerLevel) {\n            return memberB.powerLevel - memberA.powerLevel;\n        }\n\n        // Third by last active\n        if (showPresence && userA!.getLastActiveTs() !== userB!.getLastActiveTs()) {\n            return userB!.getLastActiveTs() - userA!.getLastActiveTs();\n        }\n\n        // Fourth by name (alphabetical)\n        return this.collator!.compare(this.canonicalisedName(memberA.name), this.canonicalisedName(memberB.name));\n    }\n\n    /**\n     * Calculate the canonicalised name for the input name.\n     * @param name The member display name\n     * @returns The name to sort on\n     */\n    private canonicalisedName(name: string): string {\n        let result = this.sortNames.get(name);\n        if (result) {\n            return result;\n        }\n        result = (name[0] === \"@\" ? name.slice(1) : name).replace(SORT_REGEX, \"\");\n        this.sortNames.set(name, result);\n        return result;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2022 The Matrix.org Foundation C.I.C.\nCopyright 2017, 2018 New Vector Ltd\nCopyright 2017 Vector Creations Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode } from \"react\";\nimport * as utils from \"matrix-js-sdk/src/utils\";\nimport { MatrixError, JoinRule, type Room, type MatrixEvent, type IJoinRoomOpts } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type ViewRoom as ViewRoomEvent } from \"@matrix-org/analytics-events/types/typescript/ViewRoom\";\nimport { type JoinedRoom as JoinedRoomEvent } from \"@matrix-org/analytics-events/types/typescript/JoinedRoom\";\nimport EventEmitter from \"events\";\nimport {\n    RoomViewLifecycle,\n    type ViewRoomOpts,\n} from \"@matrix-org/react-sdk-module-api/lib/lifecycles/RoomViewLifecycle\";\n\nimport { type MatrixDispatcher } from \"../dispatcher/dispatcher\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport Modal from \"../Modal\";\nimport { _t } from \"../languageHandler\";\nimport { getCachedRoomIdForAlias, storeRoomAliasInCache } from \"../RoomAliasCache\";\nimport { Action } from \"../dispatcher/actions\";\nimport { retry } from \"../utils/promise\";\nimport { TimelineRenderingType } from \"../contexts/RoomContext\";\nimport { type ViewRoomPayload } from \"../dispatcher/payloads/ViewRoomPayload\";\nimport DMRoomMap from \"../utils/DMRoomMap\";\nimport { isMetaSpace, MetaSpace } from \"./spaces\";\nimport { type JoinRoomPayload } from \"../dispatcher/payloads/JoinRoomPayload\";\nimport { type JoinRoomReadyPayload } from \"../dispatcher/payloads/JoinRoomReadyPayload\";\nimport { type JoinRoomErrorPayload } from \"../dispatcher/payloads/JoinRoomErrorPayload\";\nimport { type ViewRoomErrorPayload } from \"../dispatcher/payloads/ViewRoomErrorPayload\";\nimport ErrorDialog from \"../components/views/dialogs/ErrorDialog\";\nimport { type ActiveRoomChangedPayload } from \"../dispatcher/payloads/ActiveRoomChangedPayload\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { awaitRoomDownSync } from \"../utils/RoomUpgrade\";\nimport { UPDATE_EVENT } from \"./AsyncStore\";\nimport { type SdkContextClass } from \"../contexts/SDKContext\";\nimport { CallStore } from \"./CallStore\";\nimport { type ThreadPayload } from \"../dispatcher/payloads/ThreadPayload\";\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport { type CancelAskToJoinPayload } from \"../dispatcher/payloads/CancelAskToJoinPayload\";\nimport { type SubmitAskToJoinPayload } from \"../dispatcher/payloads/SubmitAskToJoinPayload\";\nimport { ModuleRunner } from \"../modules/ModuleRunner\";\nimport { setMarkedUnreadState } from \"../utils/notifications\";\nimport { ConnectionState, ElementCall } from \"../models/Call\";\nimport { isVideoRoom } from \"../utils/video-rooms\";\nimport { ModuleApi } from \"../modules/Api\";\n\nconst NUM_JOIN_RETRY = 5;\n\ninterface State {\n    /**\n     * Whether we're joining the currently viewed (see isJoining())\n     */\n    joining: boolean;\n    /**\n     * Any error that has occurred during joining\n     */\n    joinError: Error | null;\n    /**\n     * The ID of the room currently being viewed\n     */\n    roomId: string | null;\n    /**\n     * The ID of the thread currently being viewed\n     */\n    threadId: string | null;\n    /**\n     * The ID of the room being subscribed to (in Sliding Sync)\n     */\n    subscribingRoomId: string | null;\n    /**\n     * The event to scroll to when the room is first viewed\n     */\n    initialEventId: string | null;\n    initialEventPixelOffset: number | null;\n    /**\n     * Whether to highlight the initial event\n     */\n    isInitialEventHighlighted: boolean;\n    /**\n     * Whether to scroll the initial event into view\n     */\n    initialEventScrollIntoView: boolean;\n    /**\n     * The alias of the room (or null if not originally specified in view_room)\n     */\n    roomAlias: string | null;\n    /**\n     * Whether the current room is loading\n     */\n    roomLoading: boolean;\n    /**\n     * Any error that has occurred during loading\n     */\n    roomLoadError: MatrixError | null;\n    replyingToEvent: MatrixEvent | null;\n    shouldPeek: boolean;\n    viaServers: string[];\n    wasContextSwitch: boolean;\n    /**\n     * Whether we're viewing a call or call lobby in this room\n     */\n    viewingCall: boolean;\n\n    promptAskToJoin: boolean;\n\n    viewRoomOpts: ViewRoomOpts;\n}\n\nconst INITIAL_STATE: State = {\n    joining: false,\n    joinError: null,\n    roomId: null,\n    threadId: null,\n    subscribingRoomId: null,\n    initialEventId: null,\n    initialEventPixelOffset: null,\n    isInitialEventHighlighted: false,\n    initialEventScrollIntoView: true,\n    roomAlias: null,\n    roomLoading: false,\n    roomLoadError: null,\n    replyingToEvent: null,\n    shouldPeek: false,\n    viaServers: [],\n    wasContextSwitch: false,\n    viewingCall: false,\n    promptAskToJoin: false,\n    viewRoomOpts: { buttons: [] },\n};\n\ntype Listener = (isActive: boolean) => void;\n\n/**\n * A class for storing application state for RoomView.\n */\nexport class RoomViewStore extends EventEmitter {\n    // initialize state as a copy of the initial state. We need to copy else one RVS can talk to\n    // another RVS via INITIAL_STATE as they share the same underlying object. Mostly relevant for tests.\n    private state = utils.deepCopy(INITIAL_STATE);\n\n    private dis?: MatrixDispatcher;\n    private dispatchToken?: string;\n\n    public constructor(\n        dis: MatrixDispatcher,\n        private readonly stores: SdkContextClass,\n        private readonly lockedToRoomId?: string,\n    ) {\n        super();\n        this.resetDispatcher(dis);\n    }\n\n    public addRoomListener(roomId: string, fn: Listener): void {\n        this.on(roomId, fn);\n    }\n\n    public removeRoomListener(roomId: string, fn: Listener): void {\n        this.off(roomId, fn);\n    }\n\n    private emitForRoom(roomId: string, isActive: boolean): void {\n        this.emit(roomId, isActive);\n    }\n\n    private setState(newState: Partial<State>): void {\n        // If values haven't changed, there's nothing to do.\n        // This only tries a shallow comparison, so unchanged objects will slip\n        // through, but that's probably okay for now.\n        let stateChanged = false;\n        for (const key of Object.keys(newState)) {\n            if (this.state[key as keyof State] !== newState[key as keyof State]) {\n                stateChanged = true;\n                break;\n            }\n        }\n        if (!stateChanged) {\n            return;\n        }\n\n        const lastRoomId = this.state.roomId;\n        this.state = Object.assign(this.state, newState);\n        if (!this.lockedToRoomId && lastRoomId !== this.state.roomId) {\n            if (lastRoomId) this.emitForRoom(lastRoomId, false);\n            if (this.state.roomId) this.emitForRoom(this.state.roomId, true);\n\n            // Fired so we can reduce dependency on event emitters to this store, which is relatively\n            // central to the application and can easily cause import cycles.\n            this.dis?.dispatch<ActiveRoomChangedPayload>({\n                action: Action.ActiveRoomChanged,\n                oldRoomId: lastRoomId,\n                newRoomId: this.state.roomId,\n            });\n        }\n\n        this.emit(UPDATE_EVENT);\n    }\n\n    private onDispatch(payload: ActionPayload): void {\n        if (this.lockedToRoomId && payload.room_id && this.lockedToRoomId !== payload.room_id) {\n            return;\n        }\n        // eslint-disable-line @typescript-eslint/naming-convention\n        switch (payload.action) {\n            // view_room:\n            //      - room_alias:   '#somealias:matrix.org'\n            //      - room_id:      '!roomid123:matrix.org'\n            //      - event_id:     '$213456782:matrix.org'\n            //      - event_offset: 100\n            //      - highlighted:  true\n            case Action.ViewRoom:\n                this.viewRoom(payload as ViewRoomPayload);\n                break;\n            case Action.ViewThread:\n                this.viewThread(payload as ThreadPayload);\n                break;\n            // for these events blank out the roomId as we are no longer in the RoomView\n            case \"view_welcome_page\":\n            case Action.ViewHomePage:\n                this.setState({\n                    roomId: null,\n                    roomAlias: null,\n                    viaServers: [],\n                    wasContextSwitch: false,\n                    viewingCall: false,\n                });\n                break;\n            case Action.ViewRoomError:\n                this.viewRoomError(payload as ViewRoomErrorPayload);\n                break;\n            case \"will_join\":\n                this.setState({\n                    joining: true,\n                });\n                break;\n            case \"cancel_join\":\n                this.setState({\n                    joining: false,\n                });\n                break;\n            // join_room:\n            //      - opts: options for joinRoom\n            case Action.JoinRoom:\n                this.joinRoom(payload as JoinRoomPayload);\n                break;\n            case Action.JoinRoomError:\n                this.joinRoomError(payload as JoinRoomErrorPayload);\n                break;\n            case Action.JoinRoomReady: {\n                if (this.state.roomId === payload.roomId) {\n                    this.setState({ shouldPeek: false });\n                }\n\n                awaitRoomDownSync(MatrixClientPeg.safeGet(), payload.roomId).then((room) => {\n                    const numMembers = room.getJoinedMemberCount();\n                    const roomSize =\n                        numMembers > 1000\n                            ? \"MoreThanAThousand\"\n                            : numMembers > 100\n                              ? \"OneHundredAndOneToAThousand\"\n                              : numMembers > 10\n                                ? \"ElevenToOneHundred\"\n                                : numMembers > 2\n                                  ? \"ThreeToTen\"\n                                  : numMembers > 1\n                                    ? \"Two\"\n                                    : \"One\";\n\n                    this.stores.posthogAnalytics.trackEvent<JoinedRoomEvent>({\n                        eventName: \"JoinedRoom\",\n                        trigger: payload.metricsTrigger,\n                        roomSize,\n                        isDM: !!DMRoomMap.shared().getUserIdForRoomId(room.roomId),\n                        isSpace: room.isSpaceRoom(),\n                    });\n                });\n\n                break;\n            }\n            case Action.ClientNotViable:\n            case Action.OnLoggedOut:\n                this.reset();\n                break;\n            case \"reply_to_event\":\n                // Thread timeline view handles its own reply-to-state\n                if (TimelineRenderingType.Thread !== payload.context) {\n                    const roomId: string | undefined = payload.event?.getRoomId();\n\n                    // If currently viewed room does not match the room in which we wish to reply then change rooms this\n                    // can happen when performing a search across all rooms. Persist the data from this event for both\n                    // room and search timeline rendering types, search will get auto-closed by RoomView at this time.\n                    if (payload.event && roomId !== this.state.roomId) {\n                        // if the room is displayed in a module, we don't want to change the room view\n                        if (roomId && this.isRoomDisplayedInModule(roomId)) return;\n\n                        this.dis?.dispatch<ViewRoomPayload>({\n                            action: Action.ViewRoom,\n                            room_id: payload.event.getRoomId(),\n                            replyingToEvent: payload.event,\n                            metricsTrigger: undefined, // room doesn't change\n                        });\n                    } else {\n                        this.setState({\n                            replyingToEvent: payload.event,\n                        });\n                    }\n                }\n                break;\n            case Action.PromptAskToJoin: {\n                this.setState({ promptAskToJoin: true });\n                break;\n            }\n            case Action.SubmitAskToJoin: {\n                this.submitAskToJoin(payload as SubmitAskToJoinPayload);\n                break;\n            }\n            case Action.CancelAskToJoin: {\n                this.cancelAskToJoin(payload as CancelAskToJoinPayload);\n                break;\n            }\n            case Action.RoomLoaded: {\n                this.setViewRoomOpts();\n                break;\n            }\n        }\n    }\n\n    public async viewRoom(payload: ViewRoomPayload): Promise<void> {\n        if (payload.room_id) {\n            const room = MatrixClientPeg.safeGet().getRoom(payload.room_id);\n\n            if (payload.metricsTrigger !== null && payload.room_id !== this.state.roomId) {\n                let activeSpace: ViewRoomEvent[\"activeSpace\"];\n                if (this.stores.spaceStore.activeSpace === MetaSpace.Home) {\n                    activeSpace = \"Home\";\n                } else if (isMetaSpace(this.stores.spaceStore.activeSpace)) {\n                    activeSpace = \"Meta\";\n                } else {\n                    activeSpace =\n                        this.stores.spaceStore.activeSpaceRoom?.getJoinRule() === JoinRule.Public\n                            ? \"Public\"\n                            : \"Private\";\n                }\n\n                this.stores.posthogAnalytics.trackEvent<ViewRoomEvent>({\n                    eventName: \"ViewRoom\",\n                    trigger: payload.metricsTrigger,\n                    viaKeyboard: payload.metricsViaKeyboard,\n                    isDM: !!DMRoomMap.shared().getUserIdForRoomId(payload.room_id),\n                    isSpace: room?.isSpaceRoom(),\n                    activeSpace,\n                });\n            }\n\n            let viewingCall = payload.view_call;\n            if (viewingCall === undefined) {\n                // Default behavior: keep the same call state as before if viewing the same room\n                if (payload.room_id === this.state.roomId) viewingCall = this.state.viewingCall;\n                // Always view the call in video rooms\n                else if (room && isVideoRoom(room)) viewingCall = true;\n                // Otherwise, only view if actively connected\n                else viewingCall = CallStore.instance.getActiveCall(payload.room_id) !== null;\n            }\n\n            if (room && viewingCall) {\n                let call = CallStore.instance.getCall(payload.room_id);\n                // Start a call if not already there\n                if (call === null) {\n                    ElementCall.create(room);\n                    call = CallStore.instance.getCall(payload.room_id)!;\n                }\n                call.presented = true;\n                // Immediately start the call. This will connect to all required widget events\n                // and allow the widget to show the lobby.\n                if (call.connectionState === ConnectionState.Disconnected) {\n                    call.start({ skipLobby: payload.skipLobby, voiceOnly: payload.voiceOnly });\n                }\n            }\n            // If we switch to a different room from the call, we are no longer presenting it\n            const prevRoomCall = this.state.roomId ? CallStore.instance.getCall(this.state.roomId) : null;\n            if (prevRoomCall !== null && (!payload.view_call || payload.room_id !== this.state.roomId))\n                prevRoomCall.presented = false;\n\n            if (SettingsStore.getValue(\"feature_simplified_sliding_sync\") && this.state.roomId !== payload.room_id) {\n                this.setState({\n                    subscribingRoomId: payload.room_id,\n                    roomId: payload.room_id,\n                    initialEventId: null,\n                    initialEventPixelOffset: null,\n                    initialEventScrollIntoView: true,\n                    roomAlias: null,\n                    roomLoading: true,\n                    roomLoadError: null,\n                    viaServers: payload.via_servers,\n                    wasContextSwitch: payload.context_switch,\n                    viewingCall: payload.view_call ?? false,\n                });\n                // set this room as the room subscription. We need to await for it as this will fetch\n                // all room state for this room, which is required before we get the state below.\n                await this.stores.slidingSyncManager.setRoomVisible(payload.room_id);\n\n                // Re-fire the payload: we won't re-process it because the prev room ID == payload room ID now\n                this.dis?.dispatch({\n                    ...payload,\n                });\n                return;\n            }\n\n            const newState: Partial<State> = {\n                roomId: payload.room_id,\n                roomAlias: payload.room_alias ?? null,\n                initialEventId: payload.event_id ?? null,\n                isInitialEventHighlighted: payload.highlighted ?? false,\n                initialEventScrollIntoView: payload.scroll_into_view ?? true,\n                roomLoading: false,\n                roomLoadError: null,\n                // should peek by default\n                shouldPeek: payload.should_peek === undefined ? true : payload.should_peek,\n                // have we sent a join request for this room and are waiting for a response?\n                joining: payload.joining || false,\n                // Reset replyingToEvent because we don't want cross-room because bad UX\n                replyingToEvent: null,\n                viaServers: payload.via_servers ?? [],\n                wasContextSwitch: payload.context_switch ?? false,\n                viewingCall,\n            };\n\n            // Allow being given an event to be replied to when switching rooms but sanity check its for this room\n            if (payload.replyingToEvent?.getRoomId() === payload.room_id) {\n                newState.replyingToEvent = payload.replyingToEvent;\n            } else if (this.state.replyingToEvent?.getRoomId() === payload.room_id) {\n                // if the reply-to matches the desired room, e.g visiting a permalink then maintain replyingToEvent\n                // See https://github.com/vector-im/element-web/issues/21462\n                newState.replyingToEvent = this.state.replyingToEvent;\n            }\n\n            this.setState(newState);\n\n            if (payload.auto_join) {\n                const joinPayload: JoinRoomPayload = {\n                    ...payload,\n                    action: Action.JoinRoom,\n                    roomId: payload.room_id,\n                    metricsTrigger: payload.metricsTrigger as JoinRoomPayload[\"metricsTrigger\"],\n                    canAskToJoin: SettingsStore.getValue(\"feature_ask_to_join\"),\n                };\n                // Explicitly pass viaServers in case state doesn't contain the same due to\n                // some race issues.\n                if (payload.via_servers) {\n                    joinPayload.opts = {\n                        viaServers: payload.via_servers,\n                    };\n                }\n                this.dis?.dispatch<JoinRoomPayload>(joinPayload);\n            }\n\n            if (room) {\n                await setMarkedUnreadState(room, MatrixClientPeg.safeGet(), false);\n            }\n        } else if (payload.room_alias) {\n            let roomId: string;\n            let viaServers: string[] | undefined;\n\n            // Try the room alias to room ID navigation cache first to avoid\n            // blocking room navigation on the homeserver.\n            const cachedResult = getCachedRoomIdForAlias(payload.room_alias);\n            if (cachedResult) {\n                roomId = cachedResult.roomId;\n                viaServers = cachedResult.viaServers;\n            } else {\n                // Room alias cache miss, so let's ask the homeserver. Resolve the alias\n                // and then do a second dispatch with the room ID acquired.\n                this.setState({\n                    roomId: null,\n                    initialEventId: null,\n                    initialEventPixelOffset: null,\n                    isInitialEventHighlighted: false,\n                    initialEventScrollIntoView: true,\n                    roomAlias: payload.room_alias,\n                    roomLoading: true,\n                    roomLoadError: null,\n                    viaServers: payload.via_servers,\n                    wasContextSwitch: payload.context_switch,\n                    viewingCall: payload.view_call ?? false,\n                });\n                try {\n                    const result = await MatrixClientPeg.safeGet().getRoomIdForAlias(payload.room_alias);\n                    storeRoomAliasInCache(payload.room_alias, result.room_id, result.servers);\n                    roomId = result.room_id;\n                    viaServers = result.servers;\n                } catch (err) {\n                    logger.error(\"RVS failed to get room id for alias: \", err);\n                    this.dis?.dispatch<ViewRoomErrorPayload>({\n                        action: Action.ViewRoomError,\n                        room_id: null,\n                        room_alias: payload.room_alias,\n                        err: err instanceof MatrixError ? err : undefined,\n                    });\n                    return;\n                }\n            }\n\n            // Re-fire the payload with the newly found room_id\n            this.dis?.dispatch({\n                ...payload,\n                room_id: roomId,\n                via_servers: viaServers,\n            });\n        }\n    }\n\n    private viewThread(payload: ThreadPayload): void {\n        this.setState({\n            threadId: payload.thread_id,\n        });\n    }\n\n    private viewRoomError(payload: ViewRoomErrorPayload): void {\n        this.setState({\n            roomId: payload.room_id,\n            roomAlias: payload.room_alias,\n            roomLoading: false,\n            roomLoadError: payload.err,\n        });\n    }\n\n    private async joinRoom(payload: JoinRoomPayload): Promise<void> {\n        this.setState({\n            joining: true,\n        });\n\n        // take a copy of roomAlias, roomId & viaServers as they may change by the time the join is complete\n        const { roomAlias, roomId = payload.roomId, viaServers = [] } = this.state;\n        // prefer the room alias if we have one as it allows joining over federation even with no viaServers\n        const address = roomAlias || roomId!;\n\n        const joinOpts: IJoinRoomOpts = {\n            viaServers,\n            ...(payload.opts ?? {}),\n        };\n        if (SettingsStore.getValue(\"feature_share_history_on_invite\")) {\n            joinOpts.acceptSharedHistory = true;\n        }\n        try {\n            const cli = MatrixClientPeg.safeGet();\n            await retry<Room, MatrixError>(\n                () => cli.joinRoom(address, joinOpts),\n                NUM_JOIN_RETRY,\n                (err) => {\n                    // if we received a Gateway timeout or Cloudflare timeout then retry\n                    return err.httpStatus === 504 || err.httpStatus === 524;\n                },\n            );\n\n            // We do *not* clear the 'joining' flag because the Room object and/or our 'joined' member event may not\n            // have come down the sync stream yet, and that's the point at which we'd consider the user joined to the\n            // room.\n            this.dis?.dispatch<JoinRoomReadyPayload>({\n                action: Action.JoinRoomReady,\n                roomId: roomId!,\n                metricsTrigger: payload.metricsTrigger,\n            });\n        } catch (err) {\n            this.dis?.dispatch({\n                action: Action.JoinRoomError,\n                roomId,\n                err,\n                canAskToJoin: payload.canAskToJoin,\n            });\n\n            if (payload.canAskToJoin && err instanceof MatrixError && err.httpStatus === 403) {\n                this.dis?.dispatch({ action: Action.PromptAskToJoin });\n            }\n        }\n    }\n\n    private getInvitingUserId(roomId: string): string | undefined {\n        const cli = MatrixClientPeg.safeGet();\n        const room = cli.getRoom(roomId);\n        if (room?.getMyMembership() === KnownMembership.Invite) {\n            const myMember = room.getMember(cli.getSafeUserId());\n            const inviteEvent = myMember ? myMember.events.member : null;\n            return inviteEvent?.getSender();\n        }\n    }\n\n    public showJoinRoomError(err: MatrixError, roomId: string): void {\n        let description: ReactNode = err.message ? err.message : JSON.stringify(err);\n        logger.log(\"Failed to join room:\", description);\n\n        if (err.name === \"ConnectionError\") {\n            description = _t(\"room|error_join_connection\");\n        } else if (err.errcode === \"M_INCOMPATIBLE_ROOM_VERSION\") {\n            description = (\n                <div>\n                    {_t(\"room|error_join_incompatible_version_1\")}\n                    <br />\n                    {_t(\"room|error_join_incompatible_version_2\")}\n                </div>\n            );\n        } else if (err.httpStatus === 404) {\n            const invitingUserId = this.getInvitingUserId(roomId);\n            // provide a better error message for invites\n            if (invitingUserId) {\n                // if the inviting user is on the same HS, there can only be one cause: they left.\n                if (invitingUserId.endsWith(`:${MatrixClientPeg.safeGet().getDomain()}`)) {\n                    description = _t(\"room|error_join_404_invite_same_hs\");\n                } else {\n                    description = _t(\"room|error_join_404_invite\");\n                }\n            }\n\n            // provide a more detailed error than \"No known servers\" when attempting to\n            // join using a room ID and no via servers\n            if (roomId === this.state.roomId && this.state.viaServers.length === 0) {\n                description = (\n                    <div>\n                        {_t(\"room|error_join_404_1\")}\n                        <br />\n                        <br />\n                        {_t(\"room|error_join_404_2\")}\n                    </div>\n                );\n            }\n        }\n\n        Modal.createDialog(ErrorDialog, {\n            title: _t(\"room|error_join_title\"),\n            description,\n        });\n    }\n\n    private joinRoomError(payload: JoinRoomErrorPayload): void {\n        this.setState({\n            joining: false,\n            joinError: payload.err,\n        });\n        if (payload.err && !payload.canAskToJoin) {\n            this.showJoinRoomError(payload.err, payload.roomId);\n        }\n    }\n\n    public reset(): void {\n        this.state = Object.assign({}, INITIAL_STATE);\n    }\n\n    /**\n     * Reset which dispatcher should be used to listen for actions. The old dispatcher will be\n     * unregistered.\n     * @param dis The new dispatcher to use.\n     */\n    public resetDispatcher(dis: MatrixDispatcher): void {\n        if (this.dispatchToken) {\n            this.dis?.unregister(this.dispatchToken);\n        }\n        this.dis = dis;\n        if (dis) {\n            // Some tests mock the dispatcher file resulting in an empty defaultDispatcher\n            // so rather than dying here, just ignore it. When we no longer mock files like this,\n            // we should remove the null check.\n            this.dispatchToken = this.dis.register(this.onDispatch.bind(this));\n        }\n    }\n\n    // The room ID of the room currently being viewed\n    public getRoomId(): string | null {\n        return this.state.roomId;\n    }\n\n    public getThreadId(): string | null {\n        return this.state.threadId;\n    }\n\n    // The event to scroll to when the room is first viewed\n    public getInitialEventId(): string | null {\n        return this.state.initialEventId;\n    }\n\n    // Whether to highlight the initial event\n    public isInitialEventHighlighted(): boolean {\n        return this.state.isInitialEventHighlighted;\n    }\n\n    // Whether to avoid jumping to the initial event\n    public initialEventScrollIntoView(): boolean {\n        return this.state.initialEventScrollIntoView;\n    }\n\n    // The room alias of the room (or null if not originally specified in view_room)\n    public getRoomAlias(): string | null {\n        return this.state.roomAlias;\n    }\n\n    // Whether the current room is loading (true whilst resolving an alias)\n    public isRoomLoading(): boolean {\n        return this.state.roomLoading;\n    }\n\n    // Any error that has occurred during loading\n    public getRoomLoadError(): MatrixError | null {\n        return this.state.roomLoadError;\n    }\n\n    // True if we're expecting the user to be joined to the room currently being\n    // viewed. Note that this is left true after the join request has finished,\n    // since we should still consider a join to be in progress until the room\n    // & member events come down the sync.\n    //\n    // This flag remains true after the room has been successfully joined,\n    // (this store doesn't listen for the appropriate member events)\n    // so you should always observe the joined state from the member event\n    // if a room object is present.\n    // ie. The correct logic is:\n    // if (room) {\n    //     if (myMember.membership == 'joined') {\n    //         // user is joined to the room\n    //     } else {\n    //         // Not joined\n    //     }\n    // } else {\n    //     if (this.stores.roomViewStore.isJoining()) {\n    //         // show spinner\n    //     } else {\n    //         // show join prompt\n    //     }\n    // }\n    public isJoining(): boolean {\n        return this.state.joining;\n    }\n\n    // Any error that has occurred during joining\n    public getJoinError(): Error | null {\n        return this.state.joinError;\n    }\n\n    // The mxEvent if one is currently being replied to/quoted\n    public getQuotingEvent(): MatrixEvent | null {\n        return this.state.replyingToEvent;\n    }\n\n    public shouldPeek(): boolean {\n        return this.state.shouldPeek;\n    }\n\n    public getWasContextSwitch(): boolean {\n        return this.state.wasContextSwitch;\n    }\n\n    public isViewingCall(): boolean {\n        return this.state.viewingCall;\n    }\n\n    /**\n     * Gets the current state of the 'promptForAskToJoin' property.\n     *\n     * @returns {boolean} The value of the 'promptForAskToJoin' property.\n     */\n    public promptAskToJoin(): boolean {\n        return this.state.promptAskToJoin;\n    }\n\n    /**\n     * Submits a request to join a room by sending a knock request.\n     *\n     * @param {SubmitAskToJoinPayload} payload - The payload containing information to submit the request.\n     * @returns {void}\n     */\n    private submitAskToJoin(payload: SubmitAskToJoinPayload): void {\n        MatrixClientPeg.safeGet()\n            .knockRoom(payload.roomId, { viaServers: this.state.viaServers, ...payload.opts })\n            .catch((err: MatrixError) =>\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"room|error_join_title\"),\n                    description: err.httpStatus === 403 ? _t(\"room|error_join_403\") : err.message,\n                }),\n            )\n            .finally(() => this.setState({ promptAskToJoin: false }));\n    }\n\n    /**\n     * Cancels a request to join a room by sending a leave request.\n     *\n     * @param {CancelAskToJoinPayload} payload - The payload containing information to cancel the request.\n     * @returns {void}\n     */\n    private cancelAskToJoin(payload: CancelAskToJoinPayload): void {\n        MatrixClientPeg.safeGet()\n            .leave(payload.roomId)\n            .catch((err: MatrixError) =>\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"room|error_cancel_knock_title\"),\n                    description: err.message,\n                }),\n            );\n    }\n\n    /**\n     * Gets the current state of the 'viewRoomOpts' property.\n     *\n     * @returns {ViewRoomOpts} The value of the 'viewRoomOpts' property.\n     */\n    public getViewRoomOpts(): ViewRoomOpts {\n        return this.state.viewRoomOpts;\n    }\n\n    /**\n     * Invokes the view room lifecycle to set the view room options.\n     *\n     * @returns {void}\n     */\n    private setViewRoomOpts(): void {\n        const viewRoomOpts: ViewRoomOpts = { buttons: [] };\n        ModuleRunner.instance.invoke(RoomViewLifecycle.ViewRoom, viewRoomOpts, this.getRoomId());\n        this.setState({ viewRoomOpts });\n    }\n\n    /**\n     * Checks if a room is already displayed in the current active space module.\n     * @param roomId\n     */\n    public isRoomDisplayedInModule(roomId: string): boolean {\n        const currentSpace = this.stores.spaceStore.activeSpace;\n        const cb = ModuleApi.instance.extras.visibleRoomBySpaceKey.get(currentSpace);\n        if (!cb) return false;\n\n        return cb().includes(roomId);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type SdkContextClass } from \"../contexts/SDKContext\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { isLocalRoom } from \"../utils/localRoom/isLocalRoom\";\nimport Timer from \"../utils/Timer\";\n\nconst TYPING_USER_TIMEOUT = 10000;\nconst TYPING_SERVER_TIMEOUT = 30000;\n\n/**\n * Tracks typing state for users.\n */\nexport default class TypingStore {\n    private typingStates: {\n        [roomId: string]: {\n            isTyping: boolean;\n            userTimer: Timer;\n            serverTimer: Timer;\n        };\n    } = {};\n\n    public constructor(private readonly context: SdkContextClass) {\n        this.reset();\n    }\n\n    /**\n     * Clears all cached typing states. Intended to be called when the\n     * MatrixClientPeg client changes.\n     */\n    public reset(): void {\n        this.typingStates = {\n            // \"roomId\": {\n            //     isTyping: bool,     // Whether the user is typing or not\n            //     userTimer: Timer,   // Local timeout for \"user has stopped typing\"\n            //     serverTimer: Timer, // Maximum timeout for the typing state\n            // },\n        };\n    }\n\n    /**\n     * Changes the typing status for the MatrixClientPeg user.\n     * @param {string} roomId The room ID to set the typing state in.\n     * @param {boolean} isTyping Whether the user is typing or not.\n     */\n    public setSelfTyping(roomId: string, threadId: string | null, isTyping: boolean): void {\n        // No typing notifications for local rooms\n        if (isLocalRoom(roomId)) return;\n\n        if (!SettingsStore.getValue(\"sendTypingNotifications\")) return;\n        if (SettingsStore.getValue(\"lowBandwidth\")) return;\n        // Disable typing notification for threads for the initial launch\n        // before we figure out a better user experience for them\n        if (threadId) return;\n\n        let currentTyping = this.typingStates[roomId];\n        if ((!isTyping && !currentTyping) || currentTyping?.isTyping === isTyping) {\n            // No change in state, so don't do anything. We'll let the timer run its course.\n            return;\n        }\n\n        if (!currentTyping) {\n            currentTyping = this.typingStates[roomId] = {\n                isTyping: isTyping,\n                serverTimer: new Timer(TYPING_SERVER_TIMEOUT),\n                userTimer: new Timer(TYPING_USER_TIMEOUT),\n            };\n        }\n\n        currentTyping.isTyping = isTyping;\n\n        if (isTyping) {\n            if (!currentTyping.serverTimer.isRunning()) {\n                currentTyping.serverTimer\n                    .restart()\n                    .finished()\n                    .then(() => {\n                        const currentTyping = this.typingStates[roomId];\n                        if (currentTyping) currentTyping.isTyping = false;\n\n                        // The server will (should) time us out on typing, so we don't\n                        // need to advertise a stop of typing.\n                    });\n            } else currentTyping.serverTimer.restart();\n\n            if (!currentTyping.userTimer.isRunning()) {\n                currentTyping.userTimer\n                    .restart()\n                    .finished()\n                    .then(() => {\n                        this.setSelfTyping(roomId, threadId, false);\n                    });\n            } else currentTyping.userTimer.restart();\n        }\n\n        this.context.client?.sendTyping(roomId, isTyping, TYPING_SERVER_TIMEOUT);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\ninterface CacheItem<K, V> {\n    key: K;\n    value: V;\n    /** Next item in the list */\n    next: CacheItem<K, V> | null;\n    /** Previous item in the list */\n    prev: CacheItem<K, V> | null;\n}\n\n/**\n * Least Recently Used cache.\n * Can be initialised with a capacity and drops the least recently used items.\n * This cache should be error robust: Cache miss on error.\n *\n * Implemented via a key lookup map and a double linked list:\n *             head              tail\n *              a next → b next → c → next null\n *  null ← prev a ← prev b ← prev c\n *\n * @template K - Type of the key used to look up the values inside the cache\n * @template V - Type of the values inside the cache\n */\nexport class LruCache<K, V> {\n    /** Head of the list. */\n    private head: CacheItem<K, V> | null = null;\n    /** Tail of the list */\n    private tail: CacheItem<K, V> | null = null;\n    /** Key lookup map */\n    private map: Map<K, CacheItem<K, V>>;\n\n    /**\n     * @param capacity - Cache capcity.\n     * @throws {Error} - Raises an error if the cache capacity is less than 1.\n     */\n    public constructor(private capacity: number) {\n        if (this.capacity < 1) {\n            throw new Error(\"Cache capacity must be at least 1\");\n        }\n\n        this.map = new Map();\n    }\n\n    /**\n     * Whether the cache contains an item under this key.\n     * Marks the item as most recently used.\n     *\n     * @param key - Key of the item\n     * @returns true: item in cache, else false\n     */\n    public has(key: K): boolean {\n        try {\n            return this.getItem(key) !== undefined;\n        } catch (e) {\n            // Should not happen but makes it more robust to the unknown.\n            this.onError(e);\n            return false;\n        }\n    }\n\n    /**\n     * Returns an item from the cache.\n     * Marks the item as most recently used.\n     *\n     * @param key - Key of the item\n     * @returns The value if found, else undefined\n     */\n    public get(key: K): V | undefined {\n        try {\n            return this.getItem(key)?.value;\n        } catch (e) {\n            // Should not happen but makes it more robust to the unknown.\n            this.onError(e);\n            return undefined;\n        }\n    }\n\n    /**\n     * Adds an item to the cache.\n     * A newly added item will be the set as the most recently used.\n     *\n     * @param key - Key of the item\n     * @param value - Item value\n     */\n    public set(key: K, value: V): void {\n        try {\n            this.safeSet(key, value);\n        } catch (e) {\n            // Should not happen but makes it more robust to the unknown.\n            this.onError(e);\n        }\n    }\n\n    /**\n     * Deletes an item from the cache.\n     *\n     * @param key - Key of the item to be removed\n     */\n    public delete(key: K): void {\n        const item = this.map.get(key);\n\n        // Unknown item.\n        if (!item) return;\n\n        try {\n            this.removeItemFromList(item);\n            this.map.delete(key);\n        } catch (e) {\n            // Should not happen but makes it more robust to the unknown.\n            this.onError(e);\n        }\n    }\n\n    /**\n     * Clears the cache.\n     */\n    public clear(): void {\n        this.map = new Map();\n        this.head = null;\n        this.tail = null;\n    }\n\n    /**\n     * Returns an iterator over the cached values.\n     */\n    public *values(): IterableIterator<V> {\n        for (const item of this.map.values()) {\n            yield item.value;\n        }\n    }\n\n    private safeSet(key: K, value: V): void {\n        const item = this.getItem(key);\n\n        if (item) {\n            // The item is already stored under this key. Update the value.\n            item.value = value;\n            return;\n        }\n\n        const newItem: CacheItem<K, V> = {\n            key,\n            value,\n            next: null,\n            prev: null,\n        };\n\n        if (this.head) {\n            // Put item in front of the list.\n            this.head.prev = newItem;\n            newItem.next = this.head;\n        }\n\n        this.setHeadTail(newItem);\n\n        // Store item in lookup map.\n        this.map.set(key, newItem);\n\n        if (this.tail && this.map.size > this.capacity) {\n            // Map size exceeded cache capcity. Drop tail item.\n            this.delete(this.tail.key);\n        }\n    }\n\n    private onError(e: unknown): void {\n        logger.warn(\"LruCache error\", e);\n        this.clear();\n    }\n\n    private getItem(key: K): CacheItem<K, V> | undefined {\n        const item = this.map.get(key);\n\n        // Not in cache.\n        if (!item) return undefined;\n\n        // Item is already at the head of the list.\n        // No update required.\n        if (item === this.head) return item;\n\n        this.removeItemFromList(item);\n\n        // Put item to the front.\n\n        if (this.head) {\n            this.head.prev = item;\n        }\n\n        item.prev = null;\n        item.next = this.head;\n\n        this.setHeadTail(item);\n\n        return item;\n    }\n\n    private setHeadTail(item: CacheItem<K, V>): void {\n        if (item.prev === null) {\n            // Item has no previous item → head\n            this.head = item;\n        }\n\n        if (item.next === null) {\n            // Item has no next item → tail\n            this.tail = item;\n        }\n    }\n\n    private removeItemFromList(item: CacheItem<K, V>): void {\n        if (item === this.head) {\n            this.head = item.next;\n        }\n\n        if (item === this.tail) {\n            this.tail = item.prev;\n        }\n\n        if (item.prev) {\n            item.prev.next = item.next;\n        }\n\n        if (item.next) {\n            item.next.prev = item.prev;\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport {\n    type IMatrixProfile,\n    type MatrixClient,\n    MatrixError,\n    type MatrixEvent,\n    type RoomMember,\n    RoomMemberEvent,\n} from \"matrix-js-sdk/src/matrix\";\n\nimport { LruCache } from \"../utils/LruCache\";\n\nconst cacheSize = 500;\n\ntype StoreProfileValue = IMatrixProfile | undefined | null;\n\ninterface GetOptions {\n    /** Whether calling the function shouuld raise an Error. */\n    shouldThrow: boolean;\n}\n\n/**\n * This store provides cached access to user profiles.\n * Listens for membership events and invalidates the cache for a profile on update with different profile values.\n */\nexport class UserProfilesStore {\n    private profiles = new LruCache<string, IMatrixProfile | null>(cacheSize);\n    private profileLookupErrors = new LruCache<string, MatrixError>(cacheSize);\n    private knownProfiles = new LruCache<string, IMatrixProfile | null>(cacheSize);\n\n    public constructor(private client: MatrixClient) {\n        client.on(RoomMemberEvent.Membership, this.onRoomMembershipEvent);\n    }\n\n    /**\n     * Synchronously get a profile from the store cache.\n     *\n     * @param userId - User Id of the profile to fetch\n     * @returns The profile, if cached by the store.\n     *          Null if the profile does not exist.\n     *          Undefined if the profile is not cached by the store.\n     *          In this case a profile can be fetched from the API via {@link fetchProfile}.\n     */\n    public getProfile(userId: string): StoreProfileValue {\n        return this.profiles.get(userId);\n    }\n\n    /**\n     * Async shortcut function that returns the profile from cache or\n     * or fetches it on cache miss.\n     *\n     * @param userId - User Id of the profile to get or fetch\n     * @returns The profile, if cached by the store or fetched from the API.\n     *          Null if the profile does not exist or an error occurred during fetch.\n     */\n    public async getOrFetchProfile(userId: string, options?: GetOptions): Promise<IMatrixProfile | null> {\n        const cachedProfile = this.profiles.get(userId);\n\n        if (cachedProfile) return cachedProfile;\n\n        return this.fetchProfile(userId, options);\n    }\n\n    /**\n     * Get a profile lookup error.\n     *\n     * @param userId - User Id for which to get the lookup error\n     * @returns The lookup error or undefined if there was no error or the profile was not fetched.\n     */\n    public getProfileLookupError(userId: string): MatrixError | undefined {\n        return this.profileLookupErrors.get(userId);\n    }\n\n    /**\n     * Synchronously get a profile from known users from the store cache.\n     * Known user means that at least one shared room with the user exists.\n     *\n     * @param userId - User Id of the profile to fetch\n     * @returns The profile, if cached by the store.\n     *          Null if the profile does not exist.\n     *          Undefined if the profile is not cached by the store.\n     *          In this case a profile can be fetched from the API via {@link fetchOnlyKnownProfile}.\n     */\n    public getOnlyKnownProfile(userId: string): StoreProfileValue {\n        return this.knownProfiles.get(userId);\n    }\n\n    /**\n     * Asynchronousely fetches a profile from the API.\n     * Stores the result in the cache, so that next time {@link getProfile} returns this value.\n     *\n     * @param userId - User Id for which the profile should be fetched for\n     * @returns The profile, if found.\n     *          Null if the profile does not exist or there was an error fetching it.\n     */\n    public async fetchProfile(userId: string, options?: GetOptions): Promise<IMatrixProfile | null> {\n        const profile = await this.fetchProfileFromApi(userId, options);\n        this.profiles.set(userId, profile);\n        return profile;\n    }\n\n    /**\n     * Asynchronousely fetches a profile from a known user from the API.\n     * Known user means that at least one shared room with the user exists.\n     * Stores the result in the cache, so that next time {@link getOnlyKnownProfile} returns this value.\n     *\n     * @param userId - User Id for which the profile should be fetched for\n     * @returns The profile, if found.\n     *          Undefined if the user is unknown.\n     *          Null if the profile does not exist or there was an error fetching it.\n     */\n    public async fetchOnlyKnownProfile(userId: string): Promise<StoreProfileValue> {\n        // Do not look up unknown users. The test for existence in knownProfiles is a performance optimisation.\n        // If the user Id exists in knownProfiles we know them.\n        if (!this.knownProfiles.has(userId) && !this.isUserIdKnown(userId)) return undefined;\n\n        const profile = await this.fetchProfileFromApi(userId);\n        this.knownProfiles.set(userId, profile);\n        return profile;\n    }\n\n    public flush(): void {\n        this.profiles = new LruCache<string, IMatrixProfile | null>(cacheSize);\n        this.profileLookupErrors = new LruCache<string, MatrixError>(cacheSize);\n        this.knownProfiles = new LruCache<string, IMatrixProfile | null>(cacheSize);\n    }\n\n    /**\n     * Looks up a user profile via API.\n     *\n     * @param userId - User Id for which the profile should be fetched for\n     * @returns The profile information or null on errors\n     */\n    private async fetchProfileFromApi(userId: string, options?: GetOptions): Promise<IMatrixProfile | null> {\n        // invalidate cached profile errors\n        this.profileLookupErrors.delete(userId);\n\n        try {\n            return (await this.client.getProfileInfo(userId)) ?? null;\n        } catch (e) {\n            logger.warn(`Error retrieving profile for userId ${userId}`, e);\n\n            if (e instanceof MatrixError) {\n                this.profileLookupErrors.set(userId, e);\n            }\n\n            if (options?.shouldThrow) {\n                throw e;\n            }\n        }\n\n        return null;\n    }\n\n    /**\n     * Whether at least one shared room with the userId exists.\n     *\n     * @param userId\n     * @returns true: at least one room shared with user identified by its Id, else false.\n     */\n    private isUserIdKnown(userId: string): boolean {\n        return this.client.getRooms().some((room) => {\n            return !!room.getMember(userId);\n        });\n    }\n\n    /**\n     * Simple cache invalidation if a room membership event is received and\n     * at least one profile value differs from the cached one.\n     */\n    private onRoomMembershipEvent = (event: MatrixEvent, member: RoomMember): void => {\n        const profile = this.profiles.get(member.userId);\n\n        if (\n            profile &&\n            (profile.displayname !== member.rawDisplayName || profile.avatar_url !== member.getMxcAvatarUrl())\n        ) {\n            this.profiles.delete(member.userId);\n        }\n\n        const knownProfile = this.knownProfiles.get(member.userId);\n\n        if (\n            knownProfile &&\n            (knownProfile.displayname !== member.rawDisplayName || knownProfile.avatar_url !== member.getMxcAvatarUrl())\n        ) {\n            this.knownProfiles.delete(member.userId);\n        }\n    };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient, discoverAndValidateOIDCIssuerWellKnown } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { OidcClient } from \"oidc-client-ts\";\n\nimport {\n    getStoredOidcTokenIssuer,\n    getStoredOidcClientId,\n    getStoredOidcIdToken,\n} from \"../../utils/oidc/persistOidcSettings\";\nimport PlatformPeg from \"../../PlatformPeg\";\n\n/**\n * @experimental\n * Stores information about configured OIDC provider\n *\n * In OIDC Native mode the client is registered with OIDC directly and maintains an OIDC token.\n *\n * In OIDC Aware mode, the client is aware that the Server is using OIDC, but is using the standard Matrix APIs for most things.\n * (Notable exceptions are account management, where a link to the account management endpoint will be provided instead.)\n *\n * Otherwise, the store is not operating. Auth is then in Legacy mode and everything uses normal Matrix APIs.\n */\nexport class OidcClientStore {\n    private oidcClient?: OidcClient;\n    private initialisingOidcClientPromise: Promise<void> | undefined;\n    private authenticatedIssuer?: string; // set only in OIDC-native mode\n    private _accountManagementEndpoint?: string;\n    private _accountManagementActionsSupported?: string[];\n    /**\n     * Promise which resolves once this store is read to use, which may mean there is no OIDC client if we're in legacy mode,\n     * or we just have the account management endpoint if running in OIDC-aware mode.\n     */\n    public readonly readyPromise: Promise<void>;\n\n    public constructor(private readonly matrixClient: MatrixClient) {\n        this.readyPromise = this.init();\n    }\n\n    private async init(): Promise<void> {\n        this.authenticatedIssuer = getStoredOidcTokenIssuer();\n        if (this.authenticatedIssuer) {\n            await this.getOidcClient();\n        } else {\n            // We are not in OIDC Native mode, as we have no locally stored issuer. Check if the server delegates auth to OIDC.\n            try {\n                const authMetadata = await this.matrixClient.getAuthMetadata();\n                this.setAccountManagementEndpoint(\n                    authMetadata.account_management_uri,\n                    authMetadata.issuer,\n                    authMetadata.account_management_actions_supported,\n                );\n            } catch (e) {\n                console.log(\"Auth issuer not found\", e);\n            }\n        }\n    }\n\n    /**\n     * True when the active user is authenticated via OIDC\n     */\n    public get isUserAuthenticatedWithOidc(): boolean {\n        return !!this.authenticatedIssuer;\n    }\n\n    private setAccountManagementEndpoint(\n        endpoint: string | undefined,\n        issuer: string,\n        actionsSupported?: string[],\n    ): void {\n        // if no account endpoint is configured default to the issuer\n        const url = new URL(endpoint ?? issuer);\n        const idToken = getStoredOidcIdToken();\n        if (idToken) {\n            url.searchParams.set(\"id_token_hint\", idToken);\n        }\n        this._accountManagementEndpoint = url.toString();\n        this._accountManagementActionsSupported = actionsSupported;\n    }\n\n    public get accountManagementEndpoint(): string | undefined {\n        return this._accountManagementEndpoint;\n    }\n\n    public get accountManagementActionsSupported(): string[] | undefined {\n        return this._accountManagementActionsSupported;\n    }\n\n    /**\n     * Revokes provided access and refresh tokens with the configured OIDC provider\n     * @param accessToken\n     * @param refreshToken\n     * @returns Promise that resolves when tokens have been revoked\n     * @throws when OidcClient cannot be initialised, or revoking either token fails\n     */\n    public async revokeTokens(accessToken?: string, refreshToken?: string): Promise<void> {\n        const client = await this.getOidcClient();\n\n        if (!client) {\n            throw new Error(\"No OIDC client\");\n        }\n\n        const results = await Promise.all([\n            this.tryRevokeToken(client, accessToken, \"access_token\"),\n            this.tryRevokeToken(client, refreshToken, \"refresh_token\"),\n        ]);\n\n        if (results.some((success) => !success)) {\n            throw new Error(\"Failed to revoke tokens\");\n        }\n    }\n\n    /**\n     * Try to revoke a given token\n     * @param oidcClient\n     * @param token\n     * @param tokenType passed to revocation endpoint as token type hint\n     * @returns Promise that resolved with boolean whether the token revocation succeeded or not\n     */\n    private async tryRevokeToken(\n        oidcClient: OidcClient,\n        token: string | undefined,\n        tokenType: \"access_token\" | \"refresh_token\",\n    ): Promise<boolean> {\n        try {\n            if (!token) {\n                return false;\n            }\n            await oidcClient.revokeToken(token, tokenType);\n            return true;\n        } catch (error) {\n            logger.error(`Failed to revoke ${tokenType}`, error);\n            return false;\n        }\n    }\n\n    private async getOidcClient(): Promise<OidcClient | undefined> {\n        if (!this.oidcClient && !this.initialisingOidcClientPromise) {\n            this.initialisingOidcClientPromise = this.initOidcClient();\n        }\n        await this.initialisingOidcClientPromise;\n        this.initialisingOidcClientPromise = undefined;\n        return this.oidcClient;\n    }\n\n    /**\n     * Tries to initialise an OidcClient using stored clientId and OIDC discovery.\n     * Assigns this.oidcClient and accountManagement endpoint.\n     * Logs errors and does not throw when oidc client cannot be initialised.\n     * @returns promise that resolves when initialising OidcClient succeeds or fails\n     */\n    private async initOidcClient(): Promise<void> {\n        if (!this.authenticatedIssuer) {\n            logger.error(\"Cannot initialise OIDC client without issuer.\");\n            return;\n        }\n\n        try {\n            const clientId = getStoredOidcClientId();\n            const authMetadata = await discoverAndValidateOIDCIssuerWellKnown(this.authenticatedIssuer);\n            this.setAccountManagementEndpoint(\n                authMetadata.account_management_uri,\n                authMetadata.issuer,\n                authMetadata.account_management_actions_supported,\n            );\n            this.oidcClient = new OidcClient({\n                authority: authMetadata.issuer,\n                signingKeys: authMetadata.signingKeys ?? undefined,\n                redirect_uri: PlatformPeg.get()!.getOidcCallbackUrl().href,\n                client_id: clientId,\n            });\n        } catch (error) {\n            logger.error(\"Failed to initialise OidcClientStore\", error);\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\n * Fires when the middle panel has been resized (throttled).\n * @event module:utils~ResizeNotifier#\"middlePanelResized\"\n */\n/**\n * Fires when the middle panel has been resized by a pixel.\n * @event module:utils~ResizeNotifier#\"middlePanelResizedNoisy\"\n */\n\nimport { EventEmitter } from \"events\";\nimport { throttle } from \"lodash\";\n\nexport default class ResizeNotifier extends EventEmitter {\n    private _isResizing = false;\n\n    // with default options, will call fn once at first call, and then every x ms\n    // if there was another call in that timespan\n    private throttledMiddlePanel = throttle(() => this.emit(\"middlePanelResized\"), 200);\n\n    public get isResizing(): boolean {\n        return this._isResizing;\n    }\n\n    public startResizing(): void {\n        this._isResizing = true;\n        this.emit(\"isResizing\", true);\n    }\n\n    public stopResizing(): void {\n        this._isResizing = false;\n        this.emit(\"isResizing\", false);\n    }\n\n    private noisyMiddlePanel(): void {\n        this.emit(\"middlePanelResizedNoisy\");\n    }\n\n    private updateMiddlePanel(): void {\n        this.throttledMiddlePanel();\n        this.noisyMiddlePanel();\n    }\n\n    // can be called in quick succession\n    public notifyLeftHandleResized(): void {\n        // don't emit event for own region\n        this.updateMiddlePanel();\n    }\n\n    // can be called in quick succession\n    public notifyRightHandleResized(): void {\n        this.updateMiddlePanel();\n    }\n\n    public notifyTimelineHeightChanged(): void {\n        this.updateMiddlePanel();\n    }\n\n    // can be called in quick succession\n    public notifyWindowResized(): void {\n        this.updateMiddlePanel();\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { RoomViewStore } from \"./RoomViewStore\";\nimport { type MatrixDispatcher } from \"../dispatcher/dispatcher\";\nimport { type SdkContextClass } from \"../contexts/SDKContext\";\nimport { Action } from \"../dispatcher/actions\";\n\n/**\n * Acts as a cache of many RoomViewStore instances, creating them as necessary\n * given a room ID.\n */\nexport class MultiRoomViewStore {\n    /**\n     * Map from room-id to RVS instance.\n     */\n    private stores: Map<string, RoomViewStore> = new Map();\n\n    public constructor(\n        private dispatcher: MatrixDispatcher,\n        private sdkContextClass: SdkContextClass,\n    ) {}\n\n    /**\n     * Get a RVS instance for the room identified by the given roomId.\n     */\n    public getRoomViewStoreForRoom(roomId: string): RoomViewStore {\n        // Get existing store / create new store\n        const store = this.stores.has(roomId)\n            ? this.stores.get(roomId)!\n            : new RoomViewStore(this.dispatcher, this.sdkContextClass, roomId);\n\n        // RoomView component does not render the room unless you call viewRoom\n        store.viewRoom({\n            action: Action.ViewRoom,\n            room_id: roomId,\n            metricsTrigger: undefined,\n        });\n\n        // Cache the store, okay to do even if the store is already in the map\n        this.stores.set(roomId, store);\n\n        return store;\n    }\n\n    /**\n     * Remove a RVS instance that was created by {@link getRoomViewStoreForRoom}.\n     */\n    public removeRoomViewStore(roomId: string): void {\n        const didRemove = this.stores.delete(roomId);\n        if (!didRemove) {\n            logger.warn(`removeRoomViewStore called with ${roomId} but no store exists for this room.`);\n        }\n    }\n\n    public dispose(): void {\n        for (const id of this.stores.keys()) {\n            this.removeRoomViewStore(id);\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { createContext } from \"react\";\n\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport LegacyCallHandler from \"../LegacyCallHandler\";\nimport { PosthogAnalytics } from \"../PosthogAnalytics\";\nimport { SlidingSyncManager } from \"../SlidingSyncManager\";\nimport { MemberListStore } from \"../stores/MemberListStore\";\nimport { RoomNotificationStateStore } from \"../stores/notifications/RoomNotificationStateStore\";\nimport RightPanelStore from \"../stores/right-panel/RightPanelStore\";\nimport { RoomViewStore } from \"../stores/RoomViewStore\";\nimport SpaceStore, { type SpaceStoreClass } from \"../stores/spaces/SpaceStore\";\nimport TypingStore from \"../stores/TypingStore\";\nimport { UserProfilesStore } from \"../stores/UserProfilesStore\";\nimport { WidgetLayoutStore } from \"../stores/widgets/WidgetLayoutStore\";\nimport { WidgetPermissionStore } from \"../stores/widgets/WidgetPermissionStore\";\nimport { OidcClientStore } from \"../stores/oidc/OidcClientStore\";\nimport WidgetStore from \"../stores/WidgetStore\";\nimport ResizeNotifier from \"../utils/ResizeNotifier\";\nimport { MultiRoomViewStore } from \"../stores/MultiRoomViewStore\";\n\n// This context is available to components under MatrixChat,\n// the context must not be used by components outside a SdkContextClass tree.\n// This assertion allows us to make the type not nullable.\nexport const SDKContext = createContext<SdkContextClass>(null as any);\nSDKContext.displayName = \"SDKContext\";\n\n/**\n * A class which lazily initialises stores as and when they are requested, ensuring they remain\n * as singletons scoped to this object.\n */\nexport class SdkContextClass {\n    /**\n     * The global SdkContextClass instance. This is a temporary measure whilst so many stores remain global\n     * as well. Over time, these stores should accept a `SdkContextClass` instance in their constructor.\n     * When all stores do this, this static variable can be deleted.\n     */\n    public static readonly instance = new SdkContextClass();\n\n    // Optional as we don't have a client on initial load if unregistered. This should be set\n    // when the MatrixClient is first acquired in the dispatcher event Action.OnLoggedIn.\n    // It is only safe to set this once, as updating this value will NOT notify components using\n    // this Context.\n    public client?: MatrixClient;\n\n    // All protected fields to make it easier to derive test stores\n    protected _WidgetPermissionStore?: WidgetPermissionStore;\n    protected _MemberListStore?: MemberListStore;\n    protected _RightPanelStore?: RightPanelStore;\n    protected _RoomNotificationStateStore?: RoomNotificationStateStore;\n    protected _RoomViewStore?: RoomViewStore;\n    protected _WidgetLayoutStore?: WidgetLayoutStore;\n    protected _WidgetStore?: WidgetStore;\n    protected _PosthogAnalytics?: PosthogAnalytics;\n    protected _SlidingSyncManager?: SlidingSyncManager;\n    protected _SpaceStore?: SpaceStoreClass;\n    protected _LegacyCallHandler?: LegacyCallHandler;\n    protected _TypingStore?: TypingStore;\n    protected _UserProfilesStore?: UserProfilesStore;\n    protected _OidcClientStore?: OidcClientStore;\n    protected _ResizeNotifier?: ResizeNotifier;\n    protected _MultiRoomViewStore?: MultiRoomViewStore;\n\n    /**\n     * Automatically construct stores which need to be created eagerly so they can register with\n     * the dispatcher.\n     */\n    public constructEagerStores(): void {\n        this._RoomViewStore = this.roomViewStore;\n    }\n\n    public get legacyCallHandler(): LegacyCallHandler {\n        if (!this._LegacyCallHandler) {\n            this._LegacyCallHandler = LegacyCallHandler.instance;\n        }\n        return this._LegacyCallHandler;\n    }\n    public get rightPanelStore(): RightPanelStore {\n        if (!this._RightPanelStore) {\n            this._RightPanelStore = RightPanelStore.instance;\n        }\n        return this._RightPanelStore;\n    }\n    public get roomNotificationStateStore(): RoomNotificationStateStore {\n        if (!this._RoomNotificationStateStore) {\n            this._RoomNotificationStateStore = RoomNotificationStateStore.instance;\n        }\n        return this._RoomNotificationStateStore;\n    }\n    public get roomViewStore(): RoomViewStore {\n        if (!this._RoomViewStore) {\n            this._RoomViewStore = new RoomViewStore(defaultDispatcher, this);\n        }\n        return this._RoomViewStore;\n    }\n    public get widgetLayoutStore(): WidgetLayoutStore {\n        if (!this._WidgetLayoutStore) {\n            this._WidgetLayoutStore = WidgetLayoutStore.instance;\n        }\n        return this._WidgetLayoutStore;\n    }\n    public get widgetPermissionStore(): WidgetPermissionStore {\n        if (!this._WidgetPermissionStore) {\n            this._WidgetPermissionStore = new WidgetPermissionStore(this);\n        }\n        return this._WidgetPermissionStore;\n    }\n    public get widgetStore(): WidgetStore {\n        if (!this._WidgetStore) {\n            this._WidgetStore = WidgetStore.instance;\n        }\n        return this._WidgetStore;\n    }\n    public get posthogAnalytics(): PosthogAnalytics {\n        if (!this._PosthogAnalytics) {\n            this._PosthogAnalytics = PosthogAnalytics.instance;\n        }\n        return this._PosthogAnalytics;\n    }\n    public get memberListStore(): MemberListStore {\n        if (!this._MemberListStore) {\n            this._MemberListStore = new MemberListStore(this);\n        }\n        return this._MemberListStore;\n    }\n    public get slidingSyncManager(): SlidingSyncManager {\n        if (!this._SlidingSyncManager) {\n            this._SlidingSyncManager = SlidingSyncManager.instance;\n        }\n        return this._SlidingSyncManager;\n    }\n    public get spaceStore(): SpaceStoreClass {\n        if (!this._SpaceStore) {\n            this._SpaceStore = SpaceStore.instance;\n        }\n        return this._SpaceStore;\n    }\n    public get typingStore(): TypingStore {\n        if (!this._TypingStore) {\n            this._TypingStore = new TypingStore(this);\n            window.mxTypingStore = this._TypingStore;\n        }\n        return this._TypingStore;\n    }\n\n    public get userProfilesStore(): UserProfilesStore {\n        if (!this.client) {\n            throw new Error(\"Unable to create UserProfilesStore without a client\");\n        }\n\n        if (!this._UserProfilesStore) {\n            this._UserProfilesStore = new UserProfilesStore(this.client);\n        }\n\n        return this._UserProfilesStore;\n    }\n\n    public get oidcClientStore(): OidcClientStore {\n        if (!this.client) {\n            throw new Error(\"Unable to create OidcClientStore without a client\");\n        }\n\n        if (!this._OidcClientStore) {\n            this._OidcClientStore = new OidcClientStore(this.client);\n        }\n\n        return this._OidcClientStore;\n    }\n\n    // This is getting increasingly tenuous to have here but we still have class components so it's\n    // awkward to consume multiple contexts in them. This should be replaced with ResizeObservers\n    // anyway really.\n    public get resizeNotifier(): ResizeNotifier {\n        if (!this._ResizeNotifier) {\n            this._ResizeNotifier = new ResizeNotifier();\n        }\n        return this._ResizeNotifier;\n    }\n\n    public get multiRoomViewStore(): MultiRoomViewStore {\n        if (!this._MultiRoomViewStore) {\n            this._MultiRoomViewStore = new MultiRoomViewStore(defaultDispatcher, this);\n        }\n        return this._MultiRoomViewStore;\n    }\n\n    public onLoggedOut(): void {\n        this._UserProfilesStore = undefined;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { TypedEventEmitter } from \"matrix-js-sdk/src/matrix\";\nimport React, {\n    type JSX,\n    type ContextType,\n    createContext,\n    memo,\n    type ReactNode,\n    useContext,\n    useEffect,\n    useMemo,\n    useState,\n} from \"react\";\n\nimport { objectKeyChanges } from \"../utils/objects.ts\";\nimport { useTypedEventEmitter } from \"../hooks/useEventEmitter.ts\";\nimport RoomContext from \"./RoomContext.ts\";\n\n// React Contexts with frequently changing values (like State where the object reference is changed on every update)\n// cause performance issues by triggering a re-render on every component subscribed to that context.\n// With ScopedRoomContext we're effectively setting up virtual contexts which are a subset of the overall context object\n// and subscribers specify which fields they care about, and they will only be awoken on updates to those specific fields.\n\ntype ContextValue = ContextType<typeof RoomContext>;\n\nexport enum NotificationStateEvents {\n    Update = \"update\",\n}\n\ntype EventHandlerMap<C extends Record<string, any>> = {\n    [NotificationStateEvents.Update]: (keys: Array<keyof C>) => void;\n};\n\nclass EfficientContext<C extends Record<string, any>> extends TypedEventEmitter<\n    NotificationStateEvents,\n    EventHandlerMap<C>\n> {\n    public constructor(public state: C) {\n        super();\n    }\n\n    public setState(state: C): void {\n        const changedKeys = objectKeyChanges(this.state ?? ({} as C), state);\n        this.state = state;\n        this.emit(NotificationStateEvents.Update, changedKeys);\n    }\n}\n\nconst ScopedRoomContext = createContext<EfficientContext<ContextValue> | undefined>(undefined);\n\n// Uses react memo and leverages splatting the value to ensure that the context is only updated when the state changes (shallow compare)\nexport const ScopedRoomContextProvider = memo(\n    ({ children, ...state }: { children: ReactNode } & ContextValue): JSX.Element => {\n        // eslint-disable-next-line react-compiler/react-compiler,react-hooks/exhaustive-deps\n        const context = useMemo(() => new EfficientContext<ContextValue>(state), []);\n        useEffect(() => {\n            context.setState(state);\n        }, [context, state]);\n\n        // Includes the legacy RoomContext provider for backwards compatibility with class components\n        return (\n            <RoomContext.Provider value={state}>\n                <ScopedRoomContext.Provider value={context}>{children}</ScopedRoomContext.Provider>\n            </RoomContext.Provider>\n        );\n    },\n);\n\ntype ScopedRoomContext<K extends Array<keyof ContextValue>> = { [key in K[number]]: ContextValue[key] };\n\nexport function useScopedRoomContext<K extends Array<keyof ContextValue>>(...keys: K): ScopedRoomContext<K> {\n    const context = useContext(ScopedRoomContext);\n    const [state, setState] = useState<ScopedRoomContext<K>>(context?.state ?? ({} as ScopedRoomContext<K>));\n\n    useTypedEventEmitter(context, NotificationStateEvents.Update, (updatedKeys: K): void => {\n        if (context?.state && updatedKeys.some((updatedKey) => keys.includes(updatedKey))) {\n            setState(context.state);\n        }\n    });\n\n    return state;\n}\n","/*\nCopyright 2025 Element Creations Ltd.\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type MatrixClient,\n    ClientEvent,\n    type Room,\n    EventType,\n    RoomCreateTypeField,\n    RoomType,\n    type ICreateRoomOpts,\n    HistoryVisibility,\n    JoinRule,\n    Preset,\n    RestrictedAllowType,\n    Visibility,\n    Direction,\n    RoomStateEvent,\n    type RoomState,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type RoomEncryptionEventContent } from \"matrix-js-sdk/src/types\";\n\nimport Modal, { type IHandle } from \"./Modal\";\nimport { _t, UserFriendlyError } from \"./languageHandler\";\nimport dis from \"./dispatcher/dispatcher\";\nimport * as Rooms from \"./Rooms\";\nimport { getAddressType } from \"./UserAddress\";\nimport SpaceStore from \"./stores/spaces/SpaceStore\";\nimport { makeSpaceParentEvent } from \"./utils/space\";\nimport { JitsiCall, ElementCall } from \"./models/Call\";\nimport { Action } from \"./dispatcher/actions\";\nimport ErrorDialog from \"./components/views/dialogs/ErrorDialog\";\nimport Spinner from \"./components/views/elements/Spinner\";\nimport { type ViewRoomPayload } from \"./dispatcher/payloads/ViewRoomPayload\";\nimport { findDMForUser } from \"./utils/dm/findDMForUser\";\nimport { privateShouldBeEncrypted } from \"./utils/rooms\";\nimport { shouldForceDisableEncryption } from \"./utils/crypto/shouldForceDisableEncryption\";\nimport { waitForMember } from \"./utils/membership\";\nimport { doesRoomVersionSupport, PreferredRoomVersions } from \"./utils/PreferredRoomVersions\";\nimport SettingsStore from \"./settings/SettingsStore\";\nimport { MEGOLM_ENCRYPTION_ALGORITHM } from \"./utils/crypto\";\nimport { ElementCallMemberEventType } from \"./call-types\";\nimport { htmlSerializeFromMdIfNeeded } from \"./editor/serialize\";\n\n// we define a number of interfaces which take their names from the js-sdk\n/* eslint-disable camelcase */\n\nexport interface IOpts {\n    dmUserId?: string;\n    /**\n     * The name of the room to be created.\n     */\n    name?: string;\n    /**\n     * The topic for the room.\n     */\n    topic?: string;\n    /**\n     * Additional options to pass to the room creation API.\n     * Note: \"name\", \"topic\", and \"avatar\" should be set via their respective properties in IOpts.\n     */\n    createOpts?: Omit<ICreateRoomOpts, \"name\" | \"topic\" | \"avatar\">;\n    spinner?: boolean;\n    guestAccess?: boolean;\n    encryption?: boolean;\n    /**\n     * Encrypt state events as per MSC4362\n     */\n    stateEncryption?: boolean;\n    inlineErrors?: boolean;\n    andView?: boolean;\n    avatar?: File | string; // will upload if given file, else mxcUrl is needed\n    roomType?: RoomType | string;\n    historyVisibility?: HistoryVisibility;\n    parentSpace?: Room;\n    // contextually only makes sense if parentSpace is specified, if true then will be added to parentSpace as suggested\n    suggested?: boolean;\n    joinRule?: JoinRule;\n}\n\nconst DEFAULT_EVENT_POWER_LEVELS = {\n    [EventType.RoomName]: 50,\n    [EventType.RoomAvatar]: 50,\n    [EventType.RoomPowerLevels]: 100,\n    [EventType.RoomHistoryVisibility]: 100,\n    [EventType.RoomCanonicalAlias]: 50,\n    [EventType.RoomTombstone]: 100,\n    [EventType.RoomServerAcl]: 100,\n    [EventType.RoomEncryption]: 100,\n};\n\n/**\n * Create a new room, and switch to it.\n *\n * @param client The Matrix Client instance to create the room with\n * @param {object=} opts parameters for creating the room\n * @param {string=} opts.dmUserId If specified, make this a DM room for this user and invite them\n * @param {object=} opts.createOpts set of options to pass to createRoom call.\n * @param {bool=} opts.spinner True to show a modal spinner while the room is created.\n *     Default: True\n * @param {bool=} opts.guestAccess Whether to enable guest access.\n *     Default: True\n * @param {bool=} opts.encryption Whether to enable encryption.\n *     Default: False\n * @param {bool=} opts.inlineErrors True to raise errors off the promise instead of resolving to null.\n *     Default: False\n * @param {bool=} opts.andView True to dispatch an action to view the room once it has been created.\n *\n * @returns {Promise} which resolves to the room id, or null if the\n * action was aborted or failed.\n */\nexport default async function createRoom(client: MatrixClient, opts: IOpts): Promise<string | null> {\n    opts = opts || {};\n    if (opts.spinner === undefined) opts.spinner = true;\n    if (opts.guestAccess === undefined) opts.guestAccess = true;\n    if (opts.encryption === undefined) opts.encryption = false;\n    if (opts.stateEncryption === undefined) opts.stateEncryption = false;\n\n    if (client.isGuest()) {\n        dis.dispatch({ action: \"require_registration\" });\n        return null;\n    }\n\n    const defaultPreset = opts.dmUserId ? Preset.TrustedPrivateChat : Preset.PrivateChat;\n\n    // set some defaults for the creation\n    const createOpts: ICreateRoomOpts = opts.createOpts || {};\n    createOpts.preset = createOpts.preset || defaultPreset;\n    createOpts.visibility = createOpts.visibility || Visibility.Private;\n\n    // We allow UX of DMing ourselves as a form of creating a personal room but the server throws\n    // an error when a user tries to invite themselves so we filter it out\n    if (opts.dmUserId && opts.dmUserId !== client.getUserId() && createOpts.invite === undefined) {\n        switch (getAddressType(opts.dmUserId)) {\n            case \"mx-user-id\":\n                createOpts.invite = [opts.dmUserId];\n                break;\n            case \"email\": {\n                const isUrl = client.getIdentityServerUrl(true);\n                if (!isUrl) {\n                    throw new UserFriendlyError(\"cannot_invite_without_identity_server\");\n                }\n                createOpts.invite_3pid = [\n                    {\n                        id_server: isUrl,\n                        medium: \"email\",\n                        address: opts.dmUserId,\n                    },\n                ];\n                break;\n            }\n        }\n    }\n    if (opts.dmUserId && createOpts.is_direct === undefined) {\n        createOpts.is_direct = true;\n    }\n\n    if (opts.roomType) {\n        createOpts.creation_content = {\n            ...createOpts.creation_content,\n            [RoomCreateTypeField]: opts.roomType,\n        };\n\n        // Video rooms require custom power levels\n        if (opts.roomType === RoomType.ElementVideo || opts.roomType === RoomType.UnstableCall) {\n            createOpts.power_level_content_override = {\n                events: {\n                    ...DEFAULT_EVENT_POWER_LEVELS,\n                    // Allow all users to send call membership updates\n                    [opts.roomType === RoomType.ElementVideo\n                        ? JitsiCall.MEMBER_EVENT_TYPE\n                        : ElementCallMemberEventType.name]: 0,\n                    // Ensure all but admins can't change widgets\n                    // A previous version of the code prevented even administrators\n                    // from changing this, but this is not possible now that room creators\n                    // have an immutable power level\n                    [\"im.vector.modular.widgets\"]: 100,\n                },\n            };\n        }\n    } else if (SettingsStore.getValue(\"feature_group_calls\")) {\n        createOpts.power_level_content_override = {\n            events: {\n                ...DEFAULT_EVENT_POWER_LEVELS,\n                // It should always (including non video rooms) be possible to join a group call.\n                [ElementCallMemberEventType.name]: 0,\n            },\n        };\n    }\n\n    // By default, view the room after creating it\n    if (opts.andView === undefined) {\n        opts.andView = true;\n    }\n\n    createOpts.initial_state = createOpts.initial_state || [];\n\n    // Allow guests by default since the room is private and they'd\n    // need an invite. This means clicking on a 3pid invite email can\n    // actually drop you right in to a chat.\n    if (opts.guestAccess) {\n        createOpts.initial_state.push({\n            type: \"m.room.guest_access\",\n            state_key: \"\",\n            content: {\n                guest_access: \"can_join\",\n            },\n        });\n    }\n\n    if (opts.encryption) {\n        const content: RoomEncryptionEventContent = {\n            algorithm: MEGOLM_ENCRYPTION_ALGORITHM,\n        };\n        if (opts.stateEncryption) {\n            content[\"io.element.msc4362.encrypt_state_events\"] = true;\n        }\n        createOpts.initial_state.push({\n            type: \"m.room.encryption\",\n            state_key: \"\",\n            content,\n        });\n    }\n\n    const defaultRoomVersion = (await client.getCapabilities())[\"m.room_versions\"]?.default ?? \"1\";\n\n    if (\n        opts.joinRule === JoinRule.Knock &&\n        !doesRoomVersionSupport(defaultRoomVersion, PreferredRoomVersions.KnockRooms)\n    ) {\n        createOpts.room_version = PreferredRoomVersions.KnockRooms;\n    }\n\n    if (opts.parentSpace) {\n        createOpts.initial_state.push(makeSpaceParentEvent(opts.parentSpace, true));\n\n        if (opts.joinRule === JoinRule.Restricted) {\n            if (!doesRoomVersionSupport(defaultRoomVersion, PreferredRoomVersions.KnockRooms)) {\n                createOpts.room_version = PreferredRoomVersions.RestrictedRooms;\n            }\n\n            createOpts.initial_state.push({\n                type: EventType.RoomJoinRules,\n                content: {\n                    join_rule: JoinRule.Restricted,\n                    allow: [\n                        {\n                            type: RestrictedAllowType.RoomMembership,\n                            room_id: opts.parentSpace.roomId,\n                        },\n                    ],\n                },\n            });\n        }\n    }\n\n    // we handle the restricted join rule in the parentSpace handling block above\n    if (opts.joinRule && opts.joinRule !== JoinRule.Restricted) {\n        createOpts.initial_state.push({\n            type: EventType.RoomJoinRules,\n            content: { join_rule: opts.joinRule },\n        });\n    }\n\n    // If we are not encrypting state, copy name, topic, avatar over to\n    // createOpts so we pass them in when we call Client.createRoom().\n    if (!opts.stateEncryption) {\n        if (opts.name) {\n            createOpts.name = opts.name;\n        }\n\n        if (opts.topic) {\n            createOpts.topic = opts.topic;\n        }\n\n        if (opts.avatar) {\n            let url = opts.avatar;\n            if (opts.avatar instanceof File) {\n                ({ content_uri: url } = await client.uploadContent(opts.avatar));\n            }\n\n            createOpts.initial_state.push({\n                type: EventType.RoomAvatar,\n                content: { url },\n            });\n        }\n    }\n\n    // Set history visibility to \"invited\" for DMs and non-public rooms unless explicitly overridden\n    // This ensures that room history is only visible to invited members by default\n    let historyVisibility = opts.historyVisibility;\n    if (!historyVisibility) {\n        // Determine if the room will be public based on the join rule or preset\n        const isPublicRoom = opts.joinRule === JoinRule.Public || createOpts.preset === Preset.PublicChat;\n\n        // For DMs and non-public rooms, set history visibility to \"invited\"\n        if (opts.dmUserId || !isPublicRoom) {\n            historyVisibility = HistoryVisibility.Invited;\n        }\n    }\n\n    if (historyVisibility) {\n        createOpts.initial_state.push({\n            type: EventType.RoomHistoryVisibility,\n            content: {\n                history_visibility: historyVisibility,\n            },\n        });\n    }\n\n    let modal: IHandle<any> | undefined;\n    if (opts.spinner) modal = Modal.createDialog(Spinner, undefined, \"mx_Dialog_spinner\");\n\n    let roomId: string;\n    let room: Promise<Room>;\n    return client\n        .createRoom(createOpts)\n        .catch(function (err) {\n            // NB This checks for the Synapse-specific error condition of a room creation\n            // having been denied because the requesting user wanted to publish the room,\n            // but the server denies them that permission (via room_list_publication_rules).\n            // The check below responds by retrying without publishing the room.\n            if (\n                err.httpStatus === 403 &&\n                err.errcode === \"M_UNKNOWN\" &&\n                err.data.error === \"Not allowed to publish room\"\n            ) {\n                logger.warn(\"Failed to publish room, try again without publishing it\");\n                createOpts.visibility = Visibility.Private;\n                return client.createRoom(createOpts);\n            } else {\n                return Promise.reject(err);\n            }\n        })\n        .then(async (res): Promise<void> => {\n            roomId = res.room_id;\n\n            room = new Promise((resolve) => {\n                const storedRoom = client.getRoom(roomId);\n                if (storedRoom) {\n                    resolve(storedRoom);\n                } else {\n                    // The room hasn't arrived down sync yet\n                    const onRoom = (emittedRoom: Room): void => {\n                        if (emittedRoom.roomId === roomId) {\n                            resolve(emittedRoom);\n                            client.off(ClientEvent.Room, onRoom);\n                        }\n                    };\n                    client.on(ClientEvent.Room, onRoom);\n                }\n            });\n\n            if (opts.dmUserId) await Rooms.setDMRoom(client, roomId, opts.dmUserId);\n        })\n        .then(async () => {\n            // We need to set up initial state manually if state encryption is enabled, since it needs\n            // to be encrypted.\n            if (opts.encryption && opts.stateEncryption) {\n                await enableStateEventEncryption(client, await room, opts);\n            }\n        })\n        .finally(function () {\n            if (modal) modal.close();\n        })\n        .then(() => {\n            if (opts.parentSpace) {\n                return SpaceStore.instance.addRoomToSpace(\n                    opts.parentSpace,\n                    roomId,\n                    [client.getDomain()!],\n                    opts.suggested,\n                );\n            }\n        })\n        .then(async (): Promise<void> => {\n            if (opts.roomType === RoomType.ElementVideo) {\n                // Set up this video room with a Jitsi call\n                await JitsiCall.create(await room);\n            } else if (opts.roomType === RoomType.UnstableCall) {\n                // Set up this video room with an Element call\n                ElementCall.create(await room);\n            }\n        })\n        .then(\n            function () {\n                // NB we haven't necessarily blocked on the room promise, so we race\n                // here with the client knowing that the room exists, causing things\n                // like https://github.com/vector-im/vector-web/issues/1813\n                // Even if we were to block on the echo, servers tend to split the room\n                // state over multiple syncs so we can't atomically know when we have the\n                // entire thing.\n                if (opts.andView) {\n                    dis.dispatch<ViewRoomPayload>({\n                        action: Action.ViewRoom,\n                        room_id: roomId,\n                        should_peek: false,\n                        // Creating a room will have joined us to the room,\n                        // so we are expecting the room to come down the sync\n                        // stream, if it hasn't already.\n                        joining: true,\n                        justCreatedOpts: opts,\n                        metricsTrigger: \"Created\",\n                    });\n                }\n                return roomId;\n            },\n            function (err) {\n                // Raise the error if the caller requested that we do so.\n                if (opts.inlineErrors) throw err;\n\n                // We also failed to join the room (this sets joining to false in RoomViewStore)\n                dis.dispatch({\n                    action: Action.JoinRoomError,\n                    roomId,\n                });\n                logger.error(\"Failed to create room \" + roomId + \" \" + err);\n                let description = _t(\"create_room|generic_error\");\n                if (err.errcode === \"M_UNSUPPORTED_ROOM_VERSION\") {\n                    // Technically not possible with the UI as of April 2019 because there's no\n                    // options for the user to change this. However, it's not a bad thing to report\n                    // the error to the user for if/when the UI is available.\n                    description = _t(\"create_room|unsupported_version\");\n                }\n                Modal.createDialog(ErrorDialog, {\n                    title: _t(\"create_room|error_title\"),\n                    description,\n                });\n                return null;\n            },\n        );\n}\n\nasync function enableStateEventEncryption(client: MatrixClient, room: Room, opts: IOpts): Promise<void> {\n    // Don't send our state events until encryption is enabled. If this times\n    // out after 30 seconds, we throw since we don't want to send the events\n    // unencrypted.\n    await waitForRoomEncryption(room, 30000);\n\n    // Set room name\n    if (opts.name) {\n        await client.setRoomName(room.roomId, opts.name);\n    }\n\n    // Set room topic\n    if (opts.topic) {\n        const htmlTopic = htmlSerializeFromMdIfNeeded(opts.topic, { forceHTML: false });\n        await client.setRoomTopic(room.roomId, opts.topic, htmlTopic);\n    }\n\n    // Set room avatar\n    if (opts.avatar) {\n        let url: string;\n        if (opts.avatar instanceof File) {\n            ({ content_uri: url } = await client.uploadContent(opts.avatar));\n        } else {\n            url = opts.avatar;\n        }\n        await client.sendStateEvent(room.roomId, EventType.RoomAvatar, { url }, \"\");\n    }\n}\n\n/**\n * Wait until the supplied room has an `m.room.encryption` event, or time out\n * after 30 seconds.\n */\nexport async function waitForRoomEncryption(room: Room, waitTimeMs: number): Promise<void> {\n    if (room.hasEncryptionStateEvent()) {\n        return;\n    }\n\n    // Start a 30s timeout and return \"timed_out\" if we hit it\n    const { promise: timeoutPromise, resolve: timeoutResolve } = Promise.withResolvers();\n    const timeout = setTimeout(timeoutResolve, waitTimeMs, \"timed_out\");\n\n    // Listen for a RoomEncryption state update and return\n    // \"received_encryption_state\" if we get it\n    const roomState = room.getLiveTimeline().getState(Direction.Forward)!;\n    const { promise: stateUpdatePromise, resolve: stateUpdateResolve } = Promise.withResolvers();\n    const onRoomStateUpdate = (state: RoomState): void => {\n        if (state.getStateEvents(EventType.RoomEncryption, \"\")) {\n            stateUpdateResolve(\"received_encryption_state\");\n        }\n    };\n    roomState.on(RoomStateEvent.Update, onRoomStateUpdate);\n\n    // Wait for one of the above to happen\n    const resolution = await Promise.race([timeoutPromise, stateUpdatePromise]);\n\n    // Clear the listener and the timeout\n    roomState.off(RoomStateEvent.Update, onRoomStateUpdate);\n    clearTimeout(timeout);\n\n    // Fail if we hit the timeout\n    if (resolution === \"timed_out\") {\n        logger.warn(\"Timed out while waiting for room to enable encryption\");\n        throw new Error(\"Timed out while waiting for room to enable encryption\");\n    }\n}\n\n/*\n * Ensure that for every user in a room, there is at least one device that we\n * can encrypt to.\n */\nexport async function canEncryptToAllUsers(client: MatrixClient, userIds: string[]): Promise<boolean> {\n    try {\n        const usersDeviceMap = await client.getCrypto()?.getUserDeviceInfo(userIds, true);\n        if (!usersDeviceMap) {\n            return false;\n        }\n\n        for (const devices of usersDeviceMap.values()) {\n            if (devices.size === 0) {\n                // This user does not have any encryption-capable devices.\n                return false;\n            }\n        }\n    } catch (e) {\n        logger.error(\"Error determining if it's possible to encrypt to all users: \", e);\n        return false; // assume not\n    }\n\n    return true;\n}\n\nexport async function ensureDMExists(client: MatrixClient, userId: string): Promise<string | null> {\n    const existingDMRoom = findDMForUser(client, userId);\n    let roomId: string | null;\n    if (existingDMRoom) {\n        roomId = existingDMRoom.roomId;\n    } else {\n        let encryption: boolean | undefined;\n        if (privateShouldBeEncrypted(client)) {\n            encryption = await canEncryptToAllUsers(client, [userId]);\n        }\n\n        roomId = await createRoom(client, { encryption, dmUserId: userId, spinner: false, andView: false });\n        if (!roomId) return null;\n        await waitForMember(client, roomId, userId);\n    }\n    return roomId;\n}\n\ninterface AllowedEncryptionSetting {\n    /**\n     * True when the user is allowed to choose whether encryption is enabled\n     */\n    allowChange: boolean;\n    /**\n     * Set when user is not allowed to choose encryption setting\n     * True when encryption is forced to enabled\n     */\n    forcedValue?: boolean;\n}\n/**\n * Check if server configuration supports the user changing encryption for a room\n * First check if server features force enable encryption for the given room type\n * If not, check if server .well-known forces encryption to disabled\n * If either are forced, then do not allow the user to change room's encryption\n * @param client\n * @param chatPreset chat type\n * @returns Promise<boolean>\n */\nexport async function checkUserIsAllowedToChangeEncryption(\n    client: MatrixClient,\n    chatPreset: Preset,\n): Promise<AllowedEncryptionSetting> {\n    const doesServerForceEncryptionForPreset = await client.doesServerForceEncryptionForPreset(chatPreset);\n    const doesWellKnownForceDisableEncryption = shouldForceDisableEncryption(client);\n\n    // server is forcing encryption to ENABLED\n    // while .well-known config is forcing it to DISABLED\n    // server version config overrides wk config\n    if (doesServerForceEncryptionForPreset && doesWellKnownForceDisableEncryption) {\n        console.warn(\n            `Conflicting e2ee settings: server config and .well-known configuration disagree. Using server forced encryption setting for chat type ${chatPreset}`,\n        );\n    }\n\n    if (doesServerForceEncryptionForPreset) {\n        return { allowChange: false, forcedValue: true };\n    }\n    if (doesWellKnownForceDisableEncryption) {\n        return { allowChange: false, forcedValue: false };\n    }\n\n    return { allowChange: true };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type { AliasCustomisations } from \"@element-hq/element-web-module-api\";\n\n// A real customisation module will define and export one or more of the\n// customisation points that make up `AliasCustomisations`.\nexport default {} as AliasCustomisations;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ChatExportCustomisations } from \"@element-hq/element-web-module-api\";\n\nimport { type ExportFormat, type ExportType } from \"../utils/exportUtils/exportUtils\";\n\nexport type ForceChatExportParameters = ReturnType<\n    ChatExportCustomisations<ExportFormat, ExportType>[\"getForceChatExportParameters\"]\n>;\n\n/**\n * Force parameters in room chat export\n * fields returned here are forced\n * and not allowed to be edited in the chat export form\n */\nconst getForceChatExportParameters = (): ForceChatExportParameters => {\n    return {};\n};\n\n// A real customisation module will define and export one or more of the\n// customisation points that make up `IChatExportCustomisations`.\nexport default {\n    getForceChatExportParameters,\n} as ChatExportCustomisations<ExportFormat, ExportType>;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// Dev note: this customisation point is heavily inspired by UIFeature flags, though\n// with an intention of being used for more complex switching on whether or not a feature\n// should be shown.\n\n// Populate this class with the details of your customisations when copying it.\n\nimport { type ComponentVisibilityCustomisations as IComponentVisibilityCustomisations } from \"@element-hq/element-web-module-api\";\n\n// A real customisation module will define and export one or more of the\n// customisation points that make up the interface above.\nexport const ComponentVisibilityCustomisations: IComponentVisibilityCustomisations = {\n    // while we don't specify the functions here, their defaults are described\n    // in their pseudo-implementations above.\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type { DirectoryCustomisations } from \"@element-hq/element-web-module-api\";\n\n// A real customisation module will define and export one or more of the\n// customisation points that make up `IDirectoryCustomisations`.\nexport default {} as DirectoryCustomisations;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type { LifecycleCustomisations } from \"@element-hq/element-web-module-api\";\n\n// A real customisation module will define and export one or more of the\n// customisation points that make up `ILifecycleCustomisations`.\nexport default {} as LifecycleCustomisations;\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2021 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type MatrixClient, parseErrorResponse, type ResizeMethod } from \"matrix-js-sdk/src/matrix\";\nimport { type MediaEventContent } from \"matrix-js-sdk/src/types\";\n\nimport type { MediaCustomisations, Media } from \"@element-hq/element-web-module-api\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { type IPreparedMedia, prepEventContentAsMedia } from \"./models/IMediaEventContent\";\nimport { UserFriendlyError } from \"../languageHandler\";\n\n// Populate this class with the details of your customisations when copying it.\n\n// Implementation note: The Media class must complete the contract as shown here, though\n// the constructor can be whatever is relevant to your implementation. The mediaForX\n// functions below create an instance of the Media class and are used throughout the\n// project.\n\n/**\n * A media object is a representation of a \"source media\" and an optional\n * \"thumbnail media\", derived from event contents or external sources.\n */\nclass MediaImplementation implements Media {\n    private client: MatrixClient;\n\n    // Per above, this constructor signature can be whatever is helpful for you.\n    public constructor(\n        private prepared: IPreparedMedia,\n        client?: MatrixClient,\n    ) {\n        this.client = client ?? MatrixClientPeg.safeGet();\n        if (!this.client) {\n            throw new Error(\"No possible MatrixClient for media resolution. Please provide one or log in.\");\n        }\n    }\n\n    /**\n     * True if the media appears to be encrypted. Actual file contents may vary.\n     */\n    public get isEncrypted(): boolean {\n        return !!this.prepared.file;\n    }\n\n    /**\n     * The MXC URI of the source media.\n     */\n    public get srcMxc(): string {\n        return this.prepared.mxc;\n    }\n\n    /**\n     * The MXC URI of the thumbnail media, if a thumbnail is recorded. Null/undefined\n     * otherwise.\n     */\n    public get thumbnailMxc(): string | undefined {\n        return this.prepared.thumbnail?.mxc;\n    }\n\n    /**\n     * Whether or not a thumbnail is recorded for this media.\n     */\n    public get hasThumbnail(): boolean {\n        return !!this.thumbnailMxc;\n    }\n\n    /**\n     * The HTTP URL for the source media.\n     */\n    public get srcHttp(): string | null {\n        // eslint-disable-next-line no-restricted-properties\n        return this.client.mxcUrlToHttp(this.srcMxc, undefined, undefined, undefined, false, true) || null;\n    }\n\n    /**\n     * The HTTP URL for the thumbnail media (without any specified width, height, etc). Null/undefined\n     * if no thumbnail media recorded.\n     */\n    public get thumbnailHttp(): string | null {\n        if (!this.hasThumbnail) return null;\n        // eslint-disable-next-line no-restricted-properties\n        return this.client.mxcUrlToHttp(this.thumbnailMxc!, undefined, undefined, undefined, false, true);\n    }\n\n    /**\n     * Gets the HTTP URL for the thumbnail media with the requested characteristics, if a thumbnail\n     * is recorded for this media. Returns null/undefined otherwise.\n     * @param {number} width The desired width of the thumbnail.\n     * @param {number} height The desired height of the thumbnail.\n     * @param {\"scale\"|\"crop\"} mode The desired thumbnailing mode. Defaults to scale.\n     * @returns {string} The HTTP URL which points to the thumbnail.\n     */\n    public getThumbnailHttp(width: number, height: number, mode: ResizeMethod = \"scale\"): string | null {\n        if (!this.hasThumbnail) return null;\n        // scale using the device pixel ratio to keep images clear\n        width = Math.floor(width * window.devicePixelRatio);\n        height = Math.floor(height * window.devicePixelRatio);\n        // eslint-disable-next-line no-restricted-properties\n        return this.client.mxcUrlToHttp(this.thumbnailMxc!, width, height, mode, false, true);\n    }\n\n    /**\n     * Gets the HTTP URL for a thumbnail of the source media with the requested characteristics.\n     * @param {number} width The desired width of the thumbnail.\n     * @param {number} height The desired height of the thumbnail.\n     * @param {\"scale\"|\"crop\"} mode The desired thumbnailing mode. Defaults to scale.\n     * @returns {string} The HTTP URL which points to the thumbnail.\n     */\n    public getThumbnailOfSourceHttp(width: number, height: number, mode: ResizeMethod = \"scale\"): string | null {\n        // scale using the device pixel ratio to keep images clear\n        width = Math.floor(width * window.devicePixelRatio);\n        height = Math.floor(height * window.devicePixelRatio);\n        // eslint-disable-next-line no-restricted-properties\n        return this.client.mxcUrlToHttp(this.srcMxc, width, height, mode, false, true);\n    }\n\n    /**\n     * Creates a square thumbnail of the media. If the media has a thumbnail recorded, that MXC will\n     * be used, otherwise the source media will be used.\n     * @param {number} dim The desired width and height.\n     * @returns {string} An HTTP URL for the thumbnail.\n     */\n    public getSquareThumbnailHttp(dim: number): string | null {\n        dim = Math.floor(dim * window.devicePixelRatio); // scale using the device pixel ratio to keep images clear\n        if (this.hasThumbnail) {\n            return this.getThumbnailHttp(dim, dim, \"crop\");\n        }\n        return this.getThumbnailOfSourceHttp(dim, dim, \"crop\");\n    }\n\n    /**\n     * Downloads the source media.\n     * @returns {Promise<Response>} Resolves to the server's response for chaining.\n     */\n    public async downloadSource(): Promise<Response> {\n        const src = this.srcHttp;\n        if (!src) {\n            throw new UserFriendlyError(\"error|download_media\");\n        }\n        const res = await fetch(src);\n        if (!res.ok) {\n            throw parseErrorResponse(res, await res.text());\n        }\n        return res;\n    }\n}\n\nexport type { Media };\n\ntype BaseMedia = MediaCustomisations<Partial<MediaEventContent>, MatrixClient, IPreparedMedia>;\n\n/**\n * Creates a media object from event content.\n * @param {MediaEventContent} content The event content.\n * @param {MatrixClient} client Optional client to use.\n * @returns {MediaImplementation} The media object.\n */\nexport const mediaFromContent: BaseMedia[\"mediaFromContent\"] = (\n    content: Partial<MediaEventContent>,\n    client?: MatrixClient,\n): Media => new MediaImplementation(prepEventContentAsMedia(content), client);\n\n/**\n * Creates a media object from an MXC URI.\n * @param {string} mxc The MXC URI.\n * @param {MatrixClient} client Optional client to use.\n * @returns {MediaImplementation} The media object.\n */\nexport const mediaFromMxc: BaseMedia[\"mediaFromMxc\"] = (mxc?: string, client?: MatrixClient): Media => {\n    return mediaFromContent({ url: mxc }, client);\n};\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2021 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type EncryptedFile, type MediaEventContent } from \"matrix-js-sdk/src/types\";\n\nexport interface IPreparedMedia extends IMediaObject {\n    thumbnail?: IMediaObject;\n}\n\nexport interface IMediaObject {\n    mxc: string;\n    file?: EncryptedFile;\n}\n\n/**\n * Parses an event content body into a prepared media object. This prepared media object\n * can be used with other functions to manipulate the media.\n * @param {MediaEventContent} content Unredacted media event content. See interface.\n * @returns {IPreparedMedia} A prepared media object.\n * @throws Throws if the given content cannot be packaged into a prepared media object.\n */\nexport function prepEventContentAsMedia(content: Partial<MediaEventContent>): IPreparedMedia {\n    let thumbnail: IMediaObject | undefined;\n    if (typeof content?.info === \"object\" && \"thumbnail_url\" in content.info && content.info.thumbnail_url) {\n        thumbnail = {\n            mxc: content.info.thumbnail_url,\n            file: content.info.thumbnail_file,\n        };\n    } else if (\n        typeof content?.info === \"object\" &&\n        \"thumbnail_file\" in content.info &&\n        typeof content?.info?.thumbnail_file === \"object\" &&\n        content?.info?.thumbnail_file?.url\n    ) {\n        thumbnail = {\n            mxc: content.info.thumbnail_file.url,\n            file: content.info.thumbnail_file,\n        };\n    }\n\n    if (content?.url) {\n        return {\n            thumbnail,\n            mxc: content.url,\n            file: content.file,\n        };\n    } else if (content?.file?.url) {\n        return {\n            thumbnail,\n            mxc: content.file.url,\n            file: content.file,\n        };\n    }\n\n    throw new Error(\"Invalid file provided: cannot determine MXC URI. Has it been redacted?\");\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2020 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport type { RoomListCustomisations as IRoomListCustomisations } from \"@element-hq/element-web-module-api\";\n\n// Populate this file with the details of your customisations when copying it.\n\n// A real customisation module will define and export one or more of the\n// customisation points that make up the interface above.\nexport const RoomListCustomisations: IRoomListCustomisations<Room> = {};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type { UserIdentifierCustomisations } from \"@element-hq/element-web-module-api\";\n\n/**\n * Customise display of the user identifier\n * hide userId for guests, display 3pid\n *\n * Set withDisplayName to true when user identifier will be displayed alongside user name\n */\nfunction getDisplayUserIdentifier(\n    userId: string,\n    { roomId, withDisplayName }: { roomId?: string; withDisplayName?: boolean },\n): string | null {\n    return userId;\n}\n\n// A real customisation module will define and export one or more of the\n// customisation points that make up `IUserIdentifierCustomisations`.\nexport default {\n    getDisplayUserIdentifier,\n} as UserIdentifierCustomisations;\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2020 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\n// Populate this class with the details of your customisations when copying it.\nimport { type Capability, type Widget } from \"matrix-widget-api\";\n\nimport type { WidgetPermissionsCustomisations } from \"@element-hq/element-web-module-api\";\n\n// A real customisation module will define and export one or more of the\n// customisation points that make up the interface above.\nexport const WidgetPermissionCustomisations: WidgetPermissionsCustomisations<Widget, Capability> = {};\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2021 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\n// Populate this class with the details of your customisations when copying it.\nimport { type WidgetVariablesCustomisations } from \"@element-hq/element-web-module-api\";\n\n// A real customisation module will define and export one or more of the\n// customisation points that make up the interface above.\nexport const WidgetVariableCustomisations: WidgetVariablesCustomisations = {};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type UIComponent } from \"../../settings/UIFeature\";\nimport { ComponentVisibilityCustomisations } from \"../ComponentVisibility\";\n\nexport function shouldShowComponent(component: UIComponent): boolean {\n    return ComponentVisibilityCustomisations.shouldShowComponent?.(component) ?? true;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// Dispatcher actions also extend into any arbitrary string, so support that.\nexport type DispatcherAction = Action | string;\n\nexport enum Action {\n    // TODO: Populate with actual actions\n    // This is lazily generated as it also includes fixing a bunch of references. Work\n    // that we don't really want to take on in a giant chunk. We should always define\n    // new actions here, and ideally when we touch existing ones we take some time to\n    // define them correctly.\n\n    // When defining a new action, please use lower_scored_case with an optional class\n    // name prefix. For example, `RoomListStore.view_room` or `view_user_settings`.\n    // New definitions should also receive an accompanying interface in the payloads\n    // directory.\n\n    /**\n     * View a user's profile. Should be used with a ViewUserPayload.\n     */\n    ViewUser = \"view_user\",\n\n    /**\n     * Share a text message by forwarding it to a room selected by the user\n     */\n    Share = \"share\",\n\n    /**\n     * Open the user settings. No additional payload information required.\n     * Optionally can include an OpenToTabPayload.\n     */\n    ViewUserSettings = \"view_user_settings\",\n\n    /**\n     * Open the user device settings. No additional payload information required.\n     */\n    ViewUserDeviceSettings = \"view_user_device_settings\",\n\n    /**\n     * Opens the room directory. No additional payload information required.\n     */\n    ViewRoomDirectory = \"view_room_directory\",\n\n    /**\n     * Fires when viewing room by room_alias fails to find room\n     */\n    ViewRoomError = \"view_room_error\",\n\n    /**\n     * Navigates to app home\n     */\n    ViewHomePage = \"view_home_page\",\n\n    /**\n     * Forces the theme to reload. No additional payload information required.\n     */\n    RecheckTheme = \"recheck_theme\",\n\n    /**\n     * Provide status information for an ongoing update check. Should be used with a CheckUpdatesPayload.\n     */\n    CheckUpdates = \"check_updates\",\n\n    /**\n     * Focuses the user's cursor to the send message composer. Should be used with a FocusComposerPayload.\n     */\n    FocusSendMessageComposer = \"focus_send_message_composer\",\n\n    /**\n     * Clear the  to the send message composer. Should be used with a FocusComposerPayload.\n     */\n    ClearAndFocusSendMessageComposer = \"clear_focus_send_message_composer\",\n\n    /**\n     * Focuses the user's cursor to the edit message composer. Should be used with a FocusComposerPayload.\n     */\n    FocusEditMessageComposer = \"focus_edit_message_composer\",\n\n    /**\n     * Focuses the user's cursor to the edit message composer or send message\n     * composer based on the current edit state. Should be used with a FocusComposerPayload.\n     */\n    FocusAComposer = \"focus_a_composer\",\n\n    /**\n     * Focuses the threads panel.\n     */\n    FocusThreadsPanel = \"focus_threads_panel\",\n\n    /**\n     * Opens the user menu (previously known as the top left menu). No additional payload information required.\n     */\n    ToggleUserMenu = \"toggle_user_menu\",\n\n    /**\n     * Toggles the Space panel. No additional payload information required.\n     */\n    ToggleSpacePanel = \"toggle_space_panel\",\n\n    /**\n     * Sets the apps root font size. Should be used with UpdateFontSizePayload\n     */\n    MigrateBaseFontSize = \"migrate_base_font_size\",\n\n    /**\n     * Sets the apps root font size delta. Should be used with UpdateFontSizeDeltaPayload\n     * It will add the delta to the current font size.\n     * The delta should be between {@link FontWatcher.MIN_DELTA} and {@link FontWatcher.MAX_DELTA}.\n     */\n    UpdateFontSizeDelta = \"update_font_size_delta\",\n\n    /**\n     * Sets a system font. Should be used with UpdateSystemFontPayload\n     */\n    UpdateSystemFont = \"update_system_font\",\n\n    /**\n     * Changes room based on payload parameters. Should be used with ViewRoomPayload.\n     */\n    ViewRoom = \"view_room\",\n\n    /**\n     * Changes thread based on payload parameters. Should be used with ThreadPayload.\n     */\n    ViewThread = \"view_thread\",\n\n    /**\n     * Changes room based on room list order and payload parameters. Should be used with ViewRoomDeltaPayload.\n     */\n    ViewRoomDelta = \"view_room_delta\",\n\n    /**\n     * Opens the modal dial pad\n     */\n    OpenDialPad = \"open_dial_pad\",\n\n    /**\n     * Fired when an upload has started. Should be used with UploadStartedPayload.\n     */\n    UploadStarted = \"upload_started\",\n\n    /**\n     * Fired when an upload makes progress. Should be used with UploadProgressPayload.\n     */\n    UploadProgress = \"upload_progress\",\n\n    /**\n     * Fired when an upload is completed. Should be used with UploadFinishedPayload.\n     */\n    UploadFinished = \"upload_finished\",\n\n    /**\n     * Fired when an upload fails. Should be used with UploadErrorPayload.\n     */\n    UploadFailed = \"upload_failed\",\n\n    /**\n     * Fired when an upload is cancelled by the user. Should be used with UploadCanceledPayload.\n     */\n    UploadCanceled = \"upload_canceled\",\n\n    /**\n     * Fired when requesting to join a room. Should be used with JoinRoomPayload.\n     */\n    JoinRoom = \"join_room\",\n\n    /**\n     * Fired when successfully joining a room. Should be used with a JoinRoomReadyPayload.\n     */\n    JoinRoomReady = \"join_room_ready\",\n\n    /**\n     * Fired when joining a room failed\n     */\n    JoinRoomError = \"join_room_error\",\n\n    /**\n     * Fired when starting to bulk redact messages from a user in a room.\n     */\n    BulkRedactStart = \"bulk_redact_start\",\n\n    /**\n     * Fired when done bulk redacting messages from a user in a room.\n     */\n    BulkRedactEnd = \"bulk_redact_end\",\n\n    /**\n     * Inserts content into the active composer. Should be used with ComposerInsertPayload.\n     */\n    ComposerInsert = \"composer_insert\",\n\n    /**\n     * Switches space. Should be used with SwitchSpacePayload.\n     */\n    SwitchSpace = \"switch_space\",\n\n    /**\n     * Signals to the visible space hierarchy that a change has occurred and that it should refresh.\n     */\n    UpdateSpaceHierarchy = \"update_space_hierarchy\",\n\n    /**\n     * Fires when a monitored setting is updated,\n     * see SettingsStore::monitorSetting for more details.\n     * Should be used with SettingUpdatedPayload.\n     */\n    SettingUpdated = \"setting_updated\",\n\n    /**\n     * Fires when a user starts to edit event (e.g. up arrow in compositor)\n     */\n    EditEvent = \"edit_event\",\n\n    /**\n     * The user accepted pseudonymous analytics (i.e. posthog) from the toast\n     * Payload: none\n     */\n    PseudonymousAnalyticsAccept = \"pseudonymous_analytics_accept\",\n\n    /**\n     * The user rejected pseudonymous analytics (i.e. posthog) from the toast\n     * Payload: none\n     */\n    PseudonymousAnalyticsReject = \"pseudonymous_analytics_reject\",\n\n    /**\n     * Dispatched after leave room or space is finished\n     */\n    AfterLeaveRoom = \"after_leave_room\",\n\n    /**\n     * Dispatched after a room has been successfully forgotten\n     * Should be used with AfterForgetRoomPayload.\n     */\n    AfterForgetRoom = \"after_forget_room\",\n\n    /**\n     * Used to defer actions until after sync is complete\n     * LifecycleStore will emit deferredAction payload after 'MatrixActions.sync'\n     */\n    DoAfterSyncPrepared = \"do_after_sync_prepared\",\n\n    /**\n     * Fired when clicking user name from group view\n     */\n    ViewStartChatOrReuse = \"view_start_chat_or_reuse\",\n\n    /**\n     * Fired when the user's active room changed, possibly from/to a non-room view.\n     * Payload: ActiveRoomChangedPayload\n     */\n    ActiveRoomChanged = \"active_room_changed\",\n\n    /**\n     * Fired when the forward dialog needs to be opened.\n     * Payload: OpenForwardDialogPayload\n     */\n    OpenForwardDialog = \"open_forward_dialog\",\n\n    /**\n     * Fired when the \"report event\" dialog needs to be opened.\n     * Payload: OpenReportEventDialogPayload.\n     */\n    OpenReportEventDialog = \"open_report_event_dialog\",\n\n    /**\n     * Fired when something within the application has determined that a logout,\n     * or logout-like behaviour, needs to happen. Specifically meant to target\n     * storage deletion rather than calling the logout API.\n     *\n     * No payload.\n     */\n    TriggerLogout = \"trigger_logout\",\n\n    /**\n     * Opens the user's preferences for the given space. Used with a OpenSpacePreferencesPayload.\n     */\n    OpenSpacePreferences = \"open_space_preferences\",\n\n    /**\n     * Opens the settings for the given space. Used with a OpenSpaceSettingsPayload.\n     */\n    OpenSpaceSettings = \"open_space_settings\",\n\n    /**\n     * Opens the invite dialog. Used with a OpenInviteDialogPayload.\n     */\n    OpenInviteDialog = \"open_invite_dialog\",\n\n    /**\n     * Opens a dialog to add an existing object to a space. Used with a OpenAddExistingToSpaceDialogPayload.\n     */\n    OpenAddToExistingSpaceDialog = \"open_add_to_existing_space_dialog\",\n\n    /**\n     * Let components know that they should log any useful debugging information\n     * because we're probably about to send bug report which includes all of the\n     * logs. Fires with no payload.\n     */\n    DumpDebugLogs = \"dump_debug_logs\",\n\n    /**\n     * Show current room topic\n     */\n    ShowRoomTopic = \"show_room_topic\",\n\n    /**\n     * Fired when the client is no longer viable to use: specifically, that we have been \"soft-logged out\".\n     */\n    ClientNotViable = \"client_not_viable\",\n\n    /**\n     * Fired when the client was logged out. No additional payload information required.\n     */\n    OnLoggedOut = \"on_logged_out\",\n\n    /**\n     * Fired when the client was logged in, or has otherwise been set up with authentication data (e.g., by loading the\n     * access token from local storage). Note that this does not necessarily mean that a login action has happened,\n     * just that authentication creds have been set up.\n     *\n     * No additional payload information required.\n     */\n    OnLoggedIn = \"on_logged_in\",\n\n    /**\n     * Fired when the client is about to be started, shortly after {@link OnLoggedIn}.\n     *\n     * No additional payload information required.\n     */\n    WillStartClient = \"will_start_client\",\n\n    /**\n     * Fired when the client has started, shortly after {@link WillStartClient}.\n     *\n     * No additional payload information required.\n     */\n    ClientStarted = \"client_started\",\n\n    /**\n     * Overwrites the existing login with fresh session credentials. Use with a OverwriteLoginPayload.\n     */\n    OverwriteLogin = \"overwrite_login\",\n\n    /**\n     * Fired when we want to view a thread, either a new one or an existing one\n     */\n    ShowThread = \"show_thread\",\n\n    /**\n     * Fired when requesting to prompt for ask to join a room.\n     */\n    PromptAskToJoin = \"prompt_ask_to_join\",\n\n    /**\n     * Fired when requesting to submit an ask to join a room. Use with a SubmitAskToJoinPayload.\n     */\n    SubmitAskToJoin = \"submit_ask_to_join\",\n\n    /**\n     * Fired when requesting to cancel an ask to join a room. Use with a CancelAskToJoinPayload.\n     */\n    CancelAskToJoin = \"cancel_ask_to_join\",\n\n    /**\n     * Fired when we want to open spotlight search. Use with a OpenSpotlightPayload.\n     */\n    OpenSpotlight = \"open_spotlight\",\n\n    /**\n     * Fired when the room loaded.\n     */\n    RoomLoaded = \"room_loaded\",\n\n    /**\n     * Opens right panel with 3pid invite information\n     */\n    View3pidInvite = \"view_3pid_invite\",\n\n    /**\n     * Opens right panel room summary and focuses the search input. Use with a FocusMessageSearchPayload.\n     */\n    FocusMessageSearch = \"focus_search\",\n\n    /**\n     * Open the direct message dialog\n     */\n    CreateChat = \"view_create_chat\",\n\n    /**\n     * Open the create room dialog\n     */\n    CreateRoom = \"view_create_room\",\n\n    /**\n     * The `UserActivity` tracker determined that there was some activity from the user (typically a mouse movement\n     * or keyboard event).\n     */\n    UserActivity = \"user_activity\",\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Action } from \"./actions\";\nimport { type ActionPayload, AsyncActionPayload } from \"./payloads\";\n\ntype DispatchToken = string;\n\nfunction invariant(cond: any, error: string): void {\n    if (!cond) throw new Error(error);\n}\n\n/**\n * A dispatcher for ActionPayloads (the default within the SDK).\n * Based on the old Flux dispatcher https://github.com/facebook/flux/blob/main/src/Dispatcher.js\n */\nexport class MatrixDispatcher {\n    private readonly callbacks = new Map<DispatchToken, (payload: ActionPayload) => void>();\n    private readonly isHandled = new Map<DispatchToken, boolean>();\n    private readonly isPending = new Map<DispatchToken, boolean>();\n    private pendingPayload?: ActionPayload;\n    private lastId = 1;\n\n    /**\n     * Registers a callback to be invoked with every dispatched payload. Returns\n     * a token that can be used with `waitFor()`.\n     */\n    public register(callback: (payload: ActionPayload) => void): DispatchToken {\n        const id = \"ID_\" + this.lastId++;\n        this.callbacks.set(id, callback);\n        if (this.isDispatching()) {\n            // If there is a dispatch happening right now then the newly registered callback should be skipped\n            this.isPending.set(id, true);\n            this.isHandled.set(id, true);\n        }\n        return id;\n    }\n\n    /**\n     * Removes a callback based on its token.\n     * @param id The token that was returned by `register`.\n     * Can be undefined to avoid needing an if around every caller.\n     */\n    public unregister(id: DispatchToken | undefined): void {\n        if (!id) return;\n        invariant(this.callbacks.has(id), `Dispatcher.unregister(...): '${id}' does not map to a registered callback.`);\n        this.callbacks.delete(id);\n    }\n\n    /**\n     * Waits for the callbacks specified to be invoked before continuing execution\n     * of the current callback. This method should only be used by a callback in\n     * response to a dispatched payload.\n     */\n    public waitFor(ids: DispatchToken[]): void {\n        invariant(this.isDispatching(), \"Dispatcher.waitFor(...): Must be invoked while dispatching.\");\n        for (const id of ids) {\n            if (this.isPending.get(id)) {\n                invariant(\n                    this.isHandled.get(id),\n                    `Dispatcher.waitFor(...): Circular dependency detected while waiting for '${id}'.`,\n                );\n                continue;\n            }\n            invariant(\n                this.callbacks.get(id),\n                `Dispatcher.waitFor(...): '${id}' does not map to a registered callback.`,\n            );\n            this.invokeCallback(id);\n        }\n    }\n\n    /**\n     * Dispatches a payload to all registered callbacks.\n     */\n    // eslint-disable-next-line @typescript-eslint/naming-convention\n    private _dispatch = (payload: ActionPayload): void => {\n        invariant(!this.isDispatching(), \"Dispatch.dispatch(...): Cannot dispatch in the middle of a dispatch.\");\n        this.startDispatching(payload);\n        try {\n            for (const [id] of this.callbacks) {\n                if (this.isPending.get(id)) {\n                    continue;\n                }\n                this.invokeCallback(id);\n            }\n        } finally {\n            this.stopDispatching();\n        }\n    };\n\n    /**\n     * Is this Dispatcher currently dispatching.\n     */\n    public isDispatching(): boolean {\n        return !!this.pendingPayload;\n    }\n\n    /**\n     * Call the callback stored with the given id. Also do some internal\n     * bookkeeping.\n     *\n     * Must only be called with an id which has a callback and pendingPayload set\n     * @internal\n     */\n    private invokeCallback(id: DispatchToken): void {\n        this.isPending.set(id, true);\n        this.callbacks.get(id)!(this.pendingPayload!);\n        this.isHandled.set(id, true);\n    }\n\n    /**\n     * Set up bookkeeping needed when dispatching.\n     *\n     * @internal\n     */\n    private startDispatching(payload: ActionPayload): void {\n        for (const [id] of this.callbacks) {\n            this.isPending.set(id, false);\n            this.isHandled.set(id, false);\n        }\n        this.pendingPayload = payload;\n    }\n\n    /**\n     * Clear bookkeeping used for dispatching.\n     *\n     * @internal\n     */\n    private stopDispatching(): void {\n        this.pendingPayload = undefined;\n    }\n\n    /**\n     * Dispatches an event on the dispatcher's event bus.\n     * @param {ActionPayload} payload Required. The payload to dispatch.\n     * @param {boolean=false} sync Optional. Pass true to dispatch\n     *        synchronously. This is useful for anything triggering\n     *        an operation that the browser requires user interaction\n     *        for. Default false (async).\n     */\n    public dispatch<T extends ActionPayload>(payload: T, sync = false): void {\n        if (payload instanceof AsyncActionPayload) {\n            payload.fn((action: ActionPayload) => {\n                this.dispatch(action, sync);\n            });\n            return;\n        }\n\n        if (sync) {\n            this._dispatch(payload);\n        } else {\n            // Unless the caller explicitly asked for us to dispatch synchronously,\n            // we always set a timeout to do this: The flux dispatcher complains\n            // if you dispatch from within a dispatch, so rather than action\n            // handlers having to worry about not calling anything that might\n            // then dispatch, we just do dispatches asynchronously.\n            window.setTimeout(this._dispatch, 0, payload);\n        }\n    }\n\n    /**\n     * Shorthand for dispatch({action: Action.WHATEVER}, sync). No additional\n     * properties can be included with this version.\n     * @param {Action} action The action to dispatch.\n     * @param {boolean=false} sync Whether the dispatch should be sync or not.\n     * @see dispatch(action: ActionPayload, sync: boolean)\n     */\n    public fire(action: Action, sync = false): void {\n        this.dispatch({ action }, sync);\n    }\n}\n\nconst defaultDispatcher = new MatrixDispatcher();\n\nif (!window.mxDispatcher) {\n    window.mxDispatcher = defaultDispatcher;\n}\n\nexport default defaultDispatcher;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type DispatcherAction } from \"./actions\";\n\n/**\n * The base dispatch type exposed by our dispatcher.\n */\nexport interface ActionPayload {\n    [property: string]: any; // effectively makes this 'extends Object'\n    action: DispatcherAction;\n}\n\n/**\n * The function the dispatcher calls when ready for an AsyncActionPayload. The\n * single argument is used to start a dispatch. First the dispatcher calls the\n * outer function, then when the called function is ready it calls the cb\n * function to issue the dispatch. It may call the callback repeatedly if needed.\n */\nexport type AsyncActionFn = (cb: (action: ActionPayload) => void) => void;\n\n/**\n * An async version of ActionPayload\n */\nexport class AsyncActionPayload implements ActionPayload {\n    /**\n     * The function the dispatcher should call.\n     */\n    public readonly fn: AsyncActionFn;\n\n    /**\n     * @deprecated Not used on AsyncActionPayload.\n     */\n    public get action(): DispatcherAction {\n        return \"NOT_USED\";\n    }\n\n    /**\n     * Create a new AsyncActionPayload with the given ready function.\n     * @param {AsyncActionFn} readyFn The function to be called when the\n     * dispatcher is ready.\n     */\n    public constructor(readyFn: AsyncActionFn) {\n        this.fn = readyFn;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ActionPayload } from \"../payloads\";\nimport { type Action } from \"../actions\";\nimport { type TimelineRenderingType } from \"../../contexts/RoomContext\";\n\nexport enum ComposerType {\n    Send = \"send\",\n    Edit = \"edit\",\n}\n\ninterface IBaseComposerInsertPayload extends ActionPayload {\n    action: Action.ComposerInsert;\n    timelineRenderingType: TimelineRenderingType;\n    composerType?: ComposerType; // falsy if should be re-dispatched to the correct composer\n}\n\ninterface IComposerInsertMentionPayload extends IBaseComposerInsertPayload {\n    userId: string;\n}\n\ninterface IComposerInsertPlaintextPayload extends IBaseComposerInsertPayload {\n    text: string;\n}\n\nexport type ComposerInsertPayload = IComposerInsertMentionPayload | IComposerInsertPlaintextPayload;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { type RoomMessageEventContent } from \"matrix-js-sdk/src/types\";\n\nimport type EditorModel from \"./model\";\nimport { Type } from \"./parts\";\nimport { type Command, CommandCategories, getCommand } from \"../slash-commands/SlashCommands\";\nimport { UserFriendlyError, _t, _td } from \"../languageHandler\";\nimport Modal from \"../Modal\";\nimport ErrorDialog from \"../components/views/dialogs/ErrorDialog\";\nimport QuestionDialog from \"../components/views/dialogs/QuestionDialog\";\n\nexport function isSlashCommand(model: EditorModel): boolean {\n    const parts = model.parts;\n    const firstPart = parts[0];\n    if (firstPart) {\n        if (firstPart.type === Type.Command && firstPart.text.startsWith(\"/\") && !firstPart.text.startsWith(\"//\")) {\n            return true;\n        }\n\n        if (\n            firstPart.text.startsWith(\"/\") &&\n            !firstPart.text.startsWith(\"//\") &&\n            (firstPart.type === Type.Plain || firstPart.type === Type.PillCandidate)\n        ) {\n            return true;\n        }\n    }\n    return false;\n}\n\n/**\n * Get the slash command and its arguments from the editor model\n * @param roomId - The room ID to check whether the command is enabled\n * @param model - The editor model\n * @returns A tuple of the command (or undefined if not found), the arguments (or undefined), and the full command text\n */\nexport function getSlashCommand(roomId: string, model: EditorModel): [Command | undefined, string | undefined, string] {\n    const commandText = model.parts.reduce((text, part) => {\n        // use mxid to textify user pills in a command and room alias/id for room pills\n        if (part.type === Type.UserPill || part.type === Type.RoomPill) {\n            return text + part.resourceId;\n        }\n        return text + part.text;\n    }, \"\");\n    const { cmd, args } = getCommand(roomId, commandText);\n    return [cmd, args, commandText];\n}\n\nexport async function runSlashCommand(\n    matrixClient: MatrixClient,\n    cmd: Command,\n    args: string | undefined,\n    roomId: string,\n    threadId: string | null,\n): Promise<[content: RoomMessageEventContent | null, success: boolean]> {\n    const result = cmd.run(matrixClient, roomId, threadId, args);\n    let messageContent: RoomMessageEventContent | null = null;\n    let error: any = result.error;\n    if (result.promise) {\n        try {\n            if (cmd.category === CommandCategories.messages || cmd.category === CommandCategories.effects) {\n                messageContent = (await result.promise) ?? null;\n            } else {\n                await result.promise;\n            }\n        } catch (err) {\n            error = err;\n        }\n    }\n    if (error) {\n        logger.error(`Command failure: ${error}`);\n        // assume the error is a server error when the command is async\n        const isServerError = !!result.promise;\n        const title = isServerError ? _td(\"slash_command|server_error\") : _td(\"slash_command|command_error\");\n\n        let errText;\n        if (typeof error === \"string\") {\n            errText = error;\n        } else if (error instanceof UserFriendlyError) {\n            errText = error.translatedMessage;\n        } else if (error.message) {\n            errText = error.message;\n        } else {\n            errText = _t(\"slash_command|server_error_detail\");\n        }\n\n        Modal.createDialog(ErrorDialog, {\n            title: _t(title),\n            description: errText,\n        });\n        return [null, false];\n    } else {\n        logger.log(\"Command success.\");\n        return [messageContent, true];\n    }\n}\n\nexport async function shouldSendAnyway(commandText: string): Promise<boolean> {\n    // ask the user if their unknown command should be sent as a message\n    const { finished } = Modal.createDialog(QuestionDialog, {\n        title: _t(\"slash_command|unknown_command\"),\n        description: (\n            <div>\n                <p>{_t(\"slash_command|unknown_command_detail\", { commandText })}</p>\n                <p>\n                    {_t(\n                        \"slash_command|unknown_command_help\",\n                        {},\n                        {\n                            code: (t) => <code>{t}</code>,\n                        },\n                    )}\n                </p>\n                <p>\n                    {_t(\n                        \"slash_command|unknown_command_hint\",\n                        {},\n                        {\n                            code: (t) => <code>{t}</code>,\n                        },\n                    )}\n                </p>\n            </div>\n        ),\n        button: _t(\"slash_command|unknown_command_button\"),\n    });\n    const [sendAnyway] = await finished;\n    return sendAnyway || false;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, MsgType } from \"matrix-js-sdk/src/matrix\";\n\nimport { checkBlockNode } from \"../HtmlUtils\";\nimport { getPrimaryPermalinkEntity } from \"../utils/permalinks/Permalinks\";\nimport { type Part, type PartCreator, Type } from \"./parts\";\nimport SdkConfig from \"../SdkConfig\";\nimport { textToHtmlRainbow } from \"../utils/colour\";\nimport { stripPlainReply } from \"../utils/Reply\";\n\nconst LIST_TYPES = [\"UL\", \"OL\", \"LI\"];\n\n// Escapes all markup in the given text\nfunction escape(text: string): string {\n    return text.replace(/[\\\\*_[\\]`<]|^>/g, (match) => `\\\\${match}`);\n}\n\n// Finds the length of the longest backtick sequence in the given text, used for\n// escaping backticks in code blocks\nexport function longestBacktickSequence(text: string): number {\n    let length = 0;\n    let currentLength = 0;\n\n    for (const c of text) {\n        if (c === \"`\") {\n            currentLength++;\n        } else {\n            length = Math.max(length, currentLength);\n            currentLength = 0;\n        }\n    }\n\n    return Math.max(length, currentLength);\n}\n\nfunction isListChild(n: Node): boolean {\n    return LIST_TYPES.includes(n.parentNode?.nodeName || \"\");\n}\n\nfunction parseAtRoomMentions(text: string, pc: PartCreator, opts: IParseOptions): Part[] {\n    const ATROOM = \"@room\";\n    const parts: Part[] = [];\n    text.split(ATROOM).forEach((textPart, i, arr) => {\n        if (textPart.length) {\n            parts.push(...pc.plainWithEmoji(opts.shouldEscape ? escape(textPart) : textPart));\n        }\n        // it's safe to never append @room after the last textPart\n        // as split will report an empty string at the end if\n        // `text` ended in @room.\n        const isLast = i === arr.length - 1;\n        if (!isLast) {\n            parts.push(pc.atRoomPill(ATROOM));\n        }\n    });\n    return parts;\n}\n\nfunction parseLink(n: Node, pc: PartCreator, opts: IParseOptions): Part[] {\n    const { href } = n as HTMLAnchorElement;\n    const resourceId = getPrimaryPermalinkEntity(href); // The room/user ID\n\n    switch (resourceId?.[0]) {\n        case \"@\":\n            return [pc.userPill(n.textContent || \"\", resourceId)];\n        case \"#\":\n            return [pc.roomPill(resourceId)];\n    }\n\n    const children = Array.from(n.childNodes);\n    if (href === n.textContent && children.every((c) => c.nodeType === Node.TEXT_NODE)) {\n        return parseAtRoomMentions(n.textContent, pc, opts);\n    } else {\n        return [pc.plain(\"[\"), ...parseChildren(n, pc, opts), pc.plain(`](${href})`)];\n    }\n}\n\nfunction parseImage(n: Node, pc: PartCreator, opts: IParseOptions): Part[] {\n    const { alt, src } = n as HTMLImageElement;\n    return pc.plainWithEmoji(`![${escape(alt)}](${src})`);\n}\n\nfunction parseCodeBlock(n: Node, pc: PartCreator, opts: IParseOptions): Part[] {\n    if (!n.textContent) return [];\n\n    let language = \"\";\n    if (n.firstChild?.nodeName === \"CODE\") {\n        for (const className of (n.firstChild as HTMLElement).classList) {\n            if (className.startsWith(\"language-\") && !className.startsWith(\"language-_\")) {\n                language = className.slice(\"language-\".length);\n                break;\n            }\n        }\n    }\n\n    const text = n.textContent.replace(/\\n$/, \"\");\n    // Escape backticks by using even more backticks for the fence if necessary\n    const fence = \"`\".repeat(Math.max(3, longestBacktickSequence(text) + 1));\n    const parts: Part[] = [...pc.plainWithEmoji(fence + language), pc.newline()];\n\n    text.split(\"\\n\").forEach((line) => {\n        parts.push(...pc.plainWithEmoji(line));\n        parts.push(pc.newline());\n    });\n\n    parts.push(pc.plain(fence));\n    return parts;\n}\n\nfunction parseHeader(n: Node, pc: PartCreator, opts: IParseOptions): Part[] {\n    const depth = parseInt(n.nodeName.slice(1), 10);\n    const prefix = pc.plain(\"#\".repeat(depth) + \" \");\n    return [prefix, ...parseChildren(n, pc, opts)];\n}\n\nfunction checkIgnored(n: Node): boolean {\n    if (n.nodeType === Node.TEXT_NODE) {\n        // Element adds \\n text nodes in a lot of places,\n        // which should be ignored\n        return n.nodeValue === \"\\n\";\n    } else if (n.nodeType === Node.ELEMENT_NODE) {\n        return n.nodeName === \"MX-REPLY\";\n    }\n    return true;\n}\n\nfunction prefixLines(parts: Part[], prefix: string, pc: PartCreator): void {\n    parts.unshift(pc.plain(prefix));\n    for (let i = 0; i < parts.length; i++) {\n        if (parts[i].type === Type.Newline) {\n            parts.splice(i + 1, 0, pc.plain(prefix));\n            i += 1;\n        }\n    }\n}\n\nfunction parseChildren(n: Node, pc: PartCreator, opts: IParseOptions, mkListItem?: (li: Node) => Part[]): Part[] {\n    let prev: ChildNode | undefined;\n    return Array.from(n.childNodes).flatMap((c) => {\n        const parsed = parseNode(c, pc, opts, mkListItem);\n        if (parsed.length && prev && (checkBlockNode(prev) || checkBlockNode(c))) {\n            if (isListChild(c)) {\n                // Use tighter spacing within lists\n                parsed.unshift(pc.newline());\n            } else {\n                parsed.unshift(pc.newline(), pc.newline());\n            }\n        }\n        if (parsed.length) prev = c;\n        return parsed;\n    });\n}\n\nfunction parseNode(n: Node, pc: PartCreator, opts: IParseOptions, mkListItem?: (li: Node) => Part[]): Part[] {\n    if (checkIgnored(n)) return [];\n\n    switch (n.nodeType) {\n        case Node.TEXT_NODE:\n            return parseAtRoomMentions(n.nodeValue || \"\", pc, opts);\n        case Node.ELEMENT_NODE:\n            switch (n.nodeName) {\n                case \"H1\":\n                case \"H2\":\n                case \"H3\":\n                case \"H4\":\n                case \"H5\":\n                case \"H6\":\n                    return parseHeader(n, pc, opts);\n                case \"A\":\n                    return parseLink(n, pc, opts);\n                case \"IMG\":\n                    return parseImage(n, pc, opts);\n                case \"BR\":\n                    return [pc.newline()];\n                case \"HR\":\n                    return [pc.plain(\"---\")];\n                case \"EM\":\n                    return [pc.plain(\"_\"), ...parseChildren(n, pc, opts), pc.plain(\"_\")];\n                case \"STRONG\":\n                    return [pc.plain(\"**\"), ...parseChildren(n, pc, opts), pc.plain(\"**\")];\n                case \"DEL\":\n                    return [pc.plain(\"<del>\"), ...parseChildren(n, pc, opts), pc.plain(\"</del>\")];\n                case \"S\":\n                    return [pc.plain(\"<s>\"), ...parseChildren(n, pc, opts), pc.plain(\"</s>\")];\n                case \"SUB\":\n                    return [pc.plain(\"<sub>\"), ...parseChildren(n, pc, opts), pc.plain(\"</sub>\")];\n                case \"SUP\":\n                    return [pc.plain(\"<sup>\"), ...parseChildren(n, pc, opts), pc.plain(\"</sup>\")];\n                case \"U\":\n                    return [pc.plain(\"<u>\"), ...parseChildren(n, pc, opts), pc.plain(\"</u>\")];\n                case \"PRE\":\n                    return parseCodeBlock(n, pc, opts);\n                case \"CODE\": {\n                    // Escape backticks by using multiple backticks for the fence if necessary\n                    const fence = \"`\".repeat(longestBacktickSequence(n.textContent || \"\") + 1);\n                    return pc.plainWithEmoji(`${fence}${n.textContent}${fence}`);\n                }\n                case \"BLOCKQUOTE\": {\n                    const parts = parseChildren(n, pc, opts);\n                    prefixLines(parts, \"> \", pc);\n                    return parts;\n                }\n                case \"LI\":\n                    return mkListItem?.(n) ?? parseChildren(n, pc, opts);\n                case \"UL\": {\n                    const parts = parseChildren(n, pc, opts, (li) => [pc.plain(\"- \"), ...parseChildren(li, pc, opts)]);\n                    if (isListChild(n)) {\n                        prefixLines(parts, \"    \", pc);\n                    }\n                    return parts;\n                }\n                case \"OL\": {\n                    let counter = (n as HTMLOListElement).start ?? 1;\n                    const parts = parseChildren(n, pc, opts, (li) => {\n                        const parts = [pc.plain(`${counter}. `), ...parseChildren(li, pc, opts)];\n                        counter++;\n                        return parts;\n                    });\n                    if (isListChild(n)) {\n                        prefixLines(parts, \"    \", pc);\n                    }\n                    return parts;\n                }\n                case \"DIV\":\n                case \"SPAN\":\n                    // Math nodes are translated back into delimited latex strings\n                    if ((n as Element).hasAttribute(\"data-mx-maths\")) {\n                        const delims = SdkConfig.get().latex_maths_delims;\n                        const delimLeft =\n                            n.nodeName === \"SPAN\" ? (delims?.inline?.left ?? \"\\\\(\") : (delims?.display?.left ?? \"\\\\[\");\n                        const delimRight =\n                            n.nodeName === \"SPAN\"\n                                ? (delims?.inline?.right ?? \"\\\\)\")\n                                : (delims?.display?.right ?? \"\\\\]\");\n                        const tex = (n as Element).getAttribute(\"data-mx-maths\");\n\n                        return pc.plainWithEmoji(`${delimLeft}${tex}${delimRight}`);\n                    }\n                    // Spoilers are translated back into their slash command form\n                    else if ((n as Element).hasAttribute(\"data-mx-spoiler\")) {\n                        return [pc.plain(\"/spoiler \"), ...parseChildren(n, pc, opts)];\n                    }\n            }\n    }\n\n    return parseChildren(n, pc, opts);\n}\n\ninterface IParseOptions {\n    isQuotedMessage?: boolean;\n    shouldEscape?: boolean;\n}\n\nfunction parseHtmlMessage(html: string, pc: PartCreator, opts: IParseOptions): Part[] {\n    // no nodes from parsing here should be inserted in the document,\n    // as scripts in event handlers, etc would be executed then.\n    // we're only taking text, so that is fine\n    const parts = parseNode(new DOMParser().parseFromString(html, \"text/html\").body, pc, opts);\n    if (opts.isQuotedMessage) {\n        prefixLines(parts, \"> \", pc);\n    }\n    return parts;\n}\n\nexport function parsePlainTextMessage(body: string, pc: PartCreator, opts: IParseOptions): Part[] {\n    const lines = body.split(/\\r\\n|\\r|\\n/g); // split on any new-line combination not just \\n, collapses \\r\\n\n    return lines.reduce((parts, line, i) => {\n        if (opts.isQuotedMessage) {\n            parts.push(pc.plain(\"> \"));\n        }\n        parts.push(...parseAtRoomMentions(line, pc, opts));\n        const isLast = i === lines.length - 1;\n        if (!isLast) {\n            parts.push(pc.newline());\n        }\n        return parts;\n    }, [] as Part[]);\n}\n\nexport function parseEvent(event: MatrixEvent, pc: PartCreator, opts: IParseOptions = { shouldEscape: true }): Part[] {\n    const content = event.getContent();\n    let parts: Part[];\n    const isEmote = content.msgtype === MsgType.Emote;\n    let isRainbow = false;\n\n    if (content.format === \"org.matrix.custom.html\") {\n        parts = parseHtmlMessage(content.formatted_body || \"\", pc, opts);\n        if (content.body && content.formatted_body && textToHtmlRainbow(content.body) === content.formatted_body) {\n            isRainbow = true;\n        }\n    } else {\n        let body = content.body || \"\";\n        if (event.replyEventId) {\n            body = stripPlainReply(body);\n        }\n        parts = parsePlainTextMessage(body, pc, opts);\n    }\n\n    if (isEmote && isRainbow) {\n        parts.unshift(pc.plain(\"/rainbowme \"));\n    } else if (isRainbow) {\n        parts.unshift(pc.plain(\"/rainbow \"));\n    } else if (isEmote) {\n        parts.unshift(pc.plain(\"/me \"));\n    }\n\n    return parts;\n}\n","/*\nCopyright 2019-2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { CARET_NODE_CHAR, isCaretNode } from \"./render\";\nimport DocumentOffset from \"./offset\";\nimport type EditorModel from \"./model\";\nimport type Range from \"./range\";\n\ntype Predicate = (node: Node) => boolean;\ntype Callback = (node: Node) => void;\n\nexport function walkDOMDepthFirst(rootNode: Node, enterNodeCallback: Predicate, leaveNodeCallback: Callback): void {\n    let node = rootNode.firstChild;\n    while (node && node !== rootNode) {\n        const shouldDescend = enterNodeCallback(node);\n        if (shouldDescend && node.firstChild) {\n            node = node.firstChild;\n        } else if (node.nextSibling) {\n            node = node.nextSibling;\n        } else {\n            while (node && !node.nextSibling && node !== rootNode) {\n                node = node.parentElement;\n                if (node && node !== rootNode) {\n                    leaveNodeCallback(node);\n                }\n            }\n            if (node && node !== rootNode) {\n                node = node.nextSibling;\n            }\n        }\n    }\n}\n\nexport function getCaretOffsetAndText(\n    editor: HTMLDivElement,\n    sel: Selection,\n): {\n    caret: DocumentOffset;\n    text: string;\n} {\n    const { offset, text } = getSelectionOffsetAndText(editor, sel.focusNode, sel.focusOffset);\n    return { caret: offset, text };\n}\n\nfunction tryReduceSelectionToTextNode(\n    selectionNode: Node | null,\n    selectionOffset: number,\n): {\n    node: Node | null;\n    characterOffset: number;\n} {\n    // if selectionNode is an element, the selected location comes after the selectionOffset-th child node,\n    // which can point past any childNode, in which case, the end of selectionNode is selected.\n    // we try to simplify this to point at a text node with the offset being\n    // a character offset within the text node\n    // Also see https://developer.mozilla.org/en-US/docs/Web/API/Selection\n    while (selectionNode && selectionNode.nodeType === Node.ELEMENT_NODE) {\n        const childNodeCount = selectionNode.childNodes.length;\n        if (childNodeCount) {\n            if (selectionOffset >= childNodeCount) {\n                selectionNode = selectionNode.lastChild;\n                if (selectionNode?.nodeType === Node.TEXT_NODE) {\n                    selectionOffset = selectionNode.textContent?.length || 0;\n                } else {\n                    // this will select the last child node in the next iteration\n                    selectionOffset = Number.MAX_SAFE_INTEGER;\n                }\n            } else {\n                selectionNode = selectionNode.childNodes[selectionOffset];\n                // this will select the first child node in the next iteration\n                selectionOffset = 0;\n            }\n        } else {\n            // here node won't be a text node,\n            // but characterOffset should be 0,\n            // this happens under some circumstances\n            // when the editor is empty.\n            // In this case characterOffset=0 is the right thing to do\n            break;\n        }\n    }\n    return {\n        node: selectionNode,\n        characterOffset: selectionOffset,\n    };\n}\n\nfunction getSelectionOffsetAndText(\n    editor: HTMLDivElement,\n    selectionNode: Node | null,\n    selectionOffset: number,\n): {\n    offset: DocumentOffset;\n    text: string;\n} {\n    const { node, characterOffset } = tryReduceSelectionToTextNode(selectionNode, selectionOffset);\n    const { text, offsetToNode } = getTextAndOffsetToNode(editor, node);\n    const offset = getCaret(node, offsetToNode, characterOffset);\n    return { offset, text };\n}\n\n// gets the caret position details, ignoring and adjusting to\n// the ZWS if you're typing in a caret node\nfunction getCaret(node: Node | null, offsetToNode: number, offsetWithinNode: number): DocumentOffset {\n    // if no node is selected, return an offset at the start\n    if (!node) {\n        return new DocumentOffset(0, false);\n    }\n    let atNodeEnd = offsetWithinNode === node.textContent?.length;\n    if (node.nodeType === Node.TEXT_NODE && isCaretNode(node.parentElement)) {\n        const nodeValue = node.nodeValue || \"\";\n        const zwsIdx = nodeValue.indexOf(CARET_NODE_CHAR);\n        if (zwsIdx !== -1 && zwsIdx < offsetWithinNode) {\n            offsetWithinNode -= 1;\n        }\n        // if typing in a caret node, you're either typing before or after the ZWS.\n        // In both cases, you should be considered at node end because the ZWS is\n        // not included in the text here, and once the model is updated and rerendered,\n        // that caret node will be removed.\n        atNodeEnd = true;\n    }\n    return new DocumentOffset(offsetToNode + offsetWithinNode, atNodeEnd);\n}\n\n// gets the text of the editor as a string,\n// and the offset in characters where the selectionNode starts in that string\n// all ZWS from caret nodes are filtered out\nfunction getTextAndOffsetToNode(\n    editor: HTMLDivElement,\n    selectionNode: Node | null,\n): { offsetToNode: number; text: string } {\n    let offsetToNode = 0;\n    let foundNode = false;\n    let text = \"\";\n\n    function enterNodeCallback(node: Node): boolean {\n        if (!foundNode) {\n            if (node === selectionNode) {\n                foundNode = true;\n            }\n        }\n        // usually newlines are entered as new DIV elements,\n        // but for example while pasting in some browsers, they are still\n        // converted to BRs, so also take these into account when they\n        // are not the last element in the DIV.\n        if (node instanceof HTMLElement && node.tagName === \"BR\" && node.nextSibling) {\n            if (!foundNode) {\n                offsetToNode += 1;\n            }\n            text += \"\\n\";\n        }\n        const nodeText = node.nodeType === Node.TEXT_NODE && getTextNodeValue(node);\n        if (nodeText) {\n            if (!foundNode) {\n                offsetToNode += nodeText.length;\n            }\n            text += nodeText;\n        }\n        return true;\n    }\n\n    function leaveNodeCallback(node: Node): void {\n        // if this is not the last DIV (which are only used as line containers atm)\n        // we don't just check if there is a nextSibling because sometimes the caret ends up\n        // after the last DIV and it creates a newline if you type then,\n        // whereas you just want it to be appended to the current line\n        if (\n            node instanceof HTMLElement &&\n            node.tagName === \"DIV\" &&\n            (<HTMLElement>node.nextSibling)?.tagName === \"DIV\"\n        ) {\n            text += \"\\n\";\n            if (!foundNode) {\n                offsetToNode += 1;\n            }\n        }\n    }\n\n    walkDOMDepthFirst(editor, enterNodeCallback, leaveNodeCallback);\n\n    return { text, offsetToNode };\n}\n\n// get text value of text node, ignoring ZWS if it's a caret node\nfunction getTextNodeValue(node: Node): string {\n    const nodeText = node.nodeValue;\n    if (!nodeText) return \"\";\n\n    // filter out ZWS for caret nodes\n    if (isCaretNode(node.parentElement)) {\n        // typed in the caret node, so there is now something more in it than the ZWS\n        // so filter out the ZWS, and take the typed text into account\n        if (nodeText.length !== 1) {\n            return nodeText.replace(CARET_NODE_CHAR, \"\");\n        } else {\n            // only contains ZWS, which is ignored, so return empty string\n            return \"\";\n        }\n    }\n\n    return nodeText;\n}\n\nexport function getRangeForSelection(editor: HTMLDivElement, model: EditorModel, selection: Selection): Range {\n    const focusOffset = getSelectionOffsetAndText(editor, selection.focusNode, selection.focusOffset).offset;\n    const anchorOffset = getSelectionOffsetAndText(editor, selection.anchorNode, selection.anchorOffset).offset;\n    const focusPosition = focusOffset.asPosition(model);\n    const anchorPosition = anchorOffset.asPosition(model);\n    return model.startRange(focusPosition, anchorPosition);\n}\n","/*\nCopyright 2019-2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport interface IDiff {\n    removed?: string;\n    added?: string;\n    at?: number;\n}\n\nfunction firstDiff(a: string, b: string): number {\n    const compareLen = Math.min(a.length, b.length);\n    for (let i = 0; i < compareLen; ++i) {\n        if (a[i] !== b[i]) {\n            return i;\n        }\n    }\n    return compareLen;\n}\n\nfunction diffStringsAtEnd(oldStr: string, newStr: string): IDiff {\n    const len = Math.min(oldStr.length, newStr.length);\n    const startInCommon = oldStr.slice(0, len) === newStr.slice(0, len);\n    if (startInCommon && oldStr.length > newStr.length) {\n        return { removed: oldStr.slice(len), at: len };\n    } else if (startInCommon && oldStr.length < newStr.length) {\n        return { added: newStr.slice(len), at: len };\n    } else {\n        const commonStartLen = firstDiff(oldStr, newStr);\n        return {\n            removed: oldStr.slice(commonStartLen),\n            added: newStr.slice(commonStartLen),\n            at: commonStartLen,\n        };\n    }\n}\n\n// assumes only characters have been deleted at one location in the string, and none added\nexport function diffDeletion(oldStr: string, newStr: string): IDiff {\n    if (oldStr === newStr) {\n        return {};\n    }\n    const firstDiffIdx = firstDiff(oldStr, newStr);\n    const amount = oldStr.length - newStr.length;\n    return { at: firstDiffIdx, removed: oldStr.slice(firstDiffIdx, firstDiffIdx + amount) };\n}\n\n/**\n * Calculates which string was added and removed around the caret position\n * @param {String} oldValue the previous value\n * @param {String} newValue the new value\n * @param {Number} caretPosition the position of the caret after `newValue` was applied.\n * @return {object} an object with `at` as the offset where characters were removed and/or added,\n *                  `added` with the added string (if any), and\n *                  `removed` with the removed string (if any)\n */\nexport function diffAtCaret(oldValue: string, newValue: string, caretPosition: number): IDiff {\n    const diffLen = newValue.length - oldValue.length;\n    const caretPositionBeforeInput = caretPosition - diffLen;\n    const oldValueBeforeCaret = oldValue.substring(0, caretPositionBeforeInput);\n    const newValueBeforeCaret = newValue.substring(0, caretPosition);\n    return diffStringsAtEnd(oldValueBeforeCaret, newValueBeforeCaret);\n}\n","/*\nCopyright 2019-2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { diffAtCaret, diffDeletion, type IDiff } from \"./diff\";\nimport DocumentPosition, { type IPosition } from \"./position\";\nimport Range from \"./range\";\nimport { type SerializedPart, type Part, type PartCreator } from \"./parts\";\nimport { type ICallback } from \"./autocomplete\";\nimport type AutocompleteWrapperModel from \"./autocomplete\";\nimport type DocumentOffset from \"./offset\";\nimport { type Caret } from \"./caret\";\n\n/**\n * @callback ModelCallback\n * @param {DocumentPosition?} caretPosition the position where the caret should be position\n * @param {string?} inputType the inputType of the DOM input event\n * @param {object?} diff an object with `removed` and `added` strings\n */\n\n/**\n * @callback TransformCallback\n * @param {DocumentPosition?} caretPosition the position where the caret should be position\n * @param {string?} inputType the inputType of the DOM input event\n * @param {object?} diff an object with `removed` and `added` strings\n * @return {Number?} addedLen how many characters were added/removed (-) before the caret during the transformation step.\n *    This is used to adjust the caret position.\n */\n\n/**\n * @callback ManualTransformCallback\n * @return the caret position\n */\n\ntype TransformCallback = (caretPosition: DocumentPosition, inputType: string | undefined, diff: IDiff) => number | void;\ntype UpdateCallback = (caret?: Caret, inputType?: string, diff?: IDiff) => void;\ntype ManualTransformCallback = () => Caret;\n\nexport default class EditorModel {\n    private _parts: Part[];\n    private readonly _partCreator: PartCreator;\n    private activePartIdx: number | null = null;\n    private _autoComplete: AutocompleteWrapperModel | null = null;\n    private autoCompletePartIdx: number | null = null;\n    private autoCompletePartCount = 0;\n    private transformCallback: TransformCallback | null = null;\n\n    public constructor(\n        parts: Part[],\n        partCreator: PartCreator,\n        private updateCallback: UpdateCallback | null = null,\n    ) {\n        this._parts = parts;\n        this._partCreator = partCreator;\n        this.transformCallback = null;\n    }\n\n    /**\n     * Set a callback for the transformation step.\n     * While processing an update, right before calling the update callback,\n     * a transform callback can be called, which serves to do modifications\n     * on the model that can span multiple parts. Also see `startRange()`.\n     * @param {TransformCallback} transformCallback\n     */\n    public setTransformCallback(transformCallback: TransformCallback): void {\n        this.transformCallback = transformCallback;\n    }\n\n    /**\n     * Set a callback for rerendering the model after it has been updated.\n     * @param {ModelCallback} updateCallback\n     */\n    public setUpdateCallback(updateCallback: UpdateCallback): void {\n        this.updateCallback = updateCallback;\n    }\n\n    public get partCreator(): PartCreator {\n        return this._partCreator;\n    }\n\n    public get isEmpty(): boolean {\n        return this._parts.reduce((len, part) => len + part.text.length, 0) === 0;\n    }\n\n    public clone(): EditorModel {\n        const clonedParts = this.parts\n            .map((p) => this.partCreator.deserializePart(p.serialize()))\n            .filter((p): p is Part => Boolean(p));\n        return new EditorModel(clonedParts, this._partCreator, this.updateCallback);\n    }\n\n    private insertPart(index: number, part: Part): void {\n        this._parts.splice(index, 0, part);\n        if (this.activePartIdx !== null && this.activePartIdx >= index) {\n            ++this.activePartIdx;\n        }\n        if (this.autoCompletePartIdx !== null && this.autoCompletePartIdx >= index) {\n            ++this.autoCompletePartIdx;\n        }\n    }\n\n    private removePart(index: number): void {\n        this._parts.splice(index, 1);\n        if (index === this.activePartIdx) {\n            this.activePartIdx = null;\n        } else if (this.activePartIdx !== null && this.activePartIdx > index) {\n            --this.activePartIdx;\n        }\n        if (index === this.autoCompletePartIdx) {\n            this.autoCompletePartIdx = null;\n        } else if (this.autoCompletePartIdx !== null && this.autoCompletePartIdx > index) {\n            --this.autoCompletePartIdx;\n        }\n    }\n\n    private replacePart(index: number, part: Part): void {\n        this._parts.splice(index, 1, part);\n    }\n\n    public get parts(): Part[] {\n        return this._parts;\n    }\n\n    public get autoComplete(): AutocompleteWrapperModel | null {\n        if (this.activePartIdx === this.autoCompletePartIdx) {\n            return this._autoComplete;\n        }\n        return null;\n    }\n\n    public getPositionAtEnd(): DocumentPosition {\n        if (this._parts.length) {\n            const index = this._parts.length - 1;\n            const part = this._parts[index];\n            return new DocumentPosition(index, part.text.length);\n        } else {\n            // part index -1, as there are no parts to point at\n            return new DocumentPosition(-1, 0);\n        }\n    }\n\n    public serializeParts(): SerializedPart[] {\n        return this._parts.map((p) => p.serialize());\n    }\n\n    private diff(newValue: string, inputType: string | undefined, caret: DocumentOffset): IDiff {\n        const previousValue = this.parts.reduce((text, p) => text + p.text, \"\");\n        // can't use caret position with drag and drop\n        if (inputType === \"deleteByDrag\") {\n            return diffDeletion(previousValue, newValue);\n        } else {\n            return diffAtCaret(previousValue, newValue, caret.offset);\n        }\n    }\n\n    public reset(serializedParts: SerializedPart[], caret?: Caret, inputType?: string): void {\n        this._parts = serializedParts\n            .map((p) => this._partCreator.deserializePart(p))\n            .filter((p): p is Part => Boolean(p));\n        if (!caret) {\n            caret = this.getPositionAtEnd();\n        }\n        // close auto complete if open\n        // this would happen when clearing the composer after sending\n        // a message with the autocomplete still open\n        if (this._autoComplete) {\n            this._autoComplete = null;\n            this.autoCompletePartIdx = null;\n        }\n        this.updateCallback?.(caret, inputType);\n    }\n\n    /**\n     * Inserts the given parts at the given position.\n     * Should be run inside a `model.transform()` callback.\n     * @param {Part[]} parts the parts to replace the range with\n     * @param {DocumentPosition} position the position to start inserting at\n     * @return {Number} the amount of characters added\n     */\n    public insert(parts: Part[], position: IPosition): number {\n        const insertIndex = this.splitAt(position);\n        let newTextLength = 0;\n        for (let i = 0; i < parts.length; ++i) {\n            const part = parts[i];\n            newTextLength += part.text.length;\n            this.insertPart(insertIndex + i, part);\n        }\n        return newTextLength;\n    }\n\n    public update(newValue: string, inputType: string | undefined, caret: DocumentOffset): Promise<void> {\n        const diff = this.diff(newValue, inputType, caret);\n        const position = this.positionForOffset(diff.at || 0, caret.atNodeEnd);\n        let removedOffsetDecrease = 0;\n        if (diff.removed) {\n            removedOffsetDecrease = this.removeText(position, diff.removed.length);\n        }\n        let addedLen = 0;\n        if (diff.added) {\n            addedLen = this.addText(position, diff.added, inputType);\n        }\n        this.mergeAdjacentParts();\n        const caretOffset = (diff.at || 0) - removedOffsetDecrease + addedLen;\n        let newPosition = this.positionForOffset(caretOffset, true);\n        const canOpenAutoComplete = inputType !== \"insertFromPaste\" && inputType !== \"insertFromDrop\";\n        const acPromise = this.setActivePart(newPosition, canOpenAutoComplete);\n        if (this.transformCallback) {\n            const transformAddedLen = this.getTransformAddedLen(newPosition, inputType, diff);\n            newPosition = this.positionForOffset(caretOffset + transformAddedLen, true);\n        }\n        this.updateCallback?.(newPosition, inputType, diff);\n        return acPromise;\n    }\n\n    private getTransformAddedLen(newPosition: DocumentPosition, inputType: string | undefined, diff: IDiff): number {\n        const result = this.transformCallback?.(newPosition, inputType, diff);\n        return Number.isFinite(result) ? (result as number) : 0;\n    }\n\n    private setActivePart(pos: DocumentPosition, canOpenAutoComplete: boolean): Promise<void> {\n        const { index } = pos;\n        const part = this._parts[index];\n        if (part) {\n            if (index !== this.activePartIdx) {\n                this.activePartIdx = index;\n                if (canOpenAutoComplete && this.activePartIdx !== this.autoCompletePartIdx) {\n                    // else try to create one\n                    const ac = part.createAutoComplete(this.onAutoComplete);\n                    if (ac) {\n                        // make sure that react picks up the difference between both acs\n                        this._autoComplete = ac;\n                        this.autoCompletePartIdx = index;\n                        this.autoCompletePartCount = 1;\n                    }\n                }\n            }\n            // not autoComplete, only there if active part is autocomplete part\n            if (this.autoComplete) {\n                return this.autoComplete.onPartUpdate(part, pos);\n            }\n        } else {\n            this.activePartIdx = null;\n            this._autoComplete = null;\n            this.autoCompletePartIdx = null;\n            this.autoCompletePartCount = 0;\n        }\n        return Promise.resolve();\n    }\n\n    private onAutoComplete = ({ replaceParts, close, range }: ICallback): void => {\n        let pos: DocumentPosition | undefined;\n        if (replaceParts) {\n            const autoCompletePartIdx = this.autoCompletePartIdx || 0;\n\n            this.replaceRange(\n                new DocumentPosition(autoCompletePartIdx, range?.start ?? 0),\n                new DocumentPosition(\n                    autoCompletePartIdx + this.autoCompletePartCount - 1,\n                    range?.end ?? this.parts[autoCompletePartIdx + this.autoCompletePartCount - 1].text.length,\n                ),\n                replaceParts,\n            );\n\n            this.autoCompletePartCount = replaceParts.length;\n            const lastPart = replaceParts[replaceParts.length - 1];\n            // `replaceRange` merges adjacent parts so we need to find it in the new parts list\n            const lastPartIndex = this.parts.indexOf(lastPart);\n            pos = new DocumentPosition(lastPartIndex, lastPart.text.length);\n        }\n        if (close) {\n            this._autoComplete = null;\n            this.autoCompletePartIdx = null;\n            this.autoCompletePartCount = 0;\n        }\n        // rerender even if editor contents didn't change\n        // to make sure the MessageEditor checks\n        // model.autoComplete being empty and closes it\n        this.updateCallback?.(pos);\n    };\n\n    private mergeAdjacentParts(): void {\n        let prevPart: Part | undefined;\n        for (let i = 0; i < this._parts.length; ++i) {\n            let part: Part | undefined = this._parts[i];\n            const isEmpty = !part.text.length;\n            const isMerged = !isEmpty && prevPart && prevPart.merge?.(part);\n            if (isEmpty || isMerged) {\n                // remove empty or merged part\n                part = prevPart;\n                this.removePart(i);\n                //repeat this index, as it's removed now\n                --i;\n            }\n            prevPart = part;\n        }\n    }\n\n    /**\n     * removes `len` amount of characters at `pos`.\n     * @param {Object} pos\n     * @param {Number} len\n     * @return {Number} how many characters before pos were also removed,\n     * usually because of non-editable parts that can only be removed in their entirety.\n     */\n    public removeText(pos: IPosition, len: number): number {\n        let { index, offset } = pos;\n        let removedOffsetDecrease = 0;\n        while (len > 0) {\n            // part might be undefined here\n            let part = this._parts[index];\n            const amount = Math.min(len, part.text.length - offset);\n            // don't allow 0 amount deletions\n            if (amount) {\n                if (part.canEdit) {\n                    const replaceWith = part.remove(offset, amount);\n                    if (typeof replaceWith === \"string\") {\n                        this.replacePart(index, this._partCreator.createDefaultPart(replaceWith));\n                    }\n                    part = this._parts[index];\n                    // remove empty part\n                    if (!part.text.length) {\n                        this.removePart(index);\n                    } else {\n                        index += 1;\n                    }\n                } else {\n                    removedOffsetDecrease += offset;\n                    this.removePart(index);\n                }\n            } else {\n                index += 1;\n            }\n            len -= amount;\n            offset = 0;\n        }\n        return removedOffsetDecrease;\n    }\n\n    // return part index where insertion will insert between at offset\n    private splitAt(pos: IPosition): number {\n        if (pos.index === -1) {\n            return 0;\n        }\n        if (pos.offset === 0) {\n            return pos.index;\n        }\n        const part = this._parts[pos.index];\n        if (pos.offset >= part.text.length) {\n            return pos.index + 1;\n        }\n\n        const secondPart = part.split(pos.offset);\n        this.insertPart(pos.index + 1, secondPart);\n        return pos.index + 1;\n    }\n\n    /**\n     * inserts `str` into the model at `pos`.\n     * @param {Object} pos\n     * @param {string} str\n     * @param {string} inputType the source of the input, see html InputEvent.inputType\n     * @return {Number} how far from position (in characters) the insertion ended.\n     * This can be more than the length of `str` when crossing non-editable parts, which are skipped.\n     */\n    private addText(pos: IPosition, str: string, inputType: string | undefined): number {\n        let { index } = pos;\n        const { offset } = pos;\n        let addLen = str.length;\n        const part = this._parts[index];\n\n        let it: string | undefined = str;\n\n        if (part) {\n            if (part.canEdit) {\n                if (part.validateAndInsert(offset, str, inputType)) {\n                    it = undefined;\n                } else {\n                    const splitPart = part.split(offset);\n                    index += 1;\n                    this.insertPart(index, splitPart);\n                }\n            } else if (offset !== 0) {\n                // not-editable part, caret is not at start,\n                // so insert str after this part\n                addLen += part.text.length - offset;\n                index += 1;\n            }\n        } else if (index < 0) {\n            // if position was not found (index: -1, as happens for empty editor)\n            // reset it to insert as first part\n            index = 0;\n        }\n\n        while (it) {\n            const newPart = this._partCreator.createPartForInput(it, index, inputType);\n            const oldStr = it;\n            it = newPart.appendUntilRejected(it, inputType);\n            if (it === oldStr) {\n                // nothing changed, break out of this infinite loop and log an error\n                console.error(`Failed to update model for input (str ${it}) (type ${inputType})`);\n                break;\n            }\n            this.insertPart(index, newPart);\n            index += 1;\n        }\n        return addLen;\n    }\n\n    public positionForOffset(totalOffset: number, atPartEnd = false): DocumentPosition {\n        let currentOffset = 0;\n        const index = this._parts.findIndex((part) => {\n            const partLen = part.text.length;\n            if (\n                (atPartEnd && currentOffset + partLen >= totalOffset) ||\n                (!atPartEnd && currentOffset + partLen > totalOffset)\n            ) {\n                return true;\n            }\n            currentOffset += partLen;\n            return false;\n        });\n        if (index === -1) {\n            return this.getPositionAtEnd();\n        } else {\n            return new DocumentPosition(index, totalOffset - currentOffset);\n        }\n    }\n\n    /**\n     * Starts a range, which can span across multiple parts, to find and replace text.\n     * @param {DocumentPosition} positionA a boundary of the range\n     * @param {DocumentPosition?} positionB the other boundary of the range, optional\n     * @return {Range}\n     */\n    public startRange(positionA: DocumentPosition, positionB = positionA): Range {\n        return new Range(this, positionA, positionB);\n    }\n\n    public replaceRange(startPosition: DocumentPosition, endPosition: DocumentPosition, parts: Part[]): void {\n        // convert end position to offset, so it is independent of how the document is split into parts\n        // which we'll change when splitting up at the start position\n        const endOffset = endPosition.asOffset(this);\n        const newStartPartIndex = this.splitAt(startPosition);\n        // convert it back to position once split at start\n        endPosition = endOffset.asPosition(this);\n        const newEndPartIndex = this.splitAt(endPosition);\n        for (let i = newEndPartIndex - 1; i >= newStartPartIndex; --i) {\n            this.removePart(i);\n        }\n        let insertIdx = newStartPartIndex;\n        for (const part of parts) {\n            this.insertPart(insertIdx, part);\n            insertIdx += 1;\n        }\n        this.mergeAdjacentParts();\n    }\n\n    /**\n     * Performs a transformation not part of an update cycle.\n     * Modifying the model should only happen inside a transform call if not part of an update call.\n     * @param {ManualTransformCallback} callback to run the transformations in\n     * @return {Promise} a promise when auto-complete (if applicable) is done updating\n     */\n    public transform(callback: ManualTransformCallback): Promise<void> {\n        const pos = callback();\n        let acPromise: Promise<void> | null;\n        if (!(pos instanceof Range)) {\n            acPromise = this.setActivePart(pos, true);\n        } else {\n            acPromise = Promise.resolve();\n        }\n        this.updateCallback?.(pos);\n        return acPromise;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type EditorModel from \"./model\";\nimport type DocumentPosition from \"./position\";\n\nexport default class DocumentOffset {\n    public constructor(\n        public offset: number,\n        public readonly atNodeEnd: boolean,\n    ) {}\n\n    public asPosition(model: EditorModel): DocumentPosition {\n        return model.positionForOffset(this.offset, this.atNodeEnd);\n    }\n\n    public add(delta: number, atNodeEnd = false): DocumentOffset {\n        return new DocumentOffset(this.offset + delta, atNodeEnd);\n    }\n}\n","/*\nCopyright 2019-2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type React from \"react\";\nimport { type Part, type CommandPartCreator, type PartCreator } from \"./parts\";\nimport type DocumentPosition from \"./position\";\nimport { type ICompletion, type ISelectionRange } from \"../autocomplete/Autocompleter\";\nimport type Autocomplete from \"../components/views/rooms/Autocomplete\";\n\nexport interface ICallback {\n    replaceParts?: Part[];\n    range?: ISelectionRange;\n    close?: boolean;\n}\n\nexport type UpdateCallback = (data: ICallback) => void;\nexport type GetAutocompleterComponent = () => Autocomplete | null;\nexport type UpdateQuery = (test: string) => Promise<void>;\n\nexport default class AutocompleteWrapperModel {\n    private partIndex?: number;\n\n    public constructor(\n        private updateCallback: UpdateCallback,\n        private getAutocompleterComponent: GetAutocompleterComponent,\n        private updateQuery: UpdateQuery,\n        private partCreator: PartCreator | CommandPartCreator,\n    ) {}\n\n    public onEscape(e: KeyboardEvent | React.KeyboardEvent): void {\n        this.getAutocompleterComponent()?.onEscape(e);\n    }\n\n    public close(): void {\n        this.updateCallback({ close: true });\n    }\n\n    public hasSelection(): boolean {\n        return !!this.getAutocompleterComponent()?.hasSelection();\n    }\n\n    public hasCompletions(): boolean {\n        const ac = this.getAutocompleterComponent();\n        return !!ac && ac.countCompletions() > 0;\n    }\n\n    public confirmCompletion(): void {\n        this.getAutocompleterComponent()?.onConfirmCompletion();\n        this.updateCallback({ close: true });\n    }\n\n    /**\n     * If there is no current autocompletion, start one and move to the first selection.\n     */\n    public async startSelection(): Promise<void> {\n        const acComponent = this.getAutocompleterComponent();\n        if (acComponent && acComponent.countCompletions() === 0) {\n            // Force completions to show for the text currently entered\n            await acComponent.forceComplete();\n        }\n    }\n\n    public selectPreviousSelection(): void {\n        this.getAutocompleterComponent()?.moveSelection(-1);\n    }\n\n    public selectNextSelection(): void {\n        this.getAutocompleterComponent()?.moveSelection(+1);\n    }\n\n    public onPartUpdate(part: Part, pos: DocumentPosition): Promise<void> {\n        this.partIndex = pos.index;\n        return this.updateQuery(part.text);\n    }\n\n    public onComponentConfirm(completion: ICompletion): void {\n        this.updateCallback({\n            replaceParts: this.partForCompletion(completion),\n            close: true,\n            range: completion.range,\n        });\n    }\n\n    private partForCompletion(completion: ICompletion): Part[] {\n        const { completionId } = completion;\n        const text = completion.completion;\n        switch (completion.type) {\n            case \"room\":\n                return [this.partCreator.roomPill(text, completionId), this.partCreator.plain(completion.suffix || \"\")];\n            case \"at-room\":\n                return [\n                    this.partCreator.atRoomPill(completionId || \"\"),\n                    this.partCreator.plain(completion.suffix || \"\"),\n                ];\n            case \"user\":\n                // Insert suffix only if the pill is the part with index 0 - we are at the start of the composer\n                return this.partCreator.createMentionParts(this.partIndex === 0, text, completionId || \"\");\n            case \"command\":\n                // command needs special handling for auto complete, but also renders as plain texts\n                return [(this.partCreator as CommandPartCreator).command(text)];\n            default:\n                // used for emoji and other plain text completion replacement\n                return this.partCreator.plainWithEmoji(text);\n        }\n    }\n}\n","/*\nCopyright 2019-2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient, type RoomMember, type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport AutocompleteWrapperModel, {\n    type GetAutocompleterComponent,\n    type UpdateCallback,\n    type UpdateQuery,\n} from \"./autocomplete\";\nimport { EMOJI_REGEX, unicodeToShortcode } from \"../HtmlUtils\";\nimport * as Avatar from \"../Avatar\";\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport { Action } from \"../dispatcher/actions\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { getFirstGrapheme, graphemeSegmenter } from \"../utils/strings\";\n\nconst REGIONAL_EMOJI_SEPARATOR = String.fromCodePoint(0x200b);\n\ninterface ISerializedPart {\n    type: Type.Plain | Type.Newline | Type.Emoji | Type.Command | Type.PillCandidate;\n    text: string;\n}\n\ninterface ISerializedPillPart {\n    type: Type.AtRoomPill | Type.RoomPill | Type.UserPill;\n    text: string;\n    resourceId?: string;\n}\n\nexport type SerializedPart = ISerializedPart | ISerializedPillPart;\n\nexport enum Type {\n    Plain = \"plain\",\n    Newline = \"newline\",\n    Emoji = \"emoji\",\n    Command = \"command\",\n    UserPill = \"user-pill\",\n    RoomPill = \"room-pill\",\n    AtRoomPill = \"at-room-pill\",\n    PillCandidate = \"pill-candidate\",\n}\n\ninterface IBasePart {\n    text: string;\n    type: Type.Plain | Type.Newline | Type.Emoji;\n    canEdit: boolean;\n    acceptsCaret: boolean;\n\n    createAutoComplete(updateCallback: UpdateCallback): void;\n\n    serialize(): SerializedPart;\n    remove(offset: number, len: number): string | undefined;\n    split(offset: number): IBasePart;\n    validateAndInsert(offset: number, str: string, inputType: string | undefined): boolean;\n    appendUntilRejected(str: string, inputType: string | undefined): string | undefined;\n    updateDOMNode(node: Node): void;\n    canUpdateDOMNode(node: Node): boolean;\n    toDOMNode(): Node;\n\n    merge?(part: Part): boolean;\n}\n\ninterface IPillCandidatePart extends Omit<IBasePart, \"type\" | \"createAutoComplete\"> {\n    type: Type.PillCandidate | Type.Command;\n    createAutoComplete(updateCallback: UpdateCallback): AutocompleteWrapperModel | undefined;\n}\n\ninterface IPillPart extends Omit<IBasePart, \"type\" | \"resourceId\"> {\n    type: Type.AtRoomPill | Type.RoomPill | Type.UserPill;\n    resourceId: string;\n}\n\nexport type Part = IBasePart | IPillCandidatePart | IPillPart;\n\nabstract class BasePart {\n    protected _text: string;\n\n    public constructor(text = \"\") {\n        this._text = text;\n    }\n\n    // chr can also be a grapheme cluster\n    protected acceptsInsertion(chr: string, offset: number, inputType: string): boolean {\n        return true;\n    }\n\n    protected acceptsRemoval(position: number, chr: string): boolean {\n        return true;\n    }\n\n    public merge(part: Part): boolean {\n        return false;\n    }\n\n    public split(offset: number): IBasePart {\n        const splitText = this.text.slice(offset);\n        this._text = this.text.slice(0, offset);\n        return new PlainPart(splitText);\n    }\n\n    // removes len chars, or returns the plain text this part should be replaced with\n    // if the part would become invalid if it removed everything.\n    public remove(offset: number, len: number): string | undefined {\n        // validate\n        const strWithRemoval = this.text.slice(0, offset) + this.text.slice(offset + len);\n        for (let i = offset; i < len + offset; ++i) {\n            const chr = this.text.charAt(i);\n            if (!this.acceptsRemoval(i, chr)) {\n                return strWithRemoval;\n            }\n        }\n        this._text = strWithRemoval;\n    }\n\n    // append str, returns the remaining string if a character was rejected.\n    public appendUntilRejected(str: string, inputType: string): string | undefined {\n        const offset = this.text.length;\n        // Take a copy as we will be taking chunks off the start of the string as we process them\n        // To only need to grapheme split the bits of the string we're working on.\n        let buffer = str;\n        while (buffer) {\n            const char = getFirstGrapheme(buffer);\n            if (!this.acceptsInsertion(char, offset + str.length - buffer.length, inputType)) {\n                break;\n            }\n            buffer = buffer.slice(char.length);\n        }\n\n        this._text += str.slice(0, str.length - buffer.length);\n        return buffer || undefined;\n    }\n\n    // inserts str at offset if all the characters in str were accepted, otherwise don't do anything\n    // return whether the str was accepted or not.\n    public validateAndInsert(offset: number, str: string, inputType: string): boolean {\n        for (let i = 0; i < str.length; ++i) {\n            const chr = str.charAt(i);\n            if (!this.acceptsInsertion(chr, offset + i, inputType)) {\n                return false;\n            }\n        }\n        const beforeInsert = this._text.slice(0, offset);\n        const afterInsert = this._text.slice(offset);\n        this._text = beforeInsert + str + afterInsert;\n        return true;\n    }\n\n    public createAutoComplete(updateCallback: UpdateCallback): void {}\n\n    protected trim(len: number): string {\n        const remaining = this._text.slice(len);\n        this._text = this._text.slice(0, len);\n        return remaining;\n    }\n\n    public get text(): string {\n        return this._text;\n    }\n\n    public abstract get type(): Type;\n\n    public get canEdit(): boolean {\n        return true;\n    }\n\n    public get acceptsCaret(): boolean {\n        return this.canEdit;\n    }\n\n    public toString(): string {\n        return `${this.type}(${this.text})`;\n    }\n\n    public serialize(): SerializedPart {\n        return {\n            type: this.type as ISerializedPart[\"type\"],\n            text: this.text,\n        };\n    }\n\n    public abstract updateDOMNode(node: Node): void;\n    public abstract canUpdateDOMNode(node: Node): boolean;\n    public abstract toDOMNode(): Node;\n}\n\nabstract class PlainBasePart extends BasePart {\n    protected acceptsInsertion(chr: string, offset: number, inputType: string): boolean {\n        if (chr === \"\\n\" || EMOJI_REGEX.test(chr)) {\n            return false;\n        }\n        // when not pasting or dropping text, reject characters that should start a pill candidate\n        if (inputType !== \"insertFromPaste\" && inputType !== \"insertFromDrop\") {\n            if (chr !== \"@\" && chr !== \"#\" && chr !== \":\" && chr !== \"+\") {\n                return true;\n            }\n\n            // split if we are at the beginning of the part text\n            if (offset === 0) {\n                return false;\n            }\n\n            // or split if the previous character is a space or regional emoji separator\n            // or if it is a + and this is a :\n            return (\n                this._text[offset - 1] !== \" \" &&\n                this._text[offset - 1] !== REGIONAL_EMOJI_SEPARATOR &&\n                (this._text[offset - 1] !== \"+\" || chr !== \":\")\n            );\n        }\n        return true;\n    }\n\n    public toDOMNode(): Node {\n        return document.createTextNode(this.text);\n    }\n\n    public merge(part: Part): boolean {\n        if (part.type === this.type) {\n            this._text = this.text + part.text;\n            return true;\n        }\n        return false;\n    }\n\n    public updateDOMNode(node: Node): void {\n        if (node.textContent !== this.text) {\n            node.textContent = this.text;\n        }\n    }\n\n    public canUpdateDOMNode(node: Node): boolean {\n        return node.nodeType === Node.TEXT_NODE;\n    }\n}\n\n// exported for unit tests, should otherwise only be used through PartCreator\nexport class PlainPart extends PlainBasePart implements IBasePart {\n    public get type(): IBasePart[\"type\"] {\n        return Type.Plain;\n    }\n}\n\nexport abstract class PillPart extends BasePart implements IPillPart {\n    public constructor(\n        public resourceId: string,\n        label: string,\n    ) {\n        super(label);\n    }\n\n    protected acceptsInsertion(chr: string): boolean {\n        return chr !== \" \";\n    }\n\n    protected acceptsRemoval(position: number, chr: string): boolean {\n        return position !== 0; //if you remove initial # or @, pill should become plain\n    }\n\n    public toDOMNode(): Node {\n        const container = document.createElement(\"span\");\n        container.setAttribute(\"spellcheck\", \"false\");\n        container.setAttribute(\"contentEditable\", \"false\");\n        if (this.onClick) container.onclick = this.onClick;\n        container.className = this.className;\n        container.appendChild(document.createTextNode(this.text));\n        this.setAvatar(container);\n        return container;\n    }\n\n    public updateDOMNode(node: HTMLElement): void {\n        const textNode = node.childNodes[0];\n        if (textNode.textContent !== this.text) {\n            textNode.textContent = this.text;\n        }\n        if (node.className !== this.className) {\n            node.className = this.className;\n        }\n        if (this.onClick && node.onclick !== this.onClick) {\n            node.onclick = this.onClick;\n        }\n        this.setAvatar(node);\n    }\n\n    public canUpdateDOMNode(node: HTMLElement): boolean {\n        return (\n            node.nodeType === Node.ELEMENT_NODE &&\n            node.nodeName === \"SPAN\" &&\n            node.childNodes.length === 1 &&\n            node.childNodes[0].nodeType === Node.TEXT_NODE\n        );\n    }\n\n    // helper method for subclasses\n    protected setAvatarVars(\n        node: HTMLElement,\n        avatarUrl: string,\n        initialLetter: string,\n        avatarTextColor?: string,\n    ): void {\n        const avatarBackground = `url('${avatarUrl}')`;\n        const avatarLetter = `'${initialLetter}'`;\n        // check if the value is changing,\n        // otherwise the avatars flicker on every keystroke while updating.\n        if (node.style.getPropertyValue(\"--avatar-background\") !== avatarBackground) {\n            node.style.setProperty(\"--avatar-background\", avatarBackground);\n        }\n        if (node.style.getPropertyValue(\"--avatar-letter\") !== avatarLetter) {\n            node.style.setProperty(\"--avatar-letter\", avatarLetter);\n        }\n        if (avatarTextColor && node.style.getPropertyValue(\"--avatar-color\") !== avatarTextColor) {\n            node.style.setProperty(\"--avatar-color\", avatarTextColor);\n        }\n    }\n\n    public serialize(): ISerializedPillPart {\n        return {\n            type: this.type,\n            text: this.text,\n            resourceId: this.resourceId,\n        };\n    }\n\n    public get canEdit(): boolean {\n        return false;\n    }\n\n    public abstract get type(): IPillPart[\"type\"];\n\n    protected abstract get className(): string;\n\n    protected onClick?: () => void;\n\n    protected abstract setAvatar(node: HTMLElement): void;\n}\n\nclass NewlinePart extends BasePart implements IBasePart {\n    protected acceptsInsertion(chr: string, offset: number): boolean {\n        return offset === 0 && chr === \"\\n\";\n    }\n\n    protected acceptsRemoval(position: number, chr: string): boolean {\n        return true;\n    }\n\n    public toDOMNode(): Node {\n        return document.createElement(\"br\");\n    }\n\n    public merge(): boolean {\n        return false;\n    }\n\n    public updateDOMNode(): void {}\n\n    public canUpdateDOMNode(node: HTMLElement): boolean {\n        return node.tagName === \"BR\";\n    }\n\n    public get type(): IBasePart[\"type\"] {\n        return Type.Newline;\n    }\n\n    // this makes the cursor skip this part when it is inserted\n    // rather than trying to append to it, which is what we want.\n    // As a newline can also be only one character, it makes sense\n    // as it can only be one character long. This caused #9741.\n    public get canEdit(): boolean {\n        return false;\n    }\n}\n\nexport class EmojiPart extends BasePart implements IBasePart {\n    protected acceptsInsertion(chr: string, offset: number): boolean {\n        return EMOJI_REGEX.test(chr);\n    }\n\n    protected acceptsRemoval(position: number, chr: string): boolean {\n        return false;\n    }\n\n    public toDOMNode(): Node {\n        const span = document.createElement(\"span\");\n        span.className = \"mx_Emoji\";\n        span.setAttribute(\"title\", unicodeToShortcode(this.text));\n        span.appendChild(document.createTextNode(this.text));\n        return span;\n    }\n\n    public updateDOMNode(node: HTMLElement): void {\n        const textNode = node.childNodes[0];\n        if (textNode.textContent !== this.text) {\n            node.setAttribute(\"title\", unicodeToShortcode(this.text));\n            textNode.textContent = this.text;\n        }\n    }\n\n    public canUpdateDOMNode(node: HTMLElement): boolean {\n        return node.className === \"mx_Emoji\";\n    }\n\n    public get type(): IBasePart[\"type\"] {\n        return Type.Emoji;\n    }\n\n    public get canEdit(): boolean {\n        return false;\n    }\n\n    public get acceptsCaret(): boolean {\n        return true;\n    }\n}\n\nclass RoomPillPart extends PillPart {\n    public constructor(\n        resourceId: string,\n        label: string,\n        private room?: Room,\n    ) {\n        super(resourceId, label);\n    }\n\n    protected setAvatar(node: HTMLElement): void {\n        let initialLetter = \"\";\n        let avatarUrl = Avatar.avatarUrlForRoom(this.room ?? null, 16, 16, \"crop\");\n        let avatarTextColor: string | undefined;\n        if (!avatarUrl) {\n            initialLetter = Avatar.getInitialLetter(this.room?.name || this.resourceId) ?? \"\";\n            avatarUrl = Avatar.defaultAvatarUrlForString(this.room?.roomId ?? this.resourceId);\n            avatarTextColor = Avatar.getAvatarTextColor(this.room?.roomId ?? this.resourceId);\n        }\n        this.setAvatarVars(node, avatarUrl, initialLetter, avatarTextColor);\n    }\n\n    public get type(): IPillPart[\"type\"] {\n        return Type.RoomPill;\n    }\n\n    protected get className(): string {\n        return \"mx_Pill \" + (this.room?.isSpaceRoom() ? \"mx_SpacePill\" : \"mx_RoomPill\");\n    }\n}\n\nclass AtRoomPillPart extends RoomPillPart {\n    public constructor(text: string, room: Room) {\n        super(text, text, room);\n    }\n\n    public get type(): IPillPart[\"type\"] {\n        return Type.AtRoomPill;\n    }\n\n    public serialize(): ISerializedPillPart {\n        return {\n            type: this.type,\n            text: this.text,\n        };\n    }\n}\n\nclass UserPillPart extends PillPart {\n    public constructor(\n        userId: string,\n        displayName: string,\n        private member?: RoomMember,\n    ) {\n        super(userId, displayName);\n    }\n\n    public get type(): IPillPart[\"type\"] {\n        return Type.UserPill;\n    }\n\n    protected get className(): string {\n        return \"mx_UserPill mx_Pill\";\n    }\n\n    protected setAvatar(node: HTMLElement): void {\n        if (!this.member) {\n            return;\n        }\n        const name = this.member.name || this.member.userId;\n        const defaultAvatarUrl = Avatar.defaultAvatarUrlForString(this.member.userId);\n        const avatarUrl = Avatar.avatarUrlForMember(this.member, 16, 16, \"crop\");\n        let initialLetter = \"\";\n        let avatarTextColor: string | undefined;\n        if (avatarUrl === defaultAvatarUrl) {\n            initialLetter = Avatar.getInitialLetter(name) ?? \"\";\n            avatarTextColor = Avatar.getAvatarTextColor(this.member.userId);\n        }\n        this.setAvatarVars(node, avatarUrl, initialLetter, avatarTextColor);\n    }\n\n    protected onClick = (): void => {\n        defaultDispatcher.dispatch({\n            action: Action.ViewUser,\n            member: this.member,\n        });\n    };\n}\n\nclass PillCandidatePart extends PlainBasePart implements IPillCandidatePart {\n    public constructor(\n        text: string,\n        private autoCompleteCreator: IAutocompleteCreator,\n    ) {\n        super(text);\n    }\n\n    public createAutoComplete(updateCallback: UpdateCallback): AutocompleteWrapperModel | undefined {\n        return this.autoCompleteCreator.create?.(updateCallback);\n    }\n\n    protected acceptsInsertion(chr: string, offset: number, inputType: string): boolean {\n        if (offset === 0) {\n            return true;\n        } else {\n            return super.acceptsInsertion(chr, offset, inputType);\n        }\n    }\n\n    public merge(): boolean {\n        return false;\n    }\n\n    protected acceptsRemoval(position: number, chr: string): boolean {\n        return true;\n    }\n\n    public get type(): IPillCandidatePart[\"type\"] {\n        return Type.PillCandidate;\n    }\n}\n\nexport function getAutoCompleteCreator(getAutocompleterComponent: GetAutocompleterComponent, updateQuery: UpdateQuery) {\n    return (partCreator: PartCreator) => {\n        return (updateCallback: UpdateCallback) => {\n            return new AutocompleteWrapperModel(updateCallback, getAutocompleterComponent, updateQuery, partCreator);\n        };\n    };\n}\n\ntype AutoCompleteCreator = ReturnType<typeof getAutoCompleteCreator>;\n\ninterface IAutocompleteCreator {\n    create: ((updateCallback: UpdateCallback) => AutocompleteWrapperModel) | undefined;\n}\n\nexport class PartCreator {\n    protected readonly autoCompleteCreator: IAutocompleteCreator;\n\n    public constructor(\n        private readonly room: Room,\n        private readonly client: MatrixClient,\n        autoCompleteCreator: AutoCompleteCreator | null = null,\n    ) {\n        // pre-create the creator as an object even without callback so it can already be passed\n        // to PillCandidatePart (e.g. while deserializing) and set later on\n        this.autoCompleteCreator = { create: autoCompleteCreator?.(this) };\n    }\n\n    public setAutoCompleteCreator(autoCompleteCreator: AutoCompleteCreator): void {\n        this.autoCompleteCreator.create = autoCompleteCreator(this);\n    }\n\n    public createPartForInput(input: string, partIndex: number, inputType?: string): Part {\n        switch (input[0]) {\n            case \"#\":\n            case \"@\":\n            case \":\":\n            case \"+\":\n                return this.pillCandidate(\"\");\n            case \"\\n\":\n                return new NewlinePart();\n            default:\n                if (EMOJI_REGEX.test(getFirstGrapheme(input))) {\n                    return new EmojiPart();\n                }\n                return new PlainPart();\n        }\n    }\n\n    public createDefaultPart(text: string): Part {\n        return this.plain(text);\n    }\n\n    public deserializePart(part: SerializedPart): Part | undefined {\n        switch (part.type) {\n            case Type.Plain:\n                return this.plain(part.text);\n            case Type.Newline:\n                return this.newline();\n            case Type.Emoji:\n                return this.emoji(part.text);\n            case Type.AtRoomPill:\n                return this.atRoomPill(part.text);\n            case Type.PillCandidate:\n                return this.pillCandidate(part.text);\n            case Type.RoomPill:\n                return part.resourceId ? this.roomPill(part.resourceId) : undefined;\n            case Type.UserPill:\n                return part.resourceId ? this.userPill(part.text, part.resourceId) : undefined;\n        }\n    }\n\n    public plain(text: string): PlainPart {\n        return new PlainPart(text);\n    }\n\n    public newline(): NewlinePart {\n        return new NewlinePart(\"\\n\");\n    }\n\n    public emoji(text: string): EmojiPart {\n        return new EmojiPart(text);\n    }\n\n    public pillCandidate(text: string): PillCandidatePart {\n        return new PillCandidatePart(text, this.autoCompleteCreator);\n    }\n\n    public roomPill(alias: string, roomId?: string): RoomPillPart {\n        let room: Room | undefined;\n        if (roomId || alias[0] !== \"#\") {\n            room = this.client.getRoom(roomId || alias) ?? undefined;\n        } else {\n            room = this.client.getRooms().find((r) => {\n                return r.getCanonicalAlias() === alias || r.getAltAliases().includes(alias);\n            });\n        }\n        return new RoomPillPart(alias, room ? room.name : alias, room);\n    }\n\n    public atRoomPill(text: string): AtRoomPillPart {\n        return new AtRoomPillPart(text, this.room);\n    }\n\n    public userPill(displayName: string, userId: string): UserPillPart {\n        const member = this.room.getMember(userId);\n        return new UserPillPart(userId, displayName, member || undefined);\n    }\n\n    private static isRegionalIndicator(c: string): boolean {\n        const codePoint = c.codePointAt(0) ?? 0;\n        return codePoint != 0 && c.length == 2 && 0x1f1e6 <= codePoint && codePoint <= 0x1f1ff;\n    }\n\n    public plainWithEmoji(text: string): (PlainPart | EmojiPart)[] {\n        const parts: (PlainPart | EmojiPart)[] = [];\n        let plainText = \"\";\n\n        for (const data of graphemeSegmenter.segment(text)) {\n            if (EMOJI_REGEX.test(data.segment)) {\n                if (plainText) {\n                    parts.push(this.plain(plainText));\n                    plainText = \"\";\n                }\n                parts.push(this.emoji(data.segment));\n                if (PartCreator.isRegionalIndicator(text)) {\n                    parts.push(this.plain(REGIONAL_EMOJI_SEPARATOR));\n                }\n            } else {\n                plainText += data.segment;\n            }\n        }\n        if (plainText) {\n            parts.push(this.plain(plainText));\n        }\n        return parts;\n    }\n\n    public createMentionParts(\n        insertTrailingCharacter: boolean,\n        displayName: string,\n        userId: string,\n    ): [UserPillPart, PlainPart] {\n        const pill = this.userPill(displayName, userId);\n        if (!SettingsStore.getValue(\"MessageComposerInput.insertTrailingColon\")) {\n            insertTrailingCharacter = false;\n        }\n        const postfix = this.plain(insertTrailingCharacter ? \": \" : \" \");\n        return [pill, postfix];\n    }\n}\n\n// part creator that support auto complete for /commands,\n// used in SendMessageComposer\nexport class CommandPartCreator extends PartCreator {\n    public createPartForInput(text: string, partIndex: number): Part {\n        // at beginning and starts with /? create\n        if (partIndex === 0 && text[0] === \"/\") {\n            // text will be inserted by model, so pass empty string\n            return this.command(\"\");\n        } else {\n            return super.createPartForInput(text, partIndex);\n        }\n    }\n\n    public command(text: string): CommandPart {\n        return new CommandPart(text, this.autoCompleteCreator);\n    }\n\n    public deserializePart(part: SerializedPart): Part | undefined {\n        if (part.type === Type.Command) {\n            return this.command(part.text);\n        } else {\n            return super.deserializePart(part);\n        }\n    }\n}\n\nclass CommandPart extends PillCandidatePart {\n    public get type(): IPillCandidatePart[\"type\"] {\n        return Type.Command;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport DocumentOffset from \"./offset\";\nimport type EditorModel from \"./model\";\nimport { type Part } from \"./parts\";\n\nexport interface IPosition {\n    index: number;\n    offset: number;\n}\n\ntype Callback = (part: Part, startIdx: number, endIdx: number) => void;\nexport type Predicate = (index: number, offset: number, part: Part) => boolean;\n\nexport default class DocumentPosition implements IPosition {\n    public constructor(\n        public readonly index: number,\n        public readonly offset: number,\n    ) {}\n\n    public compare(otherPos: DocumentPosition): number {\n        if (this.index === otherPos.index) {\n            return this.offset - otherPos.offset;\n        } else {\n            return this.index - otherPos.index;\n        }\n    }\n\n    public iteratePartsBetween(other: DocumentPosition, model: EditorModel, callback: Callback): void {\n        if (this.index === -1 || other.index === -1) {\n            return;\n        }\n        const [startPos, endPos] = this.compare(other) < 0 ? [this, other] : [other, this];\n        if (startPos.index === endPos.index) {\n            callback(model.parts[this.index], startPos.offset, endPos.offset);\n        } else {\n            const firstPart = model.parts[startPos.index];\n            callback(firstPart, startPos.offset, firstPart.text.length);\n            for (let i = startPos.index + 1; i < endPos.index; ++i) {\n                const part = model.parts[i];\n                callback(part, 0, part.text.length);\n            }\n            const lastPart = model.parts[endPos.index];\n            callback(lastPart, 0, endPos.offset);\n        }\n    }\n\n    public forwardsWhile(model: EditorModel, predicate: Predicate): DocumentPosition {\n        if (this.index === -1) {\n            return this;\n        }\n\n        let { index, offset } = this;\n        const { parts } = model;\n        while (index < parts.length) {\n            const part = parts[index];\n            while (offset < part.text.length) {\n                if (!predicate(index, offset, part)) {\n                    return new DocumentPosition(index, offset);\n                }\n                offset += 1;\n            }\n            // end reached\n            if (index === parts.length - 1) {\n                return new DocumentPosition(index, offset);\n            } else {\n                index += 1;\n                offset = 0;\n            }\n        }\n\n        return this; // impossible but Typescript doesn't believe us\n    }\n\n    public backwardsWhile(model: EditorModel, predicate: Predicate): DocumentPosition {\n        if (this.index === -1) {\n            return this;\n        }\n\n        let { index, offset } = this;\n        const parts = model.parts;\n        while (index >= 0) {\n            const part = parts[index];\n            while (offset > 0) {\n                if (!predicate(index, offset - 1, part)) {\n                    return new DocumentPosition(index, offset);\n                }\n                offset -= 1;\n            }\n            // start reached\n            if (index === 0) {\n                return new DocumentPosition(index, offset);\n            } else {\n                index -= 1;\n                offset = parts[index].text.length;\n            }\n        }\n\n        return this; // impossible but Typescript doesn't believe us\n    }\n\n    public asOffset(model: EditorModel): DocumentOffset {\n        if (this.index === -1) {\n            return new DocumentOffset(0, true);\n        }\n        let offset = 0;\n        for (let i = 0; i < this.index; ++i) {\n            offset += model.parts[i].text.length;\n        }\n        offset += this.offset;\n        const lastPart = model.parts[this.index];\n        const atEnd = !lastPart || offset >= lastPart.text.length; // if no last part, we're at the end\n        return new DocumentOffset(offset, atEnd);\n    }\n\n    public isAtEnd(model: EditorModel): boolean {\n        if (model.parts.length === 0) {\n            return true;\n        }\n        const lastPartIdx = model.parts.length - 1;\n        const lastPart = model.parts[lastPartIdx];\n        return this.index === lastPartIdx && this.offset === lastPart.text.length;\n    }\n\n    public isAtStart(): boolean {\n        return this.index === 0 && this.offset === 0;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type EditorModel from \"./model\";\nimport { type Predicate } from \"./position\";\nimport type DocumentPosition from \"./position\";\nimport { type Part } from \"./parts\";\n\nconst whitespacePredicate: Predicate = (index, offset, part) => {\n    return part.text[offset].trim() === \"\";\n};\n\nexport default class Range {\n    private _start: DocumentPosition;\n    private _end: DocumentPosition;\n    private _lastStart: DocumentPosition;\n    private _initializedEmpty: boolean;\n\n    public constructor(\n        public readonly model: EditorModel,\n        positionA: DocumentPosition,\n        positionB = positionA,\n    ) {\n        const bIsLarger = positionA.compare(positionB) < 0;\n        this._start = bIsLarger ? positionA : positionB;\n        this._end = bIsLarger ? positionB : positionA;\n        this._lastStart = this._start;\n        this._initializedEmpty = this._start.index === this._end.index && this._start.offset == this._end.offset;\n    }\n\n    public moveStartForwards(delta: number): void {\n        this._start = this._start.forwardsWhile(this.model, () => {\n            delta -= 1;\n            return delta >= 0;\n        });\n    }\n\n    public wasInitializedEmpty(): boolean {\n        return this._initializedEmpty;\n    }\n\n    public setWasEmpty(value: boolean): void {\n        this._initializedEmpty = value;\n    }\n\n    public getLastStartingPosition(): DocumentPosition {\n        return this._lastStart;\n    }\n\n    public setLastStartingPosition(position: DocumentPosition): void {\n        this._lastStart = position;\n    }\n\n    public moveEndBackwards(delta: number): void {\n        this._end = this._end.backwardsWhile(this.model, () => {\n            delta -= 1;\n            return delta >= 0;\n        });\n    }\n\n    public trim(): void {\n        if (this.text.trim() === \"\") {\n            this._start = this._end;\n            return;\n        }\n        this._start = this._start.forwardsWhile(this.model, whitespacePredicate);\n        this._end = this._end.backwardsWhile(this.model, whitespacePredicate);\n    }\n\n    public expandBackwardsWhile(predicate: Predicate): void {\n        this._start = this._start.backwardsWhile(this.model, predicate);\n    }\n\n    public expandForwardsWhile(predicate: Predicate): void {\n        this._end = this._end.forwardsWhile(this.model, predicate);\n    }\n\n    public get text(): string {\n        let text = \"\";\n        this._start.iteratePartsBetween(this._end, this.model, (part, startIdx, endIdx) => {\n            const t = part.text.substring(startIdx, endIdx);\n            text = text + t;\n        });\n        return text;\n    }\n\n    /**\n     * Splits the model at the range boundaries and replaces with the given parts.\n     * Should be run inside a `model.transform()` callback.\n     * @param {Part[]} parts the parts to replace the range with\n     * @return {Number} the net amount of characters added, can be negative.\n     */\n    public replace(parts: Part[]): number {\n        const newLength = parts.reduce((sum, part) => sum + part.text.length, 0);\n        let oldLength = 0;\n        this._start.iteratePartsBetween(this._end, this.model, (part, startIdx, endIdx) => {\n            oldLength += endIdx - startIdx;\n        });\n        this.model.replaceRange(this._start, this._end, parts);\n        return newLength - oldLength;\n    }\n\n    /**\n     * Returns a copy of the (partial) parts within the range.\n     * For partial parts, only the text is adjusted to the part that intersects with the range.\n     */\n    public get parts(): Part[] {\n        const parts: Part[] = [];\n        this._start.iteratePartsBetween(this._end, this.model, (part, startIdx, endIdx) => {\n            const serializedPart = part.serialize();\n            serializedPart.text = part.text.substring(startIdx, endIdx);\n            const newPart = this.model.partCreator.deserializePart(serializedPart);\n            if (newPart) parts.push(newPart);\n        });\n        return parts;\n    }\n\n    public get length(): number {\n        let len = 0;\n        this._start.iteratePartsBetween(this._end, this.model, (part, startIdx, endIdx) => {\n            len += endIdx - startIdx;\n        });\n        return len;\n    }\n\n    public get start(): DocumentPosition {\n        return this._start;\n    }\n\n    public get end(): DocumentPosition {\n        return this._end;\n    }\n}\n","/*\nCopyright 2019-2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Part, Type } from \"./parts\";\nimport type EditorModel from \"./model\";\n\nexport function needsCaretNodeBefore(part: Part, prevPart?: Part): boolean {\n    const isFirst = !prevPart || prevPart.type === Type.Newline;\n    return !part.acceptsCaret && (isFirst || !prevPart.acceptsCaret);\n}\n\nexport function needsCaretNodeAfter(part: Part, isLastOfLine: boolean): boolean {\n    return !part.acceptsCaret && isLastOfLine;\n}\n\nfunction insertAfter(node: ChildNode, nodeToInsert: ChildNode): void {\n    const next = node.nextSibling;\n    if (next) {\n        node.parentElement!.insertBefore(nodeToInsert, next);\n    } else {\n        node.parentElement!.appendChild(nodeToInsert);\n    }\n}\n\n// Use a BOM marker for caret nodes.\n// On a first test, they seem to be filtered out when copying text out of the editor,\n// but this could be platform dependent.\n// As a precautionary measure, I chose the character that slate also uses.\nexport const CARET_NODE_CHAR = \"\\ufeff\";\n// a caret node is a node that allows the caret to be placed\n// where otherwise it wouldn't be possible\n// (e.g. next to a pill span without adjacent text node)\nfunction createCaretNode(): HTMLElement {\n    const span = document.createElement(\"span\");\n    span.className = \"caretNode\";\n    span.appendChild(document.createTextNode(CARET_NODE_CHAR));\n    return span;\n}\n\nfunction updateCaretNode(node: ChildNode): void {\n    // ensure the caret node contains only a zero-width space\n    if (node.textContent !== CARET_NODE_CHAR) {\n        node.textContent = CARET_NODE_CHAR;\n    }\n}\n\nexport function isCaretNode(node?: Node | null): node is HTMLElement {\n    return !!node && node instanceof HTMLElement && node.tagName === \"SPAN\" && node.className === \"caretNode\";\n}\n\nfunction removeNextSiblings(node: ChildNode | null): void {\n    if (!node) {\n        return;\n    }\n    node = node.nextSibling;\n    while (node) {\n        const removeNode = node;\n        node = node.nextSibling;\n        removeNode.remove();\n    }\n}\n\nfunction removeChildren(parent: HTMLElement): void {\n    const firstChild = parent.firstChild;\n    if (firstChild) {\n        removeNextSiblings(firstChild);\n        firstChild.remove();\n    }\n}\n\nfunction reconcileLine(lineContainer: ChildNode, parts: Part[]): void {\n    let currentNode: ChildNode | null = null;\n    let prevPart: Part | undefined;\n    const lastPart = parts[parts.length - 1];\n\n    for (const part of parts) {\n        const isFirst = !prevPart;\n        currentNode = isFirst ? lineContainer.firstChild : currentNode!.nextSibling;\n\n        if (needsCaretNodeBefore(part, prevPart)) {\n            if (isCaretNode(currentNode as Element)) {\n                updateCaretNode(currentNode!);\n                currentNode = currentNode!.nextSibling;\n            } else {\n                lineContainer.insertBefore(createCaretNode(), currentNode);\n            }\n        }\n        // remove nodes until matching current part\n        while (currentNode && !part.canUpdateDOMNode(currentNode)) {\n            const nextNode = currentNode.nextSibling;\n            lineContainer.removeChild(currentNode);\n            currentNode = nextNode;\n        }\n        // update or insert node for current part\n        if (currentNode && part) {\n            part.updateDOMNode(currentNode);\n        } else if (part) {\n            currentNode = part.toDOMNode() as ChildNode;\n            // hooks up nextSibling for next iteration\n            lineContainer.appendChild(currentNode);\n        }\n\n        if (needsCaretNodeAfter(part, part === lastPart)) {\n            if (isCaretNode(currentNode?.nextSibling as Element)) {\n                currentNode = currentNode!.nextSibling;\n                updateCaretNode(currentNode as HTMLElement);\n            } else {\n                const caretNode = createCaretNode();\n                insertAfter(currentNode as HTMLElement, caretNode);\n                currentNode = caretNode;\n            }\n        }\n\n        prevPart = part;\n    }\n\n    removeNextSiblings(currentNode);\n}\n\nfunction reconcileEmptyLine(lineContainer: HTMLElement): void {\n    // empty div needs to have a BR in it to give it height\n    let foundBR = false;\n    let partNode = lineContainer.firstChild;\n    while (partNode) {\n        const nextNode = partNode.nextSibling;\n        if (!foundBR && (partNode as HTMLElement).tagName === \"BR\") {\n            foundBR = true;\n        } else {\n            partNode.remove();\n        }\n        partNode = nextNode;\n    }\n    if (!foundBR) {\n        lineContainer.appendChild(document.createElement(\"br\"));\n    }\n}\n\nexport function renderModel(editor: HTMLDivElement, model: EditorModel): void {\n    const lines = model.parts.reduce<Part[][]>(\n        (linesArr, part) => {\n            if (part.type === Type.Newline) {\n                linesArr.push([]);\n            } else {\n                const lastLine = linesArr[linesArr.length - 1];\n                lastLine.push(part);\n            }\n            return linesArr;\n        },\n        [[]],\n    );\n    lines.forEach((parts, i) => {\n        // find first (and remove anything else) div without className\n        // (as browsers insert these in contenteditable) line container\n        let lineContainer = editor.childNodes[i];\n        while (lineContainer && ((<Element>lineContainer).tagName !== \"DIV\" || !!(<Element>lineContainer).className)) {\n            editor.removeChild(lineContainer);\n            lineContainer = editor.childNodes[i];\n        }\n        if (!lineContainer) {\n            lineContainer = document.createElement(\"div\");\n            editor.appendChild(lineContainer);\n        }\n\n        if (parts.length) {\n            reconcileLine(lineContainer, parts);\n        } else {\n            reconcileEmptyLine(lineContainer as HTMLElement);\n        }\n    });\n    if (lines.length) {\n        removeNextSiblings(editor.children[lines.length - 1]);\n    } else {\n        removeChildren(editor);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { encode } from \"html-entities\";\nimport escapeHtml from \"escape-html\";\n\nimport Markdown from \"../Markdown\";\nimport { makeGenericPermalink } from \"../utils/permalinks/Permalinks\";\nimport type EditorModel from \"./model\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport SdkConfig from \"../SdkConfig\";\nimport { Type } from \"./parts\";\n\nexport function mdSerialize(model: EditorModel): string {\n    return model.parts.reduce((html, part) => {\n        switch (part.type) {\n            case Type.Newline:\n                return html + \"\\n\";\n            case Type.Plain:\n            case Type.Emoji:\n            case Type.Command:\n            case Type.PillCandidate:\n            case Type.AtRoomPill:\n                return html + part.text;\n            case Type.RoomPill: {\n                const url = makeGenericPermalink(part.resourceId, true);\n                // Escape square brackets and backslashes\n                // Here we use the resourceId for compatibility with non-rich text clients\n                // See https://github.com/vector-im/element-web/issues/16660\n                const title = part.resourceId.replace(/[[\\\\\\]]/g, (c) => \"\\\\\" + c);\n                return html + `[${title}](${url})`;\n            }\n            case Type.UserPill: {\n                const url = makeGenericPermalink(part.resourceId, true);\n                // Escape square brackets and backslashes; convert newlines to HTML\n                const title = part.text.replace(/[[\\\\\\]]/g, (c) => \"\\\\\" + c).replace(/\\n/g, \"<br>\");\n                return html + `[${title}](${url})`;\n            }\n        }\n    }, \"\");\n}\n\ninterface ISerializeOpts {\n    forceHTML?: boolean;\n    useMarkdown?: boolean;\n}\n\nexport function htmlSerializeIfNeeded(\n    model: EditorModel,\n    { forceHTML = false, useMarkdown = true }: ISerializeOpts = {},\n): string | undefined {\n    if (!useMarkdown) {\n        return escapeHtml(textSerialize(model)).replace(/\\n/g, \"<br/>\");\n    }\n\n    const md = mdSerialize(model);\n    return htmlSerializeFromMdIfNeeded(md, { forceHTML });\n}\n\nexport function htmlSerializeFromMdIfNeeded(md: string, { forceHTML = false } = {}): string | undefined {\n    // copy of raw input to remove unwanted math later\n    const orig = md;\n\n    if (SettingsStore.getValue(\"feature_latex_maths\")) {\n        const patternNames = [\"tex\", \"latex\"] as const;\n        const patternTypes = [\"display\", \"inline\"] as const;\n        const patternDefaults = {\n            tex: {\n                // detect math with tex delimiters, inline: $...$, display $$...$$\n                // preferably use negative lookbehinds, not supported in all major browsers:\n                // const displayPattern = \"^(?<!\\\\\\\\)\\\\$\\\\$(?![ \\\\t])(([^$]|\\\\\\\\\\\\$)+?)\\\\$\\\\$$\";\n                // const inlinePattern = \"(?:^|\\\\s)(?<!\\\\\\\\)\\\\$(?!\\\\s)(([^$]|\\\\\\\\\\\\$)+?)(?<!\\\\\\\\|\\\\s)\\\\$\";\n\n                // conditions for display math detection $$...$$:\n                // - pattern starts and ends on a new line\n                // - left delimiter ($$) is not escaped by backslash\n                display: \"(^)\\\\$\\\\$(([^$]|\\\\\\\\\\\\$)+?)\\\\$\\\\$$\",\n\n                // conditions for inline math detection $...$:\n                // - pattern starts at beginning of line, follows whitespace character or punctuation\n                // - pattern is on a single line\n                // - left and right delimiters ($) are not escaped by backslashes\n                // - left delimiter is not followed by whitespace character\n                // - right delimiter is not prefixed with whitespace character\n                inline: \"(^|\\\\s|[.,!?:;])(?!\\\\\\\\)\\\\$(?!\\\\s)(([^$\\\\n]|\\\\\\\\\\\\$)*([^\\\\\\\\\\\\s\\\\$]|\\\\\\\\\\\\$)(?:\\\\\\\\\\\\$)?)\\\\$\",\n            },\n            latex: {\n                // detect math with latex delimiters, inline: \\(...\\), display \\[...\\]\n\n                // conditions for display math detection \\[...\\]:\n                // - pattern starts and ends on a new line\n                // - pattern is not empty\n                display: \"(^)\\\\\\\\\\\\[(?!\\\\\\\\\\\\])(.*?)\\\\\\\\\\\\]$\",\n\n                // conditions for inline math detection \\(...\\):\n                // - pattern starts at beginning of line or is not prefixed with backslash\n                // - pattern is not empty\n                inline: \"(^|[^\\\\\\\\])\\\\\\\\\\\\((?!\\\\\\\\\\\\))(.*?)\\\\\\\\\\\\)\",\n            },\n        };\n\n        patternNames.forEach(function (patternName) {\n            patternTypes.forEach(function (patternType) {\n                // get the regex replace pattern from config or use the default\n                const pattern =\n                    SdkConfig.get(\"latex_maths_delims\")?.[patternType]?.[\"pattern\"]?.[patternName] ||\n                    patternDefaults[patternName][patternType];\n\n                md = md.replace(RegExp(pattern, \"gms\"), function (m, p1, p2) {\n                    const p2e = encode(p2);\n                    switch (patternType) {\n                        case \"display\":\n                            return `${p1}<div data-mx-maths=\"${p2e}\">\\n\\n</div>\\n\\n`;\n                        case \"inline\":\n                            return `${p1}<span data-mx-maths=\"${p2e}\"></span>`;\n                    }\n                });\n            });\n        });\n\n        // make sure div tags always start on a new line, otherwise it will confuse the markdown parser\n        md = md.replace(/(.)<div/g, function (m, p1) {\n            return `${p1}\\n<div`;\n        });\n    }\n\n    const parser = new Markdown(md);\n    if (!parser.isPlainText() || forceHTML) {\n        // feed Markdown output to HTML parser\n        const phtml = new DOMParser().parseFromString(parser.toHTML(), \"text/html\");\n\n        if (SettingsStore.getValue(\"feature_latex_maths\")) {\n            // original Markdown without LaTeX replacements\n            const parserOrig = new Markdown(orig);\n            const phtmlOrig = new DOMParser().parseFromString(parserOrig.toHTML(), \"text/html\");\n\n            // since maths delimiters are handled before Markdown,\n            // code blocks could contain mangled content.\n            // replace code blocks with original content\n            [...phtmlOrig.getElementsByTagName(\"code\")].forEach((e, i) => {\n                phtml.getElementsByTagName(\"code\").item(i)!.textContent = e.textContent;\n            });\n\n            // add fallback output for latex math, which should not be interpreted as markdown\n            [...phtml.querySelectorAll(\"div, span\")].forEach((e, i) => {\n                const tex = e.getAttribute(\"data-mx-maths\");\n                if (tex) {\n                    e.innerHTML = `<code>${tex}</code>`;\n                }\n            });\n        }\n        return phtml.body.innerHTML;\n    }\n    // ensure removal of escape backslashes in non-Markdown messages\n    if (md.indexOf(\"\\\\\") > -1) {\n        return parser.toPlaintext();\n    }\n}\n\nexport function textSerialize(model: EditorModel): string {\n    return model.parts.reduce((text, part) => {\n        switch (part.type) {\n            case Type.Newline:\n                return text + \"\\n\";\n            case Type.Plain:\n            case Type.Emoji:\n            case Type.Command:\n            case Type.PillCandidate:\n            case Type.AtRoomPill:\n                return text + part.text;\n            case Type.RoomPill:\n                // Here we use the resourceId for compatibility with non-rich text clients\n                // See https://github.com/vector-im/element-web/issues/16660\n                return text + `${part.resourceId}`;\n            case Type.UserPill:\n                return text + `${part.text}`;\n        }\n    }, \"\");\n}\n\nexport function containsEmote(model: EditorModel): boolean {\n    const hasCommand = startsWith(model, \"/me \", false);\n    const hasArgument = model.parts[0]?.text?.length > 4 || model.parts.length > 1;\n    return hasCommand && hasArgument;\n}\n\nexport function startsWith(model: EditorModel, prefix: string, caseSensitive = true): boolean {\n    const firstPart = model.parts[0];\n    // part type will be \"plain\" while editing,\n    // and \"command\" while composing a message.\n    let text = firstPart?.text || \"\";\n    if (!caseSensitive) {\n        prefix = prefix.toLowerCase();\n        text = text.toLowerCase();\n    }\n\n    return firstPart && (firstPart.type === Type.Plain || firstPart.type === Type.Command) && text.startsWith(prefix);\n}\n\nexport function stripEmoteCommand(model: EditorModel): EditorModel {\n    // trim \"/me \"\n    return stripPrefix(model, \"/me \");\n}\n\nexport function stripPrefix(model: EditorModel, prefix: string): EditorModel {\n    model = model.clone();\n    model.removeText({ index: 0, offset: 0 }, prefix.length);\n    return model;\n}\n\nexport function unescapeMessage(model: EditorModel): EditorModel {\n    const { parts } = model;\n    if (parts.length) {\n        const firstPart = parts[0];\n        // only unescape \\/ to / at start of editor\n        if (firstPart.type === Type.Plain && firstPart.text.startsWith(\"\\\\/\")) {\n            model = model.clone();\n            model.removeText({ index: 0, offset: 0 }, 1);\n        }\n    }\n    return model;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 Nurjin Jafar\nCopyright 2020 Nordeck IT + Consulting GmbH.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n */\nimport { _t, _td } from \"../languageHandler\";\nimport { type ConfettiOptions } from \"./confetti\";\nimport { type Effect } from \"./effect\";\nimport { type FireworksOptions } from \"./fireworks\";\nimport { type RainfallOptions } from \"./rainfall\";\nimport { type SnowfallOptions } from \"./snowfall\";\nimport { type SpaceInvadersOptions } from \"./spaceinvaders\";\nimport { type HeartOptions } from \"./hearts\";\n\n/**\n * This configuration defines room effects that can be triggered by custom message types and emojis\n */\nexport const CHAT_EFFECTS: Array<Effect<{ [key: string]: any }>> = [\n    {\n        emojis: [\"🎊\", \"🎉\"],\n        msgType: \"nic.custom.confetti\",\n        command: \"confetti\",\n        description: () => _td(\"chat_effects|confetti_description\"),\n        fallbackMessage: () => _t(\"chat_effects|confetti_message\") + \" 🎉\",\n        options: {\n            maxCount: 150,\n            speed: 3,\n            frameInterval: 15,\n            alpha: 1.0,\n            gradient: false,\n        },\n    } as Effect<ConfettiOptions>,\n    {\n        emojis: [\"🎆\"],\n        msgType: \"nic.custom.fireworks\",\n        command: \"fireworks\",\n        description: () => _td(\"chat_effects|fireworks_description\"),\n        fallbackMessage: () => _t(\"chat_effects|fireworks_message\") + \" 🎆\",\n        options: {\n            maxCount: 500,\n            gravity: 0.05,\n        },\n    } as Effect<FireworksOptions>,\n    {\n        emojis: [\"🌧️\", \"⛈️\", \"🌦️\"],\n        msgType: \"io.element.effect.rainfall\",\n        command: \"rainfall\",\n        description: () => _td(\"chat_effects|rainfall_description\"),\n        fallbackMessage: () => _t(\"chat_effects|rainfall_message\") + \" 🌧️\",\n        options: {\n            maxCount: 600,\n            speed: 10,\n        },\n    } as Effect<RainfallOptions>,\n    {\n        emojis: [\"❄\", \"🌨\"],\n        msgType: \"io.element.effect.snowfall\",\n        command: \"snowfall\",\n        description: () => _td(\"chat_effects|snowfall_description\"),\n        fallbackMessage: () => _t(\"chat_effects|snowfall_message\") + \" ❄\",\n        options: {\n            maxCount: 200,\n            gravity: 0.05,\n            maxDrift: 5,\n        },\n    } as Effect<SnowfallOptions>,\n    {\n        emojis: [\"👾\", \"🌌\"],\n        msgType: \"io.element.effects.space_invaders\",\n        command: \"spaceinvaders\",\n        description: () => _td(\"chat_effects|spaceinvaders_description\"),\n        fallbackMessage: () => _t(\"chat_effects|spaceinvaders_message\") + \" 👾\",\n        options: {\n            maxCount: 50,\n            gravity: 0.01,\n        },\n    } as Effect<SpaceInvadersOptions>,\n    {\n        emojis: [\"💝\"],\n        msgType: \"io.element.effect.hearts\",\n        command: \"hearts\",\n        description: () => _td(\"chat_effects|hearts_description\"),\n        fallbackMessage: () => _t(\"chat_effects|hearts_message\") + \" 💝\",\n        options: {\n            maxCount: 120,\n            gravity: 3.2,\n        },\n    } as Effect<HeartOptions>,\n];\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 Nurjin Jafar\nCopyright 2020 Nordeck IT + Consulting GmbH.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n */\n\nimport { type IContent } from \"matrix-js-sdk/src/matrix\";\n\n/**\n * Checks a message if it contains one of the provided emojis\n * @param  {Object} content The message\n * @param  {Array<string>} emojis The list of emojis to check for\n */\nexport const containsEmoji = (content: IContent, emojis: Array<string>): boolean => {\n    return emojis.some((emoji) => content.body && content.body.includes(emoji));\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// Regexp based on Simpler Version from https://gist.github.com/gregseth/5582254 - matches RFC2822\nconst EMAIL_ADDRESS_REGEX = new RegExp(\n    \"^[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\\\\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*\" + // localpart\n        \"@(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\\\\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?$\",\n    \"i\",\n);\n\nexport function looksValid(email: string): boolean {\n    // short circuit regex with this basic check\n    if (email.indexOf(\"@\") < 1) return false;\n\n    return EMAIL_ADDRESS_REGEX.test(email);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Tulir Asokan <tulir@maunium.net>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { orderBy } from \"lodash\";\n\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { SettingLevel } from \"../settings/SettingLevel\";\n\ninterface ILegacyFormat {\n    [emoji: string]: [number, number]; // [count, date]\n}\n\n// New format tries to be more space efficient for synchronization. Ordered by Date descending.\nexport type RecentEmojiData = [emoji: string, count: number][];\n\nconst SETTING_NAME = \"recent_emoji\";\n\n// we store more recents than we typically query but this lets us sort by weighted usage\n// even if you haven't used your typically favourite emoji for a little while.\nconst STORAGE_LIMIT = 100;\n\n// TODO remove this after some time\nfunction migrate(): void {\n    const data: ILegacyFormat = JSON.parse(window.localStorage.mx_reaction_count || \"{}\");\n    const sorted = Object.entries(data).sort(([, [count1, date1]], [, [count2, date2]]) => date2 - date1);\n    const newFormat = sorted.map(([emoji, [count, date]]) => [emoji, count]);\n    SettingsStore.setValue(SETTING_NAME, null, SettingLevel.ACCOUNT, newFormat.slice(0, STORAGE_LIMIT));\n}\n\nfunction getRecentEmoji(): RecentEmojiData {\n    return SettingsStore.getValue(SETTING_NAME) || [];\n}\n\nexport function add(emoji: string): void {\n    const recents = getRecentEmoji();\n    const i = recents.findIndex(([e]) => e === emoji);\n\n    let newEntry;\n    if (i >= 0) {\n        // first remove the existing tuple so that we can increment it and push it to the front\n        [newEntry] = recents.splice(i, 1);\n        newEntry[1]++; // increment the usage count\n    } else {\n        newEntry = [emoji, 1];\n    }\n\n    SettingsStore.setValue(SETTING_NAME, null, SettingLevel.ACCOUNT, [newEntry, ...recents].slice(0, STORAGE_LIMIT));\n}\n\nexport function get(limit = 24): string[] {\n    let recents = getRecentEmoji();\n\n    if (recents.length < 1) {\n        migrate();\n        recents = getRecentEmoji();\n    }\n\n    // perform a stable sort on `count` to keep the recent (date) order as a secondary sort factor\n    const sorted = orderBy(recents, \"1\", \"desc\");\n    return sorted.slice(0, limit).map(([emoji]) => emoji);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type FC, useState, useEffect, memo } from \"react\";\nimport { type MatrixRTCSession } from \"matrix-js-sdk/src/matrixrtc\";\n\nimport { formatPreciseDuration } from \"../../../DateUtils\";\n\ninterface CallDurationProps {\n    delta: number;\n}\n\n/**\n * A call duration counter.\n */\nexport const CallDuration: FC<CallDurationProps> = memo(({ delta }) => {\n    // Clock desync could lead to a negative duration, so just hide it if that happens\n    if (delta <= 0) return null;\n    return <div className=\"mx_CallDuration\">{formatPreciseDuration(delta)}</div>;\n});\n\ninterface SessionDurationProps {\n    session: MatrixRTCSession | undefined;\n}\n\n/**\n * A call duration counter that automatically counts up, given a matrixRTC session\n * object.\n */\nexport const SessionDuration: FC<SessionDurationProps> = ({ session }) => {\n    const [now, setNow] = useState(() => Date.now());\n\n    useEffect(() => {\n        const timer = window.setInterval(() => setNow(Date.now()), 1000);\n        return () => clearInterval(timer);\n    }, []);\n\n    // This is a temporal solution.\n    // Using the oldest membership will update when this user leaves.\n    // This implies that the displayed call duration will also update consequently.\n    const createdTs = session?.getOldestMembership()?.createdTs();\n    return createdTs ? <CallDuration delta={now - createdTs} /> : <CallDuration delta={0} />;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type Ref, useCallback, useContext, useMemo, type JSX } from \"react\";\nimport { VideoCallSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport type { MatrixEvent, RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { ConnectionState, type ElementCall } from \"../../../models/Call\";\nimport { _t } from \"../../../languageHandler\";\nimport { useCall, useConnectionState, useParticipatingMembers } from \"../../../hooks/useCall\";\nimport defaultDispatcher from \"../../../dispatcher/dispatcher\";\nimport type { ViewRoomPayload } from \"../../../dispatcher/payloads/ViewRoomPayload\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport AccessibleButton, { type AccessibleButtonKind, type ButtonEvent } from \"../elements/AccessibleButton\";\nimport MemberAvatar from \"../avatars/MemberAvatar\";\nimport { LiveContentSummary, LiveContentType } from \"../rooms/LiveContentSummary\";\nimport FacePile from \"../elements/FacePile\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { CallDuration, SessionDuration } from \"../voip/CallDuration\";\n\nconst MAX_FACES = 8;\n\ninterface ActiveCallEventProps {\n    mxEvent: MatrixEvent;\n    call: ElementCall | null;\n    participatingMembers: RoomMember[];\n    buttonText: string;\n    buttonKind: AccessibleButtonKind;\n    buttonDisabledTooltip?: string;\n    onButtonClick: ((ev: ButtonEvent) => void) | null;\n    ref?: Ref<HTMLDivElement>;\n}\n\nconst ActiveCallEvent = ({\n    mxEvent,\n    call,\n    participatingMembers,\n    buttonText,\n    buttonKind,\n    buttonDisabledTooltip,\n    onButtonClick,\n    ref,\n}: ActiveCallEventProps): JSX.Element => {\n    const senderName = useMemo(() => mxEvent.sender?.name ?? mxEvent.getSender(), [mxEvent]);\n\n    const facePileMembers = useMemo(() => participatingMembers.slice(0, MAX_FACES), [participatingMembers]);\n    const facePileOverflow = participatingMembers.length > facePileMembers.length;\n\n    return (\n        <div className=\"mx_CallEvent_wrapper\" ref={ref}>\n            <div className=\"mx_CallEvent mx_CallEvent_active\">\n                <MemberAvatar\n                    member={mxEvent.sender}\n                    fallbackUserId={mxEvent.getSender()}\n                    viewUserOnClick\n                    size=\"24px\"\n                />\n                <div className=\"mx_CallEvent_columns\">\n                    <div className=\"mx_CallEvent_details\">\n                        <span className=\"mx_CallEvent_title\">\n                            {_t(\"timeline|m.call|video_call_started_text\", { name: senderName })}\n                        </span>\n                        <LiveContentSummary\n                            type={LiveContentType.Video}\n                            text={_t(\"voip|video_call\")}\n                            active={false}\n                            participantCount={participatingMembers.length}\n                        />\n                        <FacePile members={facePileMembers} size=\"24px\" overflow={facePileOverflow} />\n                    </div>\n                    {call && <SessionDuration session={call.session} />}\n                    <AccessibleButton\n                        className=\"mx_CallEvent_button\"\n                        kind={buttonKind}\n                        disabled={onButtonClick === null || buttonDisabledTooltip !== undefined}\n                        onClick={onButtonClick}\n                        title={buttonDisabledTooltip}\n                    >\n                        {buttonText}\n                    </AccessibleButton>\n                </div>\n            </div>\n        </div>\n    );\n};\n\ninterface ActiveLoadedCallEventProps {\n    mxEvent: MatrixEvent;\n    call: ElementCall;\n    ref?: Ref<HTMLDivElement>;\n}\n\nconst ActiveLoadedCallEvent = ({ mxEvent, call, ref }: ActiveLoadedCallEventProps): JSX.Element => {\n    const connectionState = useConnectionState(call);\n    const participatingMembers = useParticipatingMembers(call);\n\n    const connect = useCallback(\n        (ev: ButtonEvent) => {\n            ev.preventDefault();\n            defaultDispatcher.dispatch<ViewRoomPayload>({\n                action: Action.ViewRoom,\n                room_id: mxEvent.getRoomId()!,\n                view_call: true,\n                metricsTrigger: undefined,\n            });\n        },\n        [mxEvent],\n    );\n\n    const disconnect = useCallback(\n        (ev: ButtonEvent) => {\n            ev.preventDefault();\n            call.disconnect();\n        },\n        [call],\n    );\n\n    const [buttonText, buttonKind, onButtonClick] = useMemo<\n        [string, AccessibleButtonKind, null | ((ev: ButtonEvent) => void)]\n    >(() => {\n        switch (connectionState) {\n            case ConnectionState.Disconnected:\n                return [_t(\"action|join\"), \"primary\", connect];\n            case ConnectionState.Connected:\n                return [_t(\"action|leave\"), \"danger\", disconnect];\n            case ConnectionState.Disconnecting:\n                return [_t(\"action|leave\"), \"danger\", null];\n        }\n    }, [connectionState, connect, disconnect]);\n\n    return (\n        <ActiveCallEvent\n            ref={ref}\n            mxEvent={mxEvent}\n            call={call}\n            participatingMembers={participatingMembers}\n            buttonText={buttonText}\n            buttonKind={buttonKind}\n            onButtonClick={onButtonClick}\n        />\n    );\n};\n\ninterface CallEventProps {\n    mxEvent: MatrixEvent;\n    ref?: Ref<HTMLDivElement>;\n}\n\n/**\n * An event tile representing an active or historical Element call.\n */\nexport const CallEvent = ({ mxEvent, ref }: CallEventProps): JSX.Element => {\n    const client = useContext(MatrixClientContext);\n    const call = useCall(mxEvent.getRoomId()!);\n    const latestEvent = client\n        .getRoom(mxEvent.getRoomId())!\n        .currentState.getStateEvents(mxEvent.getType(), mxEvent.getStateKey()!)!;\n\n    if (\"m.terminated\" in latestEvent.getContent() || latestEvent.isRedacted()) {\n        // The call is terminated\n        return (\n            <div className=\"mx_CallEvent_wrapper\" ref={ref}>\n                <div className=\"mx_CallEvent mx_CallEvent_inactive\">\n                    <div className=\"mx_CallEvent_columns\">\n                        <span className=\"mx_CallEvent_title\">\n                            <VideoCallSolidIcon />\n                            {_t(\"timeline|m.call|video_call_ended\")}\n                        </span>\n                        <CallDuration delta={latestEvent.getTs() - mxEvent.getTs()} />\n                    </div>\n                </div>\n            </div>\n        );\n    }\n\n    if (call === null) {\n        // There should be a call, but it hasn't loaded yet\n        return (\n            <ActiveCallEvent\n                ref={ref}\n                mxEvent={mxEvent}\n                call={null}\n                participatingMembers={[]}\n                buttonText={_t(\"action|join\")}\n                buttonKind=\"primary\"\n                onButtonClick={null}\n            />\n        );\n    }\n\n    return <ActiveLoadedCallEvent mxEvent={mxEvent} call={call as ElementCall} ref={ref} />;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2023 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useCallback } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type MatrixEvent, type Room, type RoomState } from \"matrix-js-sdk/src/matrix\";\nimport { ChatSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\nimport { EventTileBubble } from \"@element-hq/web-shared-components\";\n\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport { RoomPermalinkCreator } from \"../../../utils/permalinks/Permalinks\";\nimport { _t } from \"../../../languageHandler\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { type ViewRoomPayload } from \"../../../dispatcher/payloads/ViewRoomPayload\";\nimport { useRoomState } from \"../../../hooks/useRoomState\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport MatrixToPermalinkConstructor from \"../../../utils/permalinks/MatrixToPermalinkConstructor\";\nimport { useScopedRoomContext } from \"../../../contexts/ScopedRoomContext.tsx\";\n\ninterface IProps {\n    /** The m.room.create MatrixEvent that this tile represents */\n    mxEvent: MatrixEvent;\n    timestamp?: JSX.Element;\n}\n\n/**\n * A message tile showing that this room was created as an upgrade of a previous\n * room.\n */\nexport const RoomPredecessorTile: React.FC<IProps> = ({ mxEvent, timestamp }) => {\n    const msc3946ProcessDynamicPredecessor = SettingsStore.getValue(\"feature_dynamic_room_predecessors\");\n\n    // Note: we ask the room for its predecessor here, instead of directly using\n    // the information inside mxEvent. This allows us the flexibility later to\n    // use a different predecessor (e.g. through MSC3946) and still display it\n    // in the timeline location of the create event.\n    const roomContext = useScopedRoomContext(\"room\");\n    const predecessor = useRoomState(\n        roomContext.room,\n        useCallback(\n            (state: RoomState) => state.findPredecessor(msc3946ProcessDynamicPredecessor),\n            [msc3946ProcessDynamicPredecessor],\n        ),\n    );\n\n    const onLinkClicked = useCallback(\n        (e: React.MouseEvent): void => {\n            e.preventDefault();\n\n            dis.dispatch<ViewRoomPayload>({\n                action: Action.ViewRoom,\n                event_id: predecessor?.eventId,\n                highlighted: true,\n                room_id: predecessor?.roomId,\n                metricsTrigger: \"Predecessor\",\n                metricsViaKeyboard: e.type !== \"click\",\n            });\n        },\n        [predecessor?.eventId, predecessor?.roomId],\n    );\n\n    if (!roomContext.room || roomContext.room.roomId !== mxEvent.getRoomId()) {\n        logger.warn(\n            \"RoomPredecessorTile unexpectedly used outside of the context of the\" +\n                \"room containing this m.room.create event.\",\n        );\n        return <></>;\n    }\n\n    if (!predecessor) {\n        logger.warn(\"RoomPredecessorTile unexpectedly used in a room with no predecessor.\");\n        return <div />;\n    }\n\n    const prevRoom = MatrixClientPeg.safeGet().getRoom(predecessor.roomId);\n\n    // We need either the previous room, or some servers to find it with.\n    // Otherwise, we must bail out here\n    if (!prevRoom && !predecessor.viaServers) {\n        logger.warn(`Failed to find predecessor room with id ${predecessor.roomId}`);\n\n        const guessedLink = guessLinkForRoomId(predecessor.roomId);\n\n        return (\n            <EventTileBubble\n                icon={<ChatSolidIcon />}\n                className=\"mx_EventTileBubble mx_CreateEvent\"\n                title={_t(\"timeline|m.room.create|continuation\")}\n            >\n                <>\n                    <div className=\"mx_EventTile_body\">\n                        <span className=\"mx_EventTile_tileError\">\n                            {!!guessedLink ? (\n                                <>\n                                    {_t(\"timeline|m.room.create|unknown_predecessor_guess_server\", {\n                                        roomId: predecessor.roomId,\n                                    })}\n                                    <a href={guessedLink}>{guessedLink}</a>\n                                </>\n                            ) : (\n                                _t(\"timeline|m.room.create|unknown_predecessor\", {\n                                    roomId: predecessor.roomId,\n                                })\n                            )}\n                        </span>\n                    </div>\n                    {timestamp}\n                </>\n            </EventTileBubble>\n        );\n    }\n    // Otherwise, we expect to be able to find this room either because it is\n    // already loaded, or because we have via_servers that we can use.\n    // So we go ahead with rendering the tile.\n\n    const predecessorPermalink = prevRoom\n        ? createLinkWithRoom(prevRoom, predecessor.roomId, predecessor.eventId)\n        : createLinkWithoutRoom(predecessor.roomId, predecessor?.viaServers ?? [], predecessor.eventId);\n\n    const link = (\n        <a href={predecessorPermalink} onClick={onLinkClicked}>\n            {_t(\"timeline|m.room.create|see_older_messages\")}\n        </a>\n    );\n\n    return (\n        <EventTileBubble\n            icon={<ChatSolidIcon />}\n            className=\"mx_EventTileBubble mx_CreateEvent\"\n            title={_t(\"timeline|m.room.create|continuation\")}\n            subtitle={link}\n        >\n            {timestamp}\n        </EventTileBubble>\n    );\n\n    function createLinkWithRoom(room: Room, roomId: string, eventId?: string): string {\n        const permalinkCreator = new RoomPermalinkCreator(room, roomId);\n        permalinkCreator.load();\n        if (eventId) {\n            return permalinkCreator.forEvent(eventId);\n        } else {\n            return permalinkCreator.forRoom();\n        }\n    }\n\n    function createLinkWithoutRoom(roomId: string, viaServers: string[], eventId?: string): string {\n        const matrixToPermalinkConstructor = new MatrixToPermalinkConstructor();\n        if (eventId) {\n            return matrixToPermalinkConstructor.forEvent(roomId, eventId, viaServers);\n        } else {\n            return matrixToPermalinkConstructor.forRoom(roomId, viaServers);\n        }\n    }\n\n    /**\n     * Guess the permalink for a room based on its room ID.\n     *\n     * The spec says that Room IDs are opaque [1] so this can only ever be a\n     * guess. There is no guarantee that this room exists on this server.\n     *\n     * [1] https://spec.matrix.org/v1.5/appendices/#room-ids-and-event-ids\n     */\n    function guessLinkForRoomId(roomId: string): string | null {\n        const serverName = guessServerNameFromRoomId(roomId);\n        if (serverName) {\n            return new MatrixToPermalinkConstructor().forRoom(roomId, [serverName]);\n        } else {\n            return null;\n        }\n    }\n};\n\n/**\n * @internal Public for test only\n *\n * Guess the server name for a room based on its room ID.\n *\n * The spec says that Room IDs are opaque [1] so this can only ever be a\n * guess. There is no guarantee that this room exists on this server.\n *\n * [1] https://spec.matrix.org/v1.5/appendices/#room-ids-and-event-ids\n */\nexport function guessServerNameFromRoomId(roomId: string): string | null {\n    const m = roomId.match(/^[^:]*:(.*)/);\n    if (m) {\n        return m[1];\n    } else {\n        return null;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2017 Vector Creations Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { _t } from \"../../../languageHandler\";\nimport Modal from \"../../../Modal\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport { mediaFromMxc } from \"../../../customisations/Media\";\nimport RoomAvatar from \"../avatars/RoomAvatar\";\nimport ImageView from \"../elements/ImageView\";\ninterface IProps {\n    /* the MatrixEvent to show */\n    mxEvent: MatrixEvent;\n}\n\nexport default class RoomAvatarEvent extends React.Component<IProps> {\n    private onAvatarClick = (): void => {\n        const cli = MatrixClientPeg.safeGet();\n        const ev = this.props.mxEvent;\n        const httpUrl = mediaFromMxc(ev.getContent().url).srcHttp;\n        if (!httpUrl) return;\n\n        const room = cli.getRoom(this.props.mxEvent.getRoomId());\n        const text = _t(\"timeline|m.room.avatar|lightbox_title\", {\n            senderDisplayName: ev.sender && ev.sender.name ? ev.sender.name : ev.getSender(),\n            roomName: room ? room.name : \"\",\n        });\n\n        const params = {\n            src: httpUrl,\n            name: text,\n        };\n        Modal.createDialog(ImageView, params, \"mx_Dialog_lightbox\", undefined, true);\n    };\n\n    public render(): React.ReactNode {\n        const ev = this.props.mxEvent;\n        const senderDisplayName = ev.sender && ev.sender.name ? ev.sender.name : ev.getSender();\n\n        if (!ev.getContent().url || ev.getContent().url.trim().length === 0) {\n            return <div className=\"mx_TextualEvent\">{_t(\"timeline|m.room.avatar|removed\", { senderDisplayName })}</div>;\n        }\n\n        const room = MatrixClientPeg.safeGet().getRoom(ev.getRoomId());\n        // Provide all arguments to RoomAvatar via oobData because the avatar is historic\n        const oobData = {\n            avatarUrl: ev.getContent().url,\n            name: room ? room.name : \"\",\n        };\n\n        return (\n            <>\n                {_t(\n                    \"timeline|m.room.avatar|changed_img\",\n                    { senderDisplayName: senderDisplayName },\n                    {\n                        img: () => (\n                            <AccessibleButton\n                                key=\"avatar\"\n                                className=\"mx_RoomAvatarEvent_avatar\"\n                                onClick={this.onAvatarClick}\n                            >\n                                <RoomAvatar room={room ?? undefined} size=\"14px\" oobData={oobData} />\n                            </AccessibleButton>\n                        ),\n                    },\n                )}\n            </>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 , 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { LockSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\nimport { EventTileBubble } from \"@element-hq/web-shared-components\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { getNameForEventRoom, userLabelForEventRoom } from \"../../../utils/KeyVerificationStateObserver\";\nimport { useMatrixClientContext } from \"../../../contexts/MatrixClientContext\";\n\ninterface Props {\n    mxEvent: MatrixEvent;\n    timestamp?: JSX.Element;\n}\n\ninterface MKeyVerificationRequestContent {\n    body?: string;\n    format?: string;\n    formatted_body?: string;\n    from_device: string;\n    methods: Array<string>;\n    msgtype: \"m.key.verification.request\";\n    to: string;\n}\n\n/**\n * Event tile created when we receive an m.key.verification.request event.\n *\n * Displays a simple message saying that a verification was requested, either by\n * this user or someone else.\n *\n * EventTileFactory has logic meaning we only display this tile if the request\n * was sent to/from this user.\n */\nconst MKeyVerificationRequest: React.FC<Props> = ({ mxEvent, timestamp }) => {\n    const client = useMatrixClientContext();\n\n    if (!client) {\n        throw new Error(\"Attempting to render verification request without a client context!\");\n    }\n\n    const myUserId = client.getSafeUserId();\n    const content: MKeyVerificationRequestContent = mxEvent.getContent();\n    const sender = mxEvent.getSender();\n    const receiver = content.to;\n    const roomId = mxEvent.getRoomId();\n\n    if (!sender) {\n        throw new Error(\"Verification request did not include a sender!\");\n    }\n    if (!roomId) {\n        throw new Error(\"Verification request did not include a room ID!\");\n    }\n\n    let title: string;\n    let subtitle: string;\n\n    const sentByMe = sender === myUserId;\n    if (sentByMe) {\n        title = _t(\"timeline|m.key.verification.request|you_started\");\n        subtitle = userLabelForEventRoom(client, receiver, roomId);\n    } else {\n        const name = getNameForEventRoom(client, sender, roomId);\n        title = _t(\"timeline|m.key.verification.request|user_wants_to_verify\", { name });\n        subtitle = userLabelForEventRoom(client, sender, roomId);\n    }\n\n    return (\n        <EventTileBubble\n            icon={<LockSolidIcon />}\n            className=\"mx_EventTileBubble mx_cryptoEvent mx_cryptoEvent_icon\"\n            title={title}\n            subtitle={subtitle}\n        >\n            {timestamp}\n        </EventTileBubble>\n    );\n};\n\nexport default MKeyVerificationRequest;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { VideoCallSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\nimport { EventTileBubble } from \"@element-hq/web-shared-components\";\n\nimport { _t } from \"../../../languageHandler\";\nimport WidgetStore from \"../../../stores/WidgetStore\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { Container, WidgetLayoutStore } from \"../../../stores/widgets/WidgetLayoutStore\";\n\ninterface IProps {\n    mxEvent: MatrixEvent;\n    timestamp?: JSX.Element;\n}\n\nexport default class MJitsiWidgetEvent extends React.PureComponent<IProps> {\n    public render(): React.ReactNode {\n        const url = this.props.mxEvent.getContent()[\"url\"];\n        const prevUrl = this.props.mxEvent.getPrevContent()[\"url\"];\n        const senderName = this.props.mxEvent.sender?.name || this.props.mxEvent.getSender();\n        const room = MatrixClientPeg.safeGet().getRoom(this.props.mxEvent.getRoomId());\n        if (!room) return null;\n        const widgetId = this.props.mxEvent.getStateKey();\n        const widget = WidgetStore.instance.getRoom(room.roomId, true).widgets.find((w) => w.id === widgetId);\n\n        let joinCopy: string | null = _t(\"timeline|m.widget|jitsi_join_top_prompt\");\n        if (widget && WidgetLayoutStore.instance.isInContainer(room, widget, Container.Right)) {\n            joinCopy = _t(\"timeline|m.widget|jitsi_join_right_prompt\");\n        } else if (!widget) {\n            joinCopy = null;\n        }\n\n        if (!url) {\n            // removed\n            return (\n                <EventTileBubble\n                    icon={<VideoCallSolidIcon />}\n                    className=\"mx_EventTileBubble mx_MJitsiWidgetEvent\"\n                    title={_t(\"timeline|m.widget|jitsi_ended\", { senderName })}\n                >\n                    {this.props.timestamp}\n                </EventTileBubble>\n            );\n        } else if (prevUrl) {\n            // modified\n            return (\n                <EventTileBubble\n                    icon={<VideoCallSolidIcon />}\n                    className=\"mx_EventTileBubble mx_MJitsiWidgetEvent\"\n                    title={_t(\"timeline|m.widget|jitsi_updated\", { senderName })}\n                    subtitle={joinCopy}\n                >\n                    {this.props.timestamp}\n                </EventTileBubble>\n            );\n        } else {\n            // assume added\n            return (\n                <EventTileBubble\n                    icon={<VideoCallSolidIcon />}\n                    className=\"mx_EventTileBubble mx_MJitsiWidgetEvent\"\n                    title={_t(\"timeline|m.widget|jitsi_started\", { senderName })}\n                    subtitle={joinCopy}\n                >\n                    {this.props.timestamp}\n                </EventTileBubble>\n            );\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport { VisibilityOffIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { type IBodyProps } from \"./IBodyProps\";\n\n/**\n * A message hidden from the user pending moderation.\n *\n * Note: This component must not be used when the user is the author of the message\n * or has a sufficient powerlevel to see the message.\n */\nconst HiddenBody = ({ mxEvent, ref }: IBodyProps): JSX.Element => {\n    let text;\n    const visibility = mxEvent.messageVisibility();\n    switch (visibility.visible) {\n        case true:\n            throw new Error(\"HiddenBody should only be applied to hidden messages\");\n        case false:\n            if (visibility.reason) {\n                text = _t(\"timeline|pending_moderation_reason\", { reason: visibility.reason });\n            } else {\n                text = _t(\"timeline|pending_moderation\");\n            }\n            break;\n    }\n\n    return (\n        <span className=\"mx_HiddenBody\" ref={ref}>\n            <VisibilityOffIcon />\n            {text}\n        </span>\n    );\n};\n\nexport default HiddenBody;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type MatrixEvent, MatrixEventEvent } from \"matrix-js-sdk/src/matrix\";\nimport classNames from \"classnames\";\nimport { CollapseIcon, ExpandIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { _t } from \"../../../languageHandler\";\nimport AccessibleButton, { type ButtonEvent } from \"../elements/AccessibleButton\";\n\ninterface IProps {\n    mxEvent: MatrixEvent;\n}\n\ninterface IState {\n    expanded: boolean;\n}\n\nexport default class ViewSourceEvent extends React.PureComponent<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            expanded: false,\n        };\n    }\n\n    public componentDidMount(): void {\n        const { mxEvent } = this.props;\n\n        const client = MatrixClientPeg.safeGet();\n        client.decryptEventIfNeeded(mxEvent);\n\n        if (mxEvent.isBeingDecrypted()) {\n            mxEvent.once(MatrixEventEvent.Decrypted, () => this.forceUpdate());\n        }\n    }\n\n    private onToggle = (ev: ButtonEvent): void => {\n        ev.preventDefault();\n        const { expanded } = this.state;\n        this.setState({\n            expanded: !expanded,\n        });\n    };\n\n    public render(): React.ReactNode {\n        const { mxEvent } = this.props;\n        const { expanded } = this.state;\n\n        let content;\n        if (expanded) {\n            content = <pre>{JSON.stringify(mxEvent, null, 4)}</pre>;\n        } else {\n            content = <code>{`{ \"type\": ${mxEvent.getType()} }`}</code>;\n        }\n\n        const classes = classNames(\"mx_ViewSourceEvent mx_EventTile_content\", {\n            mx_ViewSourceEvent_expanded: expanded,\n        });\n\n        return (\n            <span className={classes}>\n                {content}\n                <AccessibleButton\n                    kind=\"link\"\n                    title={_t(\"devtools|toggle_event\")}\n                    className=\"mx_ViewSourceEvent_toggle\"\n                    onClick={this.onToggle}\n                >\n                    {expanded ? <CollapseIcon /> : <ExpandIcon />}\n                </AccessibleButton>\n            </span>\n        );\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { MatrixEventEvent } from \"matrix-js-sdk/src/matrix\";\nimport { type TextualEventViewSnapshot, BaseViewModel } from \"@element-hq/web-shared-components\";\n\nimport { type EventTileTypeProps } from \"../../events/EventTileFactory\";\nimport { MatrixClientPeg } from \"../../MatrixClientPeg\";\nimport { textForEvent } from \"../../TextForEvent\";\n\nexport class TextualEventViewModel extends BaseViewModel<TextualEventViewSnapshot, EventTileTypeProps> {\n    public constructor(props: EventTileTypeProps) {\n        super(props, { content: \"\" });\n        this.setTextFromEvent();\n        this.disposables.trackListener(this.props.mxEvent, MatrixEventEvent.SentinelUpdated, this.setTextFromEvent);\n    }\n\n    private setTextFromEvent = (): void => {\n        const content = textForEvent(this.props.mxEvent, MatrixClientPeg.safeGet(), true, this.props.showHiddenEvents);\n        this.snapshot.set({ content });\n    };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX } from \"react\";\nimport {\n    type MatrixEvent,\n    EventType,\n    MsgType,\n    RelationType,\n    type MatrixClient,\n    GroupCallIntent,\n    M_POLL_END,\n    M_POLL_START,\n} from \"matrix-js-sdk/src/matrix\";\nimport { TextualEventView } from \"@element-hq/web-shared-components\";\n\nimport SettingsStore from \"../settings/SettingsStore\";\nimport type LegacyCallEventGrouper from \"../components/structures/LegacyCallEventGrouper\";\nimport { type IEventTileType, type EventTileProps } from \"../components/views/rooms/EventTile\";\nimport { TimelineRenderingType } from \"../contexts/RoomContext\";\nimport MessageEvent from \"../components/views/messages/MessageEvent\";\nimport LegacyCallEvent from \"../components/views/messages/LegacyCallEvent\";\nimport { CallEvent } from \"../components/views/messages/CallEvent\";\nimport EncryptionEvent from \"../components/views/messages/EncryptionEvent\";\nimport { RoomPredecessorTile } from \"../components/views/messages/RoomPredecessorTile\";\nimport RoomAvatarEvent from \"../components/views/messages/RoomAvatarEvent\";\nimport { WIDGET_LAYOUT_EVENT_TYPE } from \"../stores/widgets/WidgetLayoutStore\";\nimport { ALL_RULE_TYPES } from \"../mjolnir/BanList\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport MKeyVerificationRequest from \"../components/views/messages/MKeyVerificationRequest\";\nimport { WidgetType } from \"../widgets/WidgetType\";\nimport MJitsiWidgetEvent from \"../components/views/messages/MJitsiWidgetEvent\";\nimport { hasText } from \"../TextForEvent\";\nimport { getMessageModerationState, MessageModerationState } from \"../utils/EventUtils\";\nimport HiddenBody from \"../components/views/messages/HiddenBody\";\nimport ViewSourceEvent from \"../components/views/messages/ViewSourceEvent\";\nimport { shouldDisplayAsBeaconTile } from \"../utils/beacon/timeline\";\nimport { type IBodyProps } from \"../components/views/messages/IBodyProps\";\nimport { ModuleApi } from \"../modules/Api\";\nimport { TextualEventViewModel } from \"../viewmodels/event-tiles/TextualEventViewModel\";\nimport { ElementCallEventType } from \"../call-types\";\n\n// Subset of EventTile's IProps plus some mixins\nexport interface EventTileTypeProps extends Pick<\n    EventTileProps,\n    | \"mxEvent\"\n    | \"highlights\"\n    | \"highlightLink\"\n    | \"showUrlPreview\"\n    | \"forExport\"\n    | \"getRelationsForEvent\"\n    | \"editState\"\n    | \"replacingEventId\"\n    | \"permalinkCreator\"\n    | \"callEventGrouper\"\n    | \"isSeeingThroughMessageHiddenForModeration\"\n    | \"inhibitInteraction\"\n> {\n    ref?: React.RefObject<IEventTileType | null>;\n    maxImageHeight?: number; // pixels\n    overrideBodyTypes?: Record<string, React.ComponentType<IBodyProps>>;\n    overrideEventTypes?: Record<string, React.ComponentType<IBodyProps>>;\n    showHiddenEvents: boolean;\n}\n\ntype FactoryProps = Omit<EventTileTypeProps, \"ref\">;\ntype Factory<X = FactoryProps> = (ref: React.RefObject<any> | undefined, props: X) => JSX.Element;\n\nexport const MessageEventFactory: Factory = (ref, props) => <MessageEvent ref={ref} {...props} />;\nconst LegacyCallEventFactory: Factory<FactoryProps & { callEventGrouper: LegacyCallEventGrouper }> = (ref, props) => (\n    <LegacyCallEvent ref={ref} {...props} />\n);\nconst CallEventFactory: Factory = (ref, props) => <CallEvent ref={ref} {...props} />;\nexport const TextualEventFactory: Factory = (ref, props) => {\n    const vm = new TextualEventViewModel(props);\n    return <TextualEventView vm={vm} />;\n};\nconst VerificationReqFactory: Factory = (_ref, props) => <MKeyVerificationRequest {...props} />;\nconst HiddenEventFactory: Factory = (ref, props) => <HiddenBody ref={ref} {...props} />;\n\n// These factories are exported for reference comparison against pickFactory()\nexport const JitsiEventFactory: Factory = (ref, props) => <MJitsiWidgetEvent ref={ref} {...props} />;\nexport const JSONEventFactory: Factory = (ref, props) => <ViewSourceEvent ref={ref} {...props} />;\nexport const RoomCreateEventFactory: Factory = (_ref, props) => <RoomPredecessorTile {...props} />;\n\nconst EVENT_TILE_TYPES = new Map<string, Factory>([\n    [EventType.RoomMessage, MessageEventFactory], // note that verification requests are handled in pickFactory()\n    [EventType.Sticker, MessageEventFactory],\n    [M_POLL_START.name, MessageEventFactory],\n    [M_POLL_START.altName, MessageEventFactory],\n    [M_POLL_END.name, MessageEventFactory],\n    [M_POLL_END.altName, MessageEventFactory],\n    [EventType.CallInvite, LegacyCallEventFactory as Factory], // note that this requires a special factory type\n]);\n\nconst STATE_EVENT_TILE_TYPES = new Map<string, Factory>([\n    [EventType.RoomEncryption, (ref, props) => <EncryptionEvent ref={ref} {...props} />],\n    [EventType.RoomCanonicalAlias, TextualEventFactory],\n    [EventType.RoomCreate, RoomCreateEventFactory],\n    [EventType.RoomMember, TextualEventFactory],\n    [EventType.RoomName, TextualEventFactory],\n    [EventType.RoomAvatar, (ref, props) => <RoomAvatarEvent ref={ref} {...props} />],\n    [EventType.RoomThirdPartyInvite, TextualEventFactory],\n    [EventType.RoomHistoryVisibility, TextualEventFactory],\n    [EventType.RoomTopic, TextualEventFactory],\n    [EventType.RoomPowerLevels, TextualEventFactory],\n    [EventType.RoomPinnedEvents, TextualEventFactory],\n    [EventType.RoomServerAcl, TextualEventFactory],\n    // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n    [\"im.vector.modular.widgets\", TextualEventFactory], // note that Jitsi widgets are special in pickFactory()\n    [WIDGET_LAYOUT_EVENT_TYPE, TextualEventFactory],\n    [EventType.RoomTombstone, TextualEventFactory],\n    [EventType.RoomJoinRules, TextualEventFactory],\n    [EventType.RoomGuestAccess, TextualEventFactory],\n]);\n\nfor (const evType of ElementCallEventType.names) {\n    STATE_EVENT_TILE_TYPES.set(evType, CallEventFactory);\n}\n\n// Add all the Mjolnir stuff to the renderer too\nfor (const evType of ALL_RULE_TYPES) {\n    STATE_EVENT_TILE_TYPES.set(evType, TextualEventFactory);\n}\n\n// These events should be recorded in the STATE_EVENT_TILE_TYPES\nconst SINGULAR_STATE_EVENTS = new Set([\n    EventType.RoomEncryption,\n    EventType.RoomCanonicalAlias,\n    EventType.RoomCreate,\n    EventType.RoomName,\n    EventType.RoomAvatar,\n    EventType.RoomHistoryVisibility,\n    EventType.RoomTopic,\n    EventType.RoomPowerLevels,\n    EventType.RoomPinnedEvents,\n    EventType.RoomServerAcl,\n    WIDGET_LAYOUT_EVENT_TYPE,\n    EventType.RoomTombstone,\n    EventType.RoomJoinRules,\n    EventType.RoomGuestAccess,\n]);\n\n/**\n * Find an event tile factory for the given conditions.\n * @param mxEvent The event.\n * @param cli The matrix client to reference when needed.\n * @param showHiddenEvents Whether hidden events should be shown.\n * @param asHiddenEv When true, treat the event as always hidden.\n * @returns The factory, or undefined if not possible.\n */\nexport function pickFactory(\n    mxEvent: MatrixEvent,\n    cli: MatrixClient,\n    showHiddenEvents: boolean,\n    asHiddenEv?: boolean,\n): Factory | undefined {\n    const evType = mxEvent.getType(); // cache this to reduce call stack execution hits\n\n    // Note: we avoid calling SettingsStore unless absolutely necessary - this code is on the critical path.\n\n    if (asHiddenEv && showHiddenEvents) {\n        return JSONEventFactory;\n    }\n\n    const noEventFactoryFactory: () => Factory | undefined = () => (showHiddenEvents ? JSONEventFactory : undefined); // just don't render things that we shouldn't render\n\n    // We run all the event type checks first as they might override the factory entirely.\n\n    const moderationState = getMessageModerationState(mxEvent, cli);\n    if (moderationState === MessageModerationState.HIDDEN_TO_CURRENT_USER) {\n        return HiddenEventFactory;\n    }\n\n    if (evType === EventType.RoomMessage) {\n        // don't show verification requests we're not involved in,\n        // not even when showing hidden events\n        const content = mxEvent.getContent();\n        if (content?.msgtype === MsgType.KeyVerificationRequest) {\n            const me = cli.getUserId();\n            if (mxEvent.getSender() !== me && content[\"to\"] !== me) {\n                return noEventFactoryFactory(); // not for/from us\n            } else {\n                // override the factory\n                return VerificationReqFactory;\n            }\n        }\n    }\n\n    if (evType === EventType.RoomCreate) {\n        const dynamicPredecessorsEnabled = SettingsStore.getValue(\"feature_dynamic_room_predecessors\");\n        const predecessor = cli.getRoom(mxEvent.getRoomId())?.findPredecessor(dynamicPredecessorsEnabled);\n        if (!predecessor) {\n            return noEventFactoryFactory();\n        }\n    }\n\n    // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n    if (evType === \"im.vector.modular.widgets\") {\n        let type = mxEvent.getContent()[\"type\"];\n        if (!type) {\n            // deleted/invalid widget - try the past widget type\n            type = mxEvent.getPrevContent()[\"type\"];\n        }\n\n        if (WidgetType.JITSI.matches(type)) {\n            // override the factory\n            return JitsiEventFactory;\n        }\n    }\n\n    // Try and pick a state event factory, if we can.\n    if (mxEvent.isState()) {\n        if (shouldDisplayAsBeaconTile(mxEvent)) {\n            return MessageEventFactory;\n        }\n\n        if (SINGULAR_STATE_EVENTS.has(evType) && mxEvent.getStateKey() !== \"\") {\n            return noEventFactoryFactory(); // improper event type to render\n        }\n\n        if (STATE_EVENT_TILE_TYPES.get(evType) === TextualEventFactory && !hasText(mxEvent, cli, showHiddenEvents)) {\n            return noEventFactoryFactory();\n        }\n\n        return STATE_EVENT_TILE_TYPES.get(evType) ?? noEventFactoryFactory();\n    }\n\n    // Blanket override for all events. The MessageEvent component handles redacted states for us.\n    if (mxEvent.isRedacted()) {\n        return MessageEventFactory;\n    }\n\n    if (mxEvent.isRelation(RelationType.Replace)) {\n        return noEventFactoryFactory();\n    }\n\n    return EVENT_TILE_TYPES.get(evType) ?? noEventFactoryFactory();\n}\n\n/**\n * Render an event as a tile\n * @param renderType The render type. Used to inform properties given to the eventual component.\n * @param props The properties to provide to the eventual component.\n * @param cli Optional client instance to use, otherwise the default MatrixClientPeg will be used.\n * @returns The tile as JSX, or null if unable to render.\n */\nexport function renderTile(\n    renderType: TimelineRenderingType,\n    props: EventTileTypeProps,\n    cli?: MatrixClient,\n): JSX.Element | null {\n    cli = cli ?? MatrixClientPeg.safeGet(); // because param defaults don't do the correct thing\n\n    const factory = pickFactory(props.mxEvent, cli, props.showHiddenEvents);\n    if (!factory) {\n        // If we don't have a factory for this event, attempt\n        // to find a custom component that can render it.\n        // Will return null if no custom component can render it.\n        return ModuleApi.instance.customComponents.renderMessage({\n            mxEvent: props.mxEvent,\n        });\n    }\n\n    // Note that we split off the ones we actually care about here just to be sure that we're\n    // not going to accidentally send things we shouldn't from lazy callers. Eg: EventTile's\n    // lazy calls of `renderTile(..., this.props)` will have a lot more than we actually care\n    // about.\n    const {\n        ref,\n        mxEvent,\n        forExport,\n        replacingEventId,\n        editState,\n        highlights,\n        highlightLink,\n        showUrlPreview,\n        permalinkCreator,\n        callEventGrouper,\n        getRelationsForEvent,\n        isSeeingThroughMessageHiddenForModeration,\n        inhibitInteraction,\n        showHiddenEvents,\n    } = props;\n\n    switch (renderType) {\n        case TimelineRenderingType.File:\n        case TimelineRenderingType.Notification:\n        case TimelineRenderingType.Thread:\n            return ModuleApi.instance.customComponents.renderMessage(\n                {\n                    mxEvent: props.mxEvent,\n                },\n                (origProps) =>\n                    factory(props.ref, {\n                        // We only want a subset of props, so we don't end up causing issues for downstream components.\n                        mxEvent,\n                        highlights,\n                        highlightLink,\n                        showUrlPreview: origProps?.showUrlPreview ?? showUrlPreview,\n                        editState,\n                        replacingEventId,\n                        getRelationsForEvent,\n                        isSeeingThroughMessageHiddenForModeration,\n                        permalinkCreator,\n                        inhibitInteraction,\n                        showHiddenEvents,\n                    }),\n            );\n        default:\n            return ModuleApi.instance.customComponents.renderMessage(\n                {\n                    mxEvent: props.mxEvent,\n                },\n                (origProps) =>\n                    factory(ref, {\n                        // NEARLY ALL THE OPTIONS!\n                        mxEvent,\n                        forExport,\n                        replacingEventId,\n                        editState,\n                        highlights,\n                        highlightLink,\n                        showUrlPreview: origProps?.showUrlPreview ?? showUrlPreview,\n                        permalinkCreator,\n                        callEventGrouper,\n                        getRelationsForEvent,\n                        isSeeingThroughMessageHiddenForModeration,\n                        inhibitInteraction,\n                        showHiddenEvents,\n                    }),\n            );\n    }\n}\n\n/**\n * A version of renderTile() specifically for replies.\n * @param props The properties to specify on the eventual object.\n * @param showHiddenEvents Whether hidden events should be shown.\n * @param cli Optional client instance to use, otherwise the default MatrixClientPeg will be used.\n * @returns The tile as JSX, or falsy if unable to render.\n */\nexport function renderReplyTile(\n    props: EventTileTypeProps,\n    showHiddenEvents: boolean,\n    cli?: MatrixClient,\n): JSX.Element | null {\n    cli = cli ?? MatrixClientPeg.safeGet(); // because param defaults don't do the correct thing\n\n    const factory = pickFactory(props.mxEvent, cli, showHiddenEvents);\n    if (!factory) {\n        // If we don't have a factory for this event, attempt\n        // to find a custom component that can render it.\n        // Will return null if no custom component can render it.\n        return ModuleApi.instance.customComponents.renderMessage({\n            mxEvent: props.mxEvent,\n        });\n    }\n\n    // See renderTile() for why we split off so much\n    const {\n        ref,\n        mxEvent,\n        highlights,\n        highlightLink,\n        showUrlPreview,\n        overrideBodyTypes,\n        overrideEventTypes,\n        replacingEventId,\n        maxImageHeight,\n        getRelationsForEvent,\n        isSeeingThroughMessageHiddenForModeration,\n        permalinkCreator,\n    } = props;\n\n    return ModuleApi.instance.customComponents.renderMessage(\n        {\n            mxEvent: props.mxEvent,\n        },\n        (origProps) =>\n            factory(ref, {\n                mxEvent,\n                highlights,\n                highlightLink,\n                showUrlPreview: origProps?.showUrlPreview ?? showUrlPreview,\n                overrideBodyTypes,\n                overrideEventTypes,\n                replacingEventId,\n                maxImageHeight,\n                getRelationsForEvent,\n                isSeeingThroughMessageHiddenForModeration,\n                permalinkCreator,\n                showHiddenEvents,\n            }),\n    );\n}\n\n// XXX: this'll eventually be dynamic based on the fields once we have extensible event types\nconst messageTypes = [EventType.RoomMessage, EventType.Sticker];\nexport function isMessageEvent(ev: MatrixEvent): boolean {\n    return (\n        messageTypes.includes(ev.getType() as EventType) ||\n        M_POLL_START.matches(ev.getType()) ||\n        M_POLL_END.matches(ev.getType())\n    );\n}\n\nexport function haveRendererForEvent(\n    mxEvent: MatrixEvent,\n    matrixClient: MatrixClient,\n    showHiddenEvents: boolean,\n): boolean {\n    // Only show \"Message deleted\" tile for plain message events, encrypted events,\n    // and state events as they'll likely still contain enough keys to be relevant.\n    if (mxEvent.isRedacted() && !mxEvent.isEncrypted() && !isMessageEvent(mxEvent) && !mxEvent.isState()) {\n        return false;\n    }\n\n    // Check to see if we have any hints for this message, which indicates\n    // there is a custom renderer for the event.\n    if (ModuleApi.instance.customComponents.getHintsForMessage(mxEvent)) {\n        return true;\n    }\n\n    // No tile for replacement events since they update the original tile\n    if (mxEvent.isRelation(RelationType.Replace)) return false;\n\n    const handler = pickFactory(mxEvent, matrixClient, showHiddenEvents);\n    if (!handler) return false;\n    if (handler === TextualEventFactory) {\n        return hasText(mxEvent, matrixClient, showHiddenEvents);\n    } else if (handler === STATE_EVENT_TILE_TYPES.get(EventType.RoomCreate)) {\n        const dynamicPredecessorsEnabled = SettingsStore.getValue(\"feature_dynamic_room_predecessors\");\n        const predecessor = matrixClient.getRoom(mxEvent.getRoomId())?.findPredecessor(dynamicPredecessorsEnabled);\n        return Boolean(predecessor);\n    } else if (ElementCallEventType.names.some((eventType) => handler === STATE_EVENT_TILE_TYPES.get(eventType))) {\n        const intent = mxEvent.getContent()[\"m.intent\"];\n        const newlyStarted = Object.keys(mxEvent.getPrevContent()).length === 0;\n        // Only interested in events that mark the start of a non-room call\n        return newlyStarted && typeof intent === \"string\" && intent !== GroupCallIntent.Room;\n    } else if (handler === JSONEventFactory) {\n        return false;\n    } else {\n        return true;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, M_BEACON_INFO } from \"matrix-js-sdk/src/matrix\";\n\n/**\n * beacon_info events without live property set to true\n * should be displayed in the timeline\n */\nexport const shouldDisplayAsBeaconTile = (event: MatrixEvent): boolean =>\n    M_BEACON_INFO.matches(event.getType()) &&\n    (event.getContent()?.live ||\n        // redacted beacons should show 'message deleted' tile\n        event.isRedacted());\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { M_POLL_END, M_POLL_START, M_BEACON_INFO, type MatrixEvent, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { getShareableLocationEventForBeacon } from \"../../utils/beacon/getShareableLocation\";\n\n/**\n * Get forwardable event for a given event\n * If an event is not forwardable return null\n */\nexport const getForwardableEvent = (event: MatrixEvent, cli: MatrixClient): MatrixEvent | null => {\n    if (M_POLL_START.matches(event.getType()) || M_POLL_END.matches(event.getType())) {\n        return null;\n    }\n\n    // Live location beacons should forward their latest location as a static pin location\n    // If the beacon is not live, or doesn't have a location forwarding is not allowed\n    if (M_BEACON_INFO.matches(event.getType())) {\n        return getShareableLocationEventForBeacon(event, cli);\n    }\n    return event;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { M_BEACON_INFO, type MatrixEvent, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { getShareableLocationEventForBeacon } from \"../../utils/beacon/getShareableLocation\";\nimport { isLocationEvent } from \"../../utils/EventUtils\";\n\n/**\n * Get event that is shareable as a location\n * If an event does not have a shareable location, return null\n */\nexport const getShareableLocationEvent = (event: MatrixEvent, cli: MatrixClient): MatrixEvent | null => {\n    if (isLocationEvent(event)) {\n        return event;\n    }\n\n    if (M_BEACON_INFO.matches(event.getType())) {\n        return getShareableLocationEventForBeacon(event, cli);\n    }\n    return null;\n};\n","/*\nCopyright 2020-2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\ninterface IParams {\n    // colour parameters\n    bgColor: string;\n    textColor: string;\n    // font styling parameters\n    fontFamily: string;\n    fontWeight: \"normal\" | \"italic\" | \"bold\" | \"bolder\" | \"lighter\" | number;\n\n    // positioning parameters\n    isUp: boolean;\n    isLeft: boolean;\n}\n\nconst defaults: IParams = {\n    bgColor: \"#d00\",\n    textColor: \"#fff\",\n    fontFamily: \"sans-serif\", // Arial,Verdana,Times New Roman,serif,sans-serif,...\n    fontWeight: \"bold\", // normal,italic,oblique,bold,bolder,lighter,100,200,300,400,500,600,700,800,900\n\n    isUp: false,\n    isLeft: false,\n};\n\nabstract class IconRenderer {\n    protected readonly canvas: HTMLCanvasElement;\n    protected readonly context: CanvasRenderingContext2D;\n    public constructor(\n        protected readonly params: IParams = defaults,\n        protected readonly baseImage?: HTMLImageElement,\n    ) {\n        this.canvas = document.createElement(\"canvas\");\n        const context = this.canvas.getContext(\"2d\");\n        if (!context) {\n            throw Error(\"Could not get canvas context\");\n        }\n        this.context = context;\n    }\n\n    private options(\n        n: number | string,\n        params: IParams,\n    ): {\n        n: string | number;\n        len: number;\n        x: number;\n        y: number;\n        w: number;\n        h: number;\n    } {\n        const opt = {\n            n: typeof n === \"number\" ? Math.abs(n | 0) : n,\n            len: (\"\" + n).length,\n            // badge positioning constants as percentages\n            x: 0.4,\n            y: 0.4,\n            w: 0.6,\n            h: 0.6,\n        };\n\n        // apply positional transformations\n        if (params.isUp) {\n            if (opt.y < 0.6) {\n                opt.y = opt.y - 0.4;\n            } else {\n                opt.y = opt.y - 2 * opt.y + (1 - opt.w);\n            }\n        }\n        if (params.isLeft) {\n            if (opt.x < 0.6) {\n                opt.x = opt.x - 0.4;\n            } else {\n                opt.x = opt.x - 2 * opt.x + (1 - opt.h);\n            }\n        }\n\n        // scale the position to the canvas\n        opt.x = this.canvas.width * opt.x;\n        opt.y = this.canvas.height * opt.y;\n        opt.w = this.canvas.width * opt.w;\n        opt.h = this.canvas.height * opt.h;\n        return opt;\n    }\n\n    /**\n     * Draws a circualr status icon, usually over the top of the application icon.\n     * @param n The content of the circle. Should be a number or a single character.\n     * @param opts Options to adjust.\n     */\n    protected circle(n: number | string, opts?: Partial<IParams>): void {\n        const params = { ...this.params, ...opts };\n        const opt = this.options(n, params);\n\n        let more = false;\n        if (!this.baseImage) {\n            // If we omit the background, assume the entire canvas is our target.\n            opt.x = 0;\n            opt.y = 0;\n            opt.w = this.canvas.width;\n            opt.h = this.canvas.height;\n        }\n        if (opt.len === 2) {\n            opt.x = opt.x - opt.w * 0.4;\n            opt.w = opt.w * 1.4;\n            more = true;\n        } else if (opt.len >= 3) {\n            opt.x = opt.x - opt.w * 0.65;\n            opt.w = opt.w * 1.65;\n            more = true;\n        }\n\n        this.context.clearRect(0, 0, this.canvas.width, this.canvas.height);\n        if (this.baseImage) {\n            this.context.drawImage(this.baseImage, 0, 0, this.canvas.width, this.canvas.height);\n        }\n        this.context.beginPath();\n        const fontSize = Math.floor(opt.h * (typeof opt.n === \"number\" && opt.n > 99 ? 0.85 : 1)) + \"px\";\n        this.context.font = `${params.fontWeight} ${fontSize} ${params.fontFamily}`;\n        this.context.textAlign = \"center\";\n\n        if (more) {\n            this.context.moveTo(opt.x + opt.w / 2, opt.y);\n            this.context.lineTo(opt.x + opt.w - opt.h / 2, opt.y);\n            this.context.quadraticCurveTo(opt.x + opt.w, opt.y, opt.x + opt.w, opt.y + opt.h / 2);\n            this.context.lineTo(opt.x + opt.w, opt.y + opt.h - opt.h / 2);\n            this.context.quadraticCurveTo(opt.x + opt.w, opt.y + opt.h, opt.x + opt.w - opt.h / 2, opt.y + opt.h);\n            this.context.lineTo(opt.x + opt.h / 2, opt.y + opt.h);\n            this.context.quadraticCurveTo(opt.x, opt.y + opt.h, opt.x, opt.y + opt.h - opt.h / 2);\n            this.context.lineTo(opt.x, opt.y + opt.h / 2);\n            this.context.quadraticCurveTo(opt.x, opt.y, opt.x + opt.h / 2, opt.y);\n        } else {\n            this.context.arc(opt.x + opt.w / 2, opt.y + opt.h / 2, opt.h / 2, 0, 2 * Math.PI);\n        }\n\n        this.context.fillStyle = params.bgColor;\n        this.context.fill();\n        this.context.closePath();\n        this.context.beginPath();\n        this.context.stroke();\n        this.context.fillStyle = params.textColor;\n\n        if (typeof opt.n === \"number\" && opt.n > 999) {\n            const count = (opt.n > 9999 ? 9 : Math.floor(opt.n / 1000)) + \"k+\";\n            this.context.fillText(count, Math.floor(opt.x + opt.w / 2), Math.floor(opt.y + opt.h - opt.h * 0.2));\n        } else {\n            this.context.fillText(\"\" + opt.n, Math.floor(opt.x + opt.w / 2), Math.floor(opt.y + opt.h - opt.h * 0.15));\n        }\n\n        this.context.closePath();\n    }\n}\n\nexport class BadgeOverlayRenderer extends IconRenderer {\n    public constructor() {\n        super();\n        // Overlays are 16x16 https://www.electronjs.org/docs/latest/api/browser-window#winsetoverlayiconoverlay-description-windows\n        this.canvas.width = 16;\n        this.canvas.height = 16;\n    }\n\n    /**\n     * Generate an overlay badge without the application icon, and export\n     * as an ArrayBuffer\n     * @param contents The content of the circle. Should be a number or a single character.\n     * @param bgColor Optional alternative background colo.r\n     * @returns An ArrayBuffer representing a 16x16 icon in `image/png` format, or `null` if no badge should be drawn.\n     */\n    public async render(contents: number | string, bgColor?: string): Promise<ArrayBuffer | null> {\n        if (contents === 0) {\n            return null;\n        }\n\n        this.circle(contents, { ...(bgColor ? { bgColor } : undefined) });\n        return new Promise((resolve, reject) => {\n            this.canvas.toBlob(\n                (blob) => {\n                    if (blob) {\n                        resolve(blob.arrayBuffer());\n                    }\n                    reject(new Error(\"Could not render badge overlay as blob\"));\n                },\n                \"image/png\",\n                1,\n            );\n        });\n    }\n}\n\n// multiple of 48 as per Google guidelines\n// multiple of 16 for higher quality scaling for small display\nconst DEFAULT_FAVICON_SIZE = 144;\n\n// Allows dynamic rendering of a circular badge atop the loaded favicon\n// supports colour, font and basic positioning parameters.\n// Based upon https://github.com/ejci/favico.js/blob/master/favico.js [MIT license]\nexport default class Favicon extends IconRenderer {\n    private readonly browser = {\n        ff: typeof window.InstallTrigger !== \"undefined\",\n        opera: !!window.opera || navigator.userAgent.includes(\"Opera\"),\n    };\n\n    private icons: HTMLLinkElement[];\n\n    private isReady = false;\n    // callback to run once isReady is asserted, allows for a badge to be queued for when it can be shown\n    private readyCb?: () => void;\n\n    public constructor() {\n        const baseImage = document.createElement(\"img\");\n        super(defaults, baseImage);\n\n        this.icons = Favicon.getIcons();\n\n        const lastIcon = this.icons[this.icons.length - 1];\n        if (lastIcon.hasAttribute(\"href\")) {\n            baseImage.setAttribute(\"crossOrigin\", \"anonymous\");\n            baseImage.onload = (): void => {\n                // get height and width of the favicon\n                this.canvas.height = baseImage.height > 0 ? baseImage.height : DEFAULT_FAVICON_SIZE;\n                this.canvas.width = baseImage.width > 0 ? baseImage.width : DEFAULT_FAVICON_SIZE;\n                this.ready();\n            };\n            baseImage.setAttribute(\"src\", lastIcon.getAttribute(\"href\")!);\n        } else {\n            this.canvas.height = baseImage.height = DEFAULT_FAVICON_SIZE;\n            this.canvas.width = baseImage.width = DEFAULT_FAVICON_SIZE;\n            this.ready();\n        }\n    }\n\n    private reset(): void {\n        this.context.clearRect(0, 0, this.canvas.width, this.canvas.height);\n        this.context.drawImage(this.baseImage!, 0, 0, this.canvas.width, this.canvas.height);\n    }\n\n    private ready(): void {\n        if (this.isReady) return;\n        this.isReady = true;\n        this.readyCb?.();\n    }\n\n    private setIcon(canvas: HTMLCanvasElement): void {\n        setTimeout(() => {\n            this.setIconSrc(canvas.toDataURL(\"image/png\"));\n        }, 0);\n    }\n\n    private setIconSrc(url: string): void {\n        // if is attached to fav icon\n        if (this.browser.ff || this.browser.opera) {\n            // for FF we need to \"recreate\" element, attach to dom and remove old <link>\n            const old = this.icons[this.icons.length - 1];\n            const newIcon = window.document.createElement(\"link\");\n            this.icons = [newIcon];\n            newIcon.setAttribute(\"rel\", \"icon\");\n            newIcon.setAttribute(\"type\", \"image/png\");\n            window.document.getElementsByTagName(\"head\")[0].appendChild(newIcon);\n            newIcon.setAttribute(\"href\", url);\n            old.parentNode?.removeChild(old);\n        } else {\n            this.icons.forEach((icon) => {\n                icon.setAttribute(\"href\", url);\n            });\n        }\n    }\n\n    public badge(content: number | string, opts?: Partial<IParams>): void {\n        if (!this.isReady) {\n            this.readyCb = (): void => {\n                this.badge(content, opts);\n            };\n            return;\n        }\n\n        if (typeof content === \"string\" || content > 0) {\n            this.circle(content, opts);\n        } else {\n            this.reset();\n        }\n\n        this.setIcon(this.canvas);\n    }\n\n    private static getLinks(): HTMLLinkElement[] {\n        const icons: HTMLLinkElement[] = [];\n        const links = window.document.getElementsByTagName(\"head\")[0].getElementsByTagName(\"link\");\n        for (const link of links) {\n            if (link.hasAttribute(\"rel\") && /(^|\\s)icon(\\s|$)/i.test(link.getAttribute(\"rel\")!)) {\n                icons.push(link);\n            }\n        }\n        return icons;\n    }\n\n    private static getIcons(): HTMLLinkElement[] {\n        // get favicon link elements\n        let elms = Favicon.getLinks();\n        if (elms.length === 0) {\n            elms = [window.document.createElement(\"link\")];\n            elms[0].setAttribute(\"rel\", \"icon\");\n            window.document.getElementsByTagName(\"head\")[0].appendChild(elms[0]);\n        }\n        return elms;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { useMemo } from \"react\";\n\nimport { TimelineRenderingType } from \"../../contexts/RoomContext\";\nimport { useSettingValue } from \"../useSettings\";\nimport { useScopedRoomContext } from \"../../contexts/ScopedRoomContext.tsx\";\n\nexport function useRoomMemberProfile({\n    userId = \"\",\n    member: propMember,\n    forceHistorical = false,\n}: {\n    userId: string | undefined;\n    member?: RoomMember | null;\n    forceHistorical?: boolean;\n}): RoomMember | undefined | null {\n    const context = useScopedRoomContext(\"room\", \"timelineRenderingType\");\n    const useOnlyCurrentProfiles = useSettingValue(\"useOnlyCurrentProfiles\");\n\n    const member = useMemo(() => {\n        const threadContexts = [TimelineRenderingType.ThreadsList, TimelineRenderingType.Thread];\n        if ((!forceHistorical && useOnlyCurrentProfiles) || threadContexts.includes(context.timelineRenderingType)) {\n            const currentMember = context.room?.getMember(userId);\n            if (currentMember) return currentMember;\n        }\n\n        return propMember;\n    }, [forceHistorical, propMember, context.room, context.timelineRenderingType, useOnlyCurrentProfiles, userId]);\n\n    return member;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useState, useEffect, type DependencyList } from \"react\";\n\ntype Fn<T> = () => Promise<T>;\n\nexport function useAsyncMemo<T>(fn: Fn<T>, deps: DependencyList, initialValue: T): T;\nexport function useAsyncMemo<T>(fn: Fn<T>, deps: DependencyList, initialValue?: T): T | undefined;\nexport function useAsyncMemo<T>(fn: Fn<T>, deps: DependencyList, initialValue?: T): T | undefined {\n    const [value, setValue] = useState<T | undefined>(initialValue);\n    useEffect(() => {\n        let discard = false;\n        fn().then((v) => {\n            if (!discard) {\n                setValue(v);\n            }\n        });\n        return () => {\n            discard = true;\n        };\n    }, deps); // eslint-disable-line react-hooks/exhaustive-deps\n    return value;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useState, useCallback, useMemo, useEffect } from \"react\";\n\nimport type { RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { type Call, ConnectionState, CallEvent } from \"../models/Call\";\nimport { useTypedEventEmitterState, useEventEmitter } from \"./useEventEmitter\";\nimport { CallStore, CallStoreEvent } from \"../stores/CallStore\";\n\nexport const useCall = (roomId: string): Call | null => {\n    const [call, setCall] = useState(() => CallStore.instance.getCall(roomId));\n    useEventEmitter(CallStore.instance, CallStoreEvent.Call, (call: Call | null, forRoomId: string) => {\n        if (forRoomId === roomId) setCall(call);\n    });\n\n    // Reset the value when the roomId changes\n    useEffect(() => {\n        setCall(CallStore.instance.getCall(roomId));\n    }, [roomId]);\n\n    return call;\n};\n\nexport const useCallForWidget = (widgetId: string, roomId: string): Call | null => {\n    const call = useCall(roomId);\n    return call?.widget.id === widgetId ? call : null;\n};\n\nexport const useConnectionState = (call: Call | null): ConnectionState =>\n    useTypedEventEmitterState(\n        call ?? undefined,\n        CallEvent.ConnectionState,\n        useCallback((state) => state ?? call?.connectionState ?? ConnectionState.Disconnected, [call]),\n    );\n\nconst useParticipants = (call: Call | null): Map<RoomMember, Set<string>> => {\n    return useTypedEventEmitterState(\n        call ?? undefined,\n        CallEvent.Participants,\n        useCallback((state) => state ?? call?.participants ?? [], [call]),\n    );\n};\n\nexport const useParticipantCount = (call: Call | null): number => {\n    const participants = useParticipants(call);\n\n    return useMemo(() => {\n        return [...participants.values()].reduce<number>((count, set) => count + set.size, 0);\n    }, [participants]);\n};\n\nexport const useParticipatingMembers = (call: Call): RoomMember[] => {\n    const participants = useParticipants(call);\n\n    return useMemo(() => {\n        const members: RoomMember[] = [];\n        for (const [member, devices] of participants) {\n            // Repeat the member for as many devices as they're using\n            for (let i = 0; i < devices.size; i++) members.push(member);\n        }\n        return members;\n    }, [participants]);\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useEffect, useRef } from \"react\";\n\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport { type MatrixDispatcher } from \"../dispatcher/dispatcher\";\n\n// Hook to simplify listening to event dispatches\nexport const useDispatcher = (dispatcher: MatrixDispatcher, handler: (payload: ActionPayload) => void): void => {\n    // Create a ref that stores handler\n    const savedHandler = useRef((payload: ActionPayload) => {});\n\n    // Update ref.current value if handler changes.\n    useEffect(() => {\n        savedHandler.current = handler;\n    }, [handler]);\n\n    useEffect(() => {\n        // Create event listener that calls handler function stored in ref\n        const ref = dispatcher.register((payload) => savedHandler.current(payload));\n        // Remove event listener on cleanup\n        return () => {\n            dispatcher.unregister(ref);\n        };\n    }, [dispatcher]);\n};\n","/*\nCopyright 2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { parseErrorResponse } from \"matrix-js-sdk/src/matrix\";\nimport { useRef, useState, useMemo, useEffect } from \"react\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport ErrorDialog from \"../components/views/dialogs/ErrorDialog\";\nimport { _t } from \"../languageHandler\";\nimport Modal from \"../Modal\";\nimport { FileDownloader } from \"../utils/FileDownloader\";\nimport { MediaEventHelper } from \"../utils/MediaEventHelper\";\nimport { ModuleApi } from \"../modules/Api\";\n\nexport interface UseDownloadMediaReturn {\n    download: () => Promise<void>;\n    loading: boolean;\n    canDownload: boolean;\n}\n\nexport function useDownloadMedia(url: string, fileName?: string, mxEvent?: MatrixEvent): UseDownloadMediaReturn {\n    const downloader = useRef(new FileDownloader()).current;\n    const blobRef = useRef<Blob>(null);\n    const [loading, setLoading] = useState(false);\n    const [canDownload, setCanDownload] = useState<boolean>(true);\n\n    const mediaEventHelper = useMemo(() => (mxEvent ? new MediaEventHelper(mxEvent) : undefined), [mxEvent]);\n\n    useEffect(() => {\n        if (!mxEvent) return;\n\n        const hints = ModuleApi.instance.customComponents.getHintsForMessage(mxEvent);\n        if (hints?.allowDownloadingMedia) {\n            setCanDownload(false);\n            hints\n                .allowDownloadingMedia()\n                .then(setCanDownload)\n                .catch((err: any) => {\n                    logger.error(`Failed to check media download permission for ${mxEvent.event.event_id}`, err);\n\n                    setCanDownload(false);\n                });\n        } else {\n            setCanDownload(true);\n        }\n    }, [mxEvent]);\n\n    const download = async (): Promise<void> => {\n        if (loading) return;\n        try {\n            setLoading(true);\n\n            if (blobRef.current) {\n                return downloadBlob(blobRef.current);\n            }\n\n            // We must download via the mediaEventHelper if given as the file may need decryption.\n            if (mediaEventHelper) {\n                blobRef.current = await mediaEventHelper.sourceBlob.value;\n            } else {\n                const res = await fetch(url);\n                if (!res.ok) {\n                    throw parseErrorResponse(res, await res.text());\n                }\n\n                blobRef.current = await res.blob();\n            }\n\n            await downloadBlob(blobRef.current);\n        } catch (e) {\n            showError(e);\n        }\n    };\n\n    const downloadBlob = async (blob: Blob): Promise<void> => {\n        await downloader.download({\n            blob,\n            name: mediaEventHelper?.fileName ?? fileName ?? _t(\"common|image\"),\n        });\n        setLoading(false);\n    };\n\n    const showError = (e: unknown): void => {\n        Modal.createDialog(ErrorDialog, {\n            title: _t(\"timeline|download_failed\"),\n            description: `${_t(\"timeline|download_failed_description\")}\\n\\n${String(e)}`,\n        });\n        setLoading(false);\n    };\n\n    return { download, loading, canDownload };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useRef, useEffect, useState, useCallback, type DependencyList } from \"react\";\nimport { type ListenerMap, type TypedEventEmitter } from \"matrix-js-sdk/src/matrix\";\n\nimport type { EventEmitter } from \"events\";\n\ntype Handler = (...args: any[]) => void;\n\nexport function useTypedEventEmitter<Events extends string, Arguments extends ListenerMap<Events>>(\n    emitter: TypedEventEmitter<Events, Arguments> | undefined,\n    eventName: Events,\n    handler: Handler,\n): void {\n    useEventEmitter(emitter, eventName, handler);\n}\n\n/**\n * Hook to wrap an EventEmitter on and off in hook lifecycle\n */\nexport function useEventEmitter(emitter: EventEmitter | undefined, eventName: string | symbol, handler: Handler): void {\n    // Create a ref that stores handler\n    const savedHandler = useRef(handler);\n\n    // Update ref.current value if handler changes.\n    useEffect(() => {\n        savedHandler.current = handler;\n    }, [handler]);\n\n    useEffect(\n        () => {\n            // allow disabling this hook by passing a falsy emitter\n            if (!emitter) return;\n\n            // Create event listener that calls handler function stored in ref\n            const eventListener = (...args: any[]): void => savedHandler.current(...args);\n\n            // Add event listener\n            emitter.on(eventName, eventListener);\n\n            // Remove event listener on cleanup\n            return () => {\n                emitter.off(eventName, eventListener);\n            };\n        },\n        [eventName, emitter], // Re-run if eventName or emitter changes\n    );\n}\n\ntype Mapper<T> = (...args: any[]) => T;\n\n/**\n * {@link useEventEmitterState}\n */\nexport function useTypedEventEmitterState<T, Events extends string, Arguments extends ListenerMap<Events>>(\n    emitter: TypedEventEmitter<Events, Arguments> | undefined,\n    eventName: Events,\n    fn: Mapper<T>,\n): T {\n    return useEventEmitterState<T>(emitter, eventName, fn);\n}\n\n/**\n * Creates a state, that can be updated by events.\n *\n * @param emitter The emitter sending the event\n * @param eventName Event name to listen for\n * @param fn The callback function, that should return the state value.\n *           It should have the signature of the event callback, except that all parameters are optional.\n *           If the params are not set, a default value for the state should be returned.\n * @returns State\n */\nexport function useEventEmitterState<T>(\n    emitter: EventEmitter | undefined,\n    eventName: string | symbol,\n    fn: Mapper<T>,\n): T {\n    const [value, setValue] = useState<T>(fn);\n    const handler = useCallback(\n        (...args: any[]) => {\n            setValue(fn(...args));\n        },\n        [fn],\n    );\n    // re-run when the emitter changes\n    useEffect(handler, [emitter]); // eslint-disable-line react-hooks/exhaustive-deps\n    useEventEmitter(emitter, eventName, handler);\n    return value;\n}\n\n/**\n * The return value of the callback function for `useEventEmitterAsyncState`.\n */\nexport type AsyncStateCallbackResult<T> = Promise<T | NoChange>;\n\n/**\n * Creates a state, which is computed asynchronously, and can be updated by events.\n *\n * Similar to `useEventEmitterState`, but the callback is `async`.\n *\n * If the event is emitted while the callback is running, it will wait until\n * after the callback completes before calling the callback again. If the event\n * is emitted multiple times while the callback is running, the callback will be\n * called once for each time the event was emitted, in the order that the events\n * were emitted.\n *\n * @param emitter The emitter sending the event\n * @param eventName Event name to listen for\n * @param fn The callback function, that should return the state value.\n *           It should have the signature of the event callback, except that all\n *           parameters are optional. If the params are not set, a default value\n *           for the state should be returned. If the state value should not\n *           change from its previous value, the function can return a `NoChange`\n *           object.\n * @param deps The dependencies of the callback function.\n * @param initialValue The initial value of the state, before the callback finishes its initial run.\n * @returns State\n */\nexport function useEventEmitterAsyncState<T, Events extends string, Arguments extends ListenerMap<Events>>(\n    emitter: TypedEventEmitter<Events, Arguments> | undefined,\n    eventName: string | symbol,\n    fn: Mapper<AsyncStateCallbackResult<T>>,\n    deps: DependencyList,\n    initialValue: T,\n): T;\nexport function useEventEmitterAsyncState<T, Events extends string, Arguments extends ListenerMap<Events>>(\n    emitter: TypedEventEmitter<Events, Arguments> | undefined,\n    eventName: string | symbol,\n    fn: Mapper<AsyncStateCallbackResult<T>>,\n    deps: DependencyList,\n    initialValue?: T,\n): T | undefined;\nexport function useEventEmitterAsyncState<T, Events extends string, Arguments extends ListenerMap<Events>>(\n    emitter: TypedEventEmitter<Events, Arguments> | undefined,\n    eventName: string | symbol,\n    fn: Mapper<AsyncStateCallbackResult<T>>,\n    deps: DependencyList,\n    initialValue?: T,\n): T | undefined {\n    const [value, setValue] = useState<T | undefined>(initialValue);\n\n    let running = false;\n    // If the handler is called while it's already running, we remember the\n    // arguments that it was called with, and call the handler again when the\n    // first call is done.\n    const rerunArgs: any[] = [];\n\n    const handler = useCallback(\n        (...args: any[]) => {\n            if (running) {\n                // We're already running, so remember the arguments we were\n                // called with, so that we can call the handler again when we're\n                // done.\n                rerunArgs.push(args);\n                return;\n            }\n            running = true; // eslint-disable-line react-hooks/exhaustive-deps\n            // Note: We need to use .then notation instead of async/await,\n            // because async/await would cause this function to return a\n            // promise, which `useEffect` doesn't like.\n            fn(...args)\n                .then((v) => {\n                    if (!(v instanceof NoChange)) {\n                        setValue(v);\n                    }\n                })\n                .finally(() => {\n                    running = false;\n                    if (rerunArgs.length != 0) {\n                        handler(...rerunArgs.shift());\n                    }\n                });\n        },\n        [fn, ...deps], // eslint-disable-line react-compiler/react-compiler\n    );\n\n    // re-run when the emitter changes\n    useEffect(handler, [emitter, handler, ...deps]);\n    useEventEmitter(emitter, eventName, handler);\n    return value;\n}\n\n/**\n * Indicates that the callback for `useEventEmitterAsyncState` is not changing the value of the state.\n */\nexport class NoChange {}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useState } from \"react\";\n\nexport default function useFocus(): [boolean, { onFocus: () => void; onBlur: () => void }] {\n    const [focused, setFocused] = useState(false);\n\n    const props = {\n        onFocus: () => setFocused(true),\n        onBlur: () => setFocused(false),\n    };\n\n    return [focused, props];\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient, type MatrixEvent, type Room, EventType } from \"matrix-js-sdk/src/matrix\";\nimport { type CryptoApi } from \"matrix-js-sdk/src/crypto-api\";\n\nimport { useRoomState } from \"./useRoomState.ts\";\nimport { useAsyncMemo } from \"./useAsyncMemo.ts\";\nimport { LocalRoom } from \"../models/LocalRoom.ts\";\n\n/**\n * Check if a room is encrypted.\n * If the room is a LocalRoom, check the state directly.\n * Otherwise, use the crypto API to check if encryption is enabled in the room.\n *\n * @param room - The room to check.\n * @param cryptoApi - The crypto API from the Matrix client.\n */\nexport async function isRoomEncrypted(room: Room, cryptoApi: CryptoApi): Promise<boolean> {\n    if (room instanceof LocalRoom) {\n        // For local room check the state.\n        // The crypto check fails because the room ID is not valid (it is a local id)\n        return (room as LocalRoom).isEncryptionEnabled();\n    }\n\n    return await cryptoApi.isEncryptionEnabledInRoom(room.roomId);\n}\n\n// Hook to simplify watching whether a Matrix room is encrypted, returns null if room is undefined or the state is loading\nexport function useIsEncrypted(cli: MatrixClient, room?: Room): boolean | null {\n    const encryptionStateEvent: MatrixEvent | undefined = useRoomState(\n        room,\n        (roomState) => roomState.getStateEvents(EventType.RoomEncryption)?.[0],\n    );\n    return useAsyncMemo(\n        async () => {\n            const crypto = cli.getCrypto();\n            if (!room || !crypto) return null;\n\n            return isRoomEncrypted(room, crypto);\n        },\n        [room, encryptionStateEvent],\n        null,\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useState } from \"react\";\n\nexport const useLocalEcho = <T, V extends T = T>(\n    currentFactory: () => T,\n    setterFn: (value: V) => Promise<unknown>,\n    errorFn: (error: unknown) => void,\n): [value: T, handler: (value: V) => void] => {\n    const [value, setValue] = useState(currentFactory);\n    const handler = async (value: V): Promise<void> => {\n        setValue(value);\n        try {\n            await setterFn(value);\n        } catch (e) {\n            setValue(currentFactory());\n            errorFn(e);\n        }\n    };\n\n    return [value, handler];\n};\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useCallback } from \"react\";\nimport { JoinRule, type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { SettingLevel } from \"../settings/SettingLevel\";\nimport { useSettingValue } from \"./useSettings\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { useMatrixClientContext } from \"../contexts/MatrixClientContext\";\nimport { MediaPreviewValue } from \"../@types/media_preview\";\nimport { useRoomState } from \"./useRoomState\";\n\nconst PRIVATE_JOIN_RULES: JoinRule[] = [JoinRule.Invite, JoinRule.Knock, JoinRule.Restricted];\n\n/**\n * Should the media event be visible in the client, or hidden.\n *\n * This function uses the `mediaPreviewConfig` setting to determine the rules for the room\n * along with the `showMediaEventIds` setting for specific events.\n *\n * A function may be provided to alter the visible state.\n *\n * @param The event that contains the media. If not provided, the global rule is used.\n *\n * @returns Returns a tuple of:\n *          A boolean describing the hidden status.\n *          A function to show or hide the event.\n */\nexport function useMediaVisible(mxEvent?: MatrixEvent): [boolean, (visible: boolean) => void] {\n    const eventId = mxEvent?.getId();\n    const mediaPreviewSetting = useSettingValue(\"mediaPreviewConfig\", mxEvent?.getRoomId());\n    const client = useMatrixClientContext();\n    const eventVisibility = useSettingValue(\"showMediaEventIds\");\n    const room = client.getRoom(mxEvent?.getRoomId()) ?? undefined;\n    const joinRule = useRoomState(room, (state) => state.getJoinRule());\n    const setMediaVisible = useCallback(\n        (visible: boolean) => {\n            SettingsStore.setValue(\"showMediaEventIds\", null, SettingLevel.DEVICE, {\n                ...eventVisibility,\n                [eventId!]: visible,\n            });\n        },\n        [eventId, eventVisibility],\n    );\n\n    const roomIsPrivate = joinRule ? PRIVATE_JOIN_RULES.includes(joinRule) : false;\n\n    const explicitEventVisiblity = eventId ? eventVisibility[eventId] : undefined;\n    // Always prefer the explicit per-event user preference here.\n    if (explicitEventVisiblity !== undefined) {\n        return [explicitEventVisiblity, setMediaVisible];\n    } else if (mxEvent?.getSender() === client.getUserId()) {\n        // If this event is ours and we've not set an explicit visibility, default to on.\n        return [true, setMediaVisible];\n    } else if (mediaPreviewSetting.media_previews === MediaPreviewValue.Off) {\n        return [false, setMediaVisible];\n    } else if (mediaPreviewSetting.media_previews === MediaPreviewValue.On) {\n        return [true, setMediaVisible];\n    } else if (mediaPreviewSetting.media_previews === MediaPreviewValue.Private) {\n        return [roomIsPrivate, setMediaVisible];\n    } else {\n        // Invalid setting.\n        console.warn(\"Invalid media visibility setting\", mediaPreviewSetting.media_previews);\n        return [false, setMediaVisible];\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useCallback, useMemo, useState } from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { type RoomNotifState } from \"../RoomNotifs\";\nimport { EchoChamber } from \"../stores/local-echo/EchoChamber\";\nimport { PROPERTY_UPDATED } from \"../stores/local-echo/GenericEchoChamber\";\nimport { CachedRoomKey } from \"../stores/local-echo/RoomEchoChamber\";\nimport { useEventEmitter } from \"./useEventEmitter\";\n\nexport const useNotificationState = (room: Room): [RoomNotifState | undefined, (state: RoomNotifState) => void] => {\n    const echoChamber = useMemo(() => EchoChamber.forRoom(room), [room]);\n    const [notificationState, setNotificationState] = useState<RoomNotifState | undefined>(\n        echoChamber.notificationVolume,\n    );\n    useEventEmitter(echoChamber, PROPERTY_UPDATED, (key: CachedRoomKey) => {\n        if (key === CachedRoomKey.NotificationVolume && echoChamber.notificationVolume !== undefined) {\n            setNotificationState(echoChamber.notificationVolume);\n        }\n    });\n    // eslint-disable-next-line react-compiler/react-compiler\n    const setter = useCallback((state: RoomNotifState) => (echoChamber.notificationVolume = state), [echoChamber]);\n    return [notificationState, setter];\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useCallback, useEffect, useRef, useState } from \"react\";\nimport { type Room, type RoomState, RoomStateEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { useTypedEventEmitter } from \"./useEventEmitter\";\n\ntype Mapper<T> = (roomState: RoomState) => T;\n\n/**\n * A hook to watch the state of a room.\n *\n * Call `useRoomState` in a component to watch the state of a room.\n *\n * A mapper function must be provided to process the room state into outputs suitable for the component. The mapper\n * function will be called whenever the room state changes.\n *\n * @example\n * ```\n * function MyComponent({room}: Props): JSX.Element {\n *   const { historyVisibility, joinRule } = useRoomState(room, state => ({\n *      historyVisibility: state.getHistoryVisibility(),\n *      joinRule: state.getJoinRule(),\n *   }));\n *   // ...\n * ```\n *\n * @param room - The room to watch. If this is undefined, the returned value will also be undefined.\n * @param mapper - A function to process the room state into outputs suitable for the component.\n * @returns The output of `mapper`, or `undefined` if `room` is undefined.\n */\nexport function useRoomState<T>(room: Room, mapper: Mapper<T>): T;\nexport function useRoomState<T>(room: Room | undefined, mapper: Mapper<T>): T | undefined;\nexport function useRoomState<T>(room: Room | undefined, mapper: Mapper<T>): T | undefined {\n    // Create a ref that stores mapper\n    const savedMapper = useRef(mapper);\n\n    // Update ref.current value if mapper changes.\n    useEffect(() => {\n        savedMapper.current = mapper;\n    }, [mapper]);\n\n    const [value, setValue] = useState<T | undefined>(room ? mapper(room.currentState) : undefined);\n\n    const update = useCallback(() => {\n        if (!room) return;\n        setValue(savedMapper.current(room.currentState));\n    }, [room]);\n\n    useTypedEventEmitter(room?.currentState, RoomStateEvent.Update, update);\n    useEffect(() => {\n        update();\n        return () => {\n            setValue(room ? savedMapper.current(room.currentState) : undefined);\n        };\n    }, [room, update]);\n    return value;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useEffect, useState } from \"react\";\n\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { type SettingLevel } from \"../settings/SettingLevel\";\nimport { type FeatureSettingKey, type SettingKey, type Settings } from \"../settings/Settings.tsx\";\n\n// Hook to fetch the value of a setting and dynamically update when it changes\nexport function useSettingValue<S extends SettingKey>(\n    settingName: S,\n    roomId: string | null,\n    excludeDefault: true,\n): Settings[S][\"default\"] | undefined;\nexport function useSettingValue<S extends SettingKey>(\n    settingName: S,\n    roomId?: string | null,\n    excludeDefault?: false,\n): Settings[S][\"default\"];\nexport function useSettingValue<S extends SettingKey>(\n    settingName: S,\n    roomId: string | null = null,\n    excludeDefault = false,\n): Settings[S][\"default\"] | undefined {\n    const [value, setValue] = useState(\n        // XXX: This seems naff but is needed to convince TypeScript that the overload is fine\n        excludeDefault\n            ? SettingsStore.getValue(settingName, roomId, excludeDefault)\n            : SettingsStore.getValue(settingName, roomId, excludeDefault),\n    );\n\n    useEffect(() => {\n        const ref = SettingsStore.watchSetting(settingName, roomId, () => {\n            setValue(\n                // XXX: This seems naff but is needed to convince TypeScript that the overload is fine\n                excludeDefault\n                    ? SettingsStore.getValue(settingName, roomId, excludeDefault)\n                    : SettingsStore.getValue(settingName, roomId, excludeDefault),\n            );\n        });\n        // clean-up\n        return () => {\n            SettingsStore.unwatchSetting(ref);\n        };\n    }, [settingName, roomId, excludeDefault]);\n\n    return value;\n}\n\n/**\n * Hook to fetch the value of a setting at a specific level and dynamically update when it changes\n * @see SettingsStore.getValueAt\n * @param level\n * @param settingName\n * @param roomId\n * @param explicit\n * @param excludeDefault\n */\nexport const useSettingValueAt = <S extends SettingKey>(\n    level: SettingLevel,\n    settingName: S,\n    roomId: string | null = null,\n    explicit = false,\n    excludeDefault = false,\n): Settings[S][\"default\"] => {\n    const [value, setValue] = useState(SettingsStore.getValueAt(level, settingName, roomId, explicit, excludeDefault));\n\n    useEffect(() => {\n        const ref = SettingsStore.watchSetting(settingName, roomId, () => {\n            setValue(SettingsStore.getValueAt(level, settingName, roomId, explicit, excludeDefault));\n        });\n        // clean-up\n        return () => {\n            SettingsStore.unwatchSetting(ref);\n        };\n    }, [level, settingName, roomId, explicit, excludeDefault]);\n\n    return value;\n};\n\n// Hook to fetch whether a feature is enabled and dynamically update when that changes\nexport const useFeatureEnabled = (featureName: FeatureSettingKey, roomId: string | null = null): boolean => {\n    const [enabled, setEnabled] = useState(SettingsStore.getValue(featureName, roomId));\n\n    useEffect(() => {\n        const ref = SettingsStore.watchSetting(featureName, roomId, () => {\n            setEnabled(SettingsStore.getValue(featureName, roomId));\n        });\n        // clean-up\n        return () => {\n            SettingsStore.unwatchSetting(ref);\n        };\n    }, [featureName, roomId]);\n\n    return enabled;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Dispatch, type SetStateAction, useState } from \"react\";\n\n// Hook to simplify toggling of a boolean state value\n// Returns value, method to toggle boolean value and method to set the boolean value\nexport const useStateToggle = (initialValue = false): [boolean, () => void, Dispatch<SetStateAction<boolean>>] => {\n    const [value, setValue] = useState(initialValue);\n    const toggleValue = (): void => {\n        setValue(!value);\n    };\n    return [value, toggleValue, setValue];\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useEffect, useRef, useState } from \"react\";\n\ntype Handler = () => void;\n\n// Hook to simplify timeouts in functional components\nexport const useTimeout = (handler: Handler, timeoutMs: number): void => {\n    // Create a ref that stores handler\n    const savedHandler = useRef<Handler>(undefined);\n\n    // Update ref.current value if handler changes.\n    useEffect(() => {\n        savedHandler.current = handler;\n    }, [handler]);\n\n    // Set up timer\n    useEffect(() => {\n        const timeoutID = window.setTimeout(() => {\n            savedHandler.current?.();\n        }, timeoutMs);\n        return () => clearTimeout(timeoutID);\n    }, [timeoutMs]);\n};\n\n// Hook to simplify intervals in functional components\nexport const useInterval = (handler: Handler, intervalMs: number): void => {\n    // Create a ref that stores handler\n    const savedHandler = useRef<Handler>(undefined);\n\n    // Update ref.current value if handler changes.\n    useEffect(() => {\n        savedHandler.current = handler;\n    }, [handler]);\n\n    // Set up timer\n    useEffect(() => {\n        const intervalID = window.setInterval(() => {\n            savedHandler.current?.();\n        }, intervalMs);\n        return () => clearInterval(intervalID);\n    }, [intervalMs]);\n};\n\n// Hook to simplify a variable counting down to 0, handler called when it reached 0\nexport const useExpiringCounter = (handler: Handler, intervalMs: number, initialCount: number): number => {\n    const [count, setCount] = useState(initialCount);\n    useInterval(() => setCount((c) => c - 1), intervalMs);\n    if (count === 0) {\n        handler();\n    }\n    return count;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022, 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { RoomEvent } from \"matrix-js-sdk/src/matrix\";\nimport { useCallback, useEffect, useState } from \"react\";\n\nimport type { NotificationCount, Room } from \"matrix-js-sdk/src/matrix\";\nimport { determineUnreadState } from \"../RoomNotifs\";\nimport { NotificationLevel } from \"../stores/notifications/NotificationLevel\";\nimport { useEventEmitter } from \"./useEventEmitter\";\n\nexport const useUnreadNotifications = (\n    room?: Room,\n    threadId?: string,\n): {\n    symbol: string | null;\n    count: number;\n    level: NotificationLevel;\n} => {\n    const [symbol, setSymbol] = useState<string | null>(null);\n    const [count, setCount] = useState<number>(0);\n    const [level, setLevel] = useState<NotificationLevel>(NotificationLevel.None);\n\n    useEventEmitter(\n        room,\n        RoomEvent.UnreadNotifications,\n        (unreadNotifications: NotificationCount, evtThreadId?: string) => {\n            // Discarding all events not related to the thread if one has been setup\n            if (threadId && threadId !== evtThreadId) return;\n            updateNotificationState();\n        },\n    );\n    useEventEmitter(room, RoomEvent.Receipt, () => updateNotificationState());\n    useEventEmitter(room, RoomEvent.Timeline, () => updateNotificationState());\n    useEventEmitter(room, RoomEvent.Redaction, () => updateNotificationState());\n    useEventEmitter(room, RoomEvent.LocalEchoUpdated, () => updateNotificationState());\n    useEventEmitter(room, RoomEvent.MyMembership, () => updateNotificationState());\n\n    const updateNotificationState = useCallback(() => {\n        const { symbol, count, level } = determineUnreadState(room, threadId, false);\n        setSymbol(symbol);\n        setCount(count);\n        setLevel(level);\n    }, [room, threadId]);\n\n    useEffect(() => {\n        updateNotificationState();\n    }, [updateNotificationState]);\n\n    return {\n        symbol,\n        count,\n        level,\n    };\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2016-2019 , 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { SERVICE_TYPES, type Room, type IOpenIDToken } from \"matrix-js-sdk/src/matrix\";\n\nimport SettingsStore from \"./settings/SettingsStore\";\nimport { Service, startTermsFlow, type TermsInteractionCallback, TermsNotSignedError } from \"./Terms\";\nimport { MatrixClientPeg } from \"./MatrixClientPeg\";\nimport SdkConfig from \"./SdkConfig\";\nimport { type WidgetType } from \"./widgets/WidgetType\";\nimport { parseUrl } from \"./utils/UrlUtils\";\n\n// The version of the integration manager API we're intending to work with\nconst imApiVersion = \"1.1\";\n\n// TODO: Generify the name of this class and all components within - it's not just for Scalar.\n\nexport default class ScalarAuthClient {\n    private scalarToken: string | null;\n    private termsInteractionCallback?: TermsInteractionCallback;\n    private isDefaultManager: boolean;\n\n    public constructor(\n        private apiUrl: string,\n        private uiUrl: string,\n    ) {\n        this.scalarToken = null;\n        // `undefined` to allow `startTermsFlow` to fallback to a default\n        // callback if this is unset.\n        this.termsInteractionCallback = undefined;\n\n        // We try and store the token on a per-manager basis, but need a fallback\n        // for the default manager.\n        const configApiUrl = SdkConfig.get(\"integrations_rest_url\");\n        const configUiUrl = SdkConfig.get(\"integrations_ui_url\");\n        this.isDefaultManager = apiUrl === configApiUrl && configUiUrl === uiUrl;\n    }\n\n    private writeTokenToStore(): void {\n        window.localStorage.setItem(\"mx_scalar_token_at_\" + this.apiUrl, this.scalarToken ?? \"\");\n        if (this.isDefaultManager) {\n            // We remove the old token from storage to migrate upwards. This is safe\n            // to do because even if the user switches to /app when this is on /develop\n            // they'll at worst register for a new token.\n            window.localStorage.removeItem(\"mx_scalar_token\"); // no-op when not present\n        }\n    }\n\n    private readTokenFromStore(): string | null {\n        let token = window.localStorage.getItem(\"mx_scalar_token_at_\" + this.apiUrl);\n        if (!token && this.isDefaultManager) {\n            token = window.localStorage.getItem(\"mx_scalar_token\");\n        }\n        return token;\n    }\n\n    private readToken(): string | null {\n        if (this.scalarToken) return this.scalarToken;\n        return this.readTokenFromStore();\n    }\n\n    public setTermsInteractionCallback(callback: TermsInteractionCallback): void {\n        this.termsInteractionCallback = callback;\n    }\n\n    public connect(): Promise<void> {\n        return this.getScalarToken().then((tok) => {\n            this.scalarToken = tok;\n        });\n    }\n\n    public hasCredentials(): boolean {\n        return this.scalarToken != null; // undef or null\n    }\n\n    // Returns a promise that resolves to a scalar_token string\n    public getScalarToken(): Promise<string> {\n        const token = this.readToken();\n\n        if (!token) {\n            return this.registerForToken();\n        } else {\n            return this.checkToken(token).catch((e) => {\n                if (e instanceof TermsNotSignedError) {\n                    // retrying won't help this\n                    throw e;\n                }\n                return this.registerForToken();\n            });\n        }\n    }\n\n    private async getAccountName(token: string): Promise<string> {\n        const url = new URL(this.apiUrl + \"/account\");\n        url.searchParams.set(\"scalar_token\", token);\n        url.searchParams.set(\"v\", imApiVersion);\n\n        const res = await fetch(url, {\n            method: \"GET\",\n        });\n\n        const body = await res.json();\n        if (body?.errcode === \"M_TERMS_NOT_SIGNED\") {\n            throw new TermsNotSignedError();\n        }\n\n        if (!res.ok) {\n            throw body;\n        }\n\n        if (!body?.user_id) {\n            throw new Error(\"Missing user_id in response\");\n        }\n\n        return body.user_id;\n    }\n\n    private checkToken(token: string): Promise<string> {\n        return this.getAccountName(token)\n            .then((userId) => {\n                const me = MatrixClientPeg.safeGet().getUserId();\n                if (userId !== me) {\n                    throw new Error(\"Scalar token is owned by someone else: \" + me);\n                }\n                return token;\n            })\n            .catch((e) => {\n                if (e instanceof TermsNotSignedError) {\n                    logger.log(\"Integration manager requires new terms to be agreed to\");\n                    // The terms endpoints are new and so live on standard _matrix prefixes,\n                    // but IM rest urls are currently configured with paths, so remove the\n                    // path from the base URL before passing it to the js-sdk\n\n                    // We continue to use the full URL for the calls done by\n                    // matrix-react-sdk, but the standard terms API called\n                    // by the js-sdk lives on the standard _matrix path. This means we\n                    // don't support running IMs on a non-root path, but it's the only\n                    // realistic way of transitioning to _matrix paths since configs in\n                    // the wild contain bits of the API path.\n\n                    // Once we've fully transitioned to _matrix URLs, we can give people\n                    // a grace period to update their configs, then use the rest url as\n                    // a regular base url.\n                    const parsedImRestUrl = parseUrl(this.apiUrl);\n                    parsedImRestUrl.pathname = \"\";\n                    return startTermsFlow(\n                        MatrixClientPeg.safeGet(),\n                        [new Service(SERVICE_TYPES.IM, parsedImRestUrl.toString(), token)],\n                        this.termsInteractionCallback,\n                    ).then(() => {\n                        return token;\n                    });\n                } else {\n                    throw e;\n                }\n            });\n    }\n\n    public registerForToken(): Promise<string> {\n        // Get openid bearer token from the HS as the first part of our dance\n        return MatrixClientPeg.safeGet()\n            .getOpenIdToken()\n            .then((tokenObject) => {\n                // Now we can send that to scalar and exchange it for a scalar token\n                return this.exchangeForScalarToken(tokenObject);\n            })\n            .then((token) => {\n                // Validate it (this mostly checks to see if the IM needs us to agree to some terms)\n                return this.checkToken(token);\n            })\n            .then((token) => {\n                this.scalarToken = token;\n                this.writeTokenToStore();\n                return token;\n            });\n    }\n\n    public async exchangeForScalarToken(openidTokenObject: IOpenIDToken): Promise<string> {\n        const scalarRestUrl = new URL(this.apiUrl + \"/register\");\n        scalarRestUrl.searchParams.set(\"v\", imApiVersion);\n\n        const res = await fetch(scalarRestUrl, {\n            method: \"POST\",\n            body: JSON.stringify(openidTokenObject),\n            headers: {\n                \"Content-Type\": \"application/json\",\n            },\n        });\n\n        if (!res.ok) {\n            throw new Error(`Scalar request failed: ${res.status}`);\n        }\n\n        const body = await res.json();\n        if (!body?.scalar_token) {\n            throw new Error(\"Missing scalar_token in response\");\n        }\n\n        return body.scalar_token;\n    }\n\n    public async getScalarPageTitle(url: string): Promise<string> {\n        const scalarPageLookupUrl = new URL(this.getStarterLink(this.apiUrl + \"/widgets/title_lookup\"));\n        scalarPageLookupUrl.searchParams.set(\"curl\", encodeURIComponent(url));\n\n        const res = await fetch(scalarPageLookupUrl, {\n            method: \"GET\",\n        });\n\n        if (!res.ok) {\n            throw new Error(`Scalar request failed: ${res.status}`);\n        }\n\n        const body = await res.json();\n        return body?.page_title_cache_item?.cached_title;\n    }\n\n    /**\n     * Mark all assets associated with the specified widget as \"disabled\" in the\n     * integration manager database.\n     * This can be useful to temporarily prevent purchased assets from being displayed.\n     * @param  {WidgetType} widgetType The Widget Type to disable assets for\n     * @param  {string} widgetId   The widget ID to disable assets for\n     * @return {Promise}           Resolves on completion\n     */\n    public async disableWidgetAssets(widgetType: WidgetType, widgetId: string): Promise<void> {\n        const url = new URL(this.getStarterLink(this.apiUrl + \"/widgets/set_assets_state\"));\n        url.searchParams.set(\"widget_type\", widgetType.preferred);\n        url.searchParams.set(\"widget_id\", widgetId);\n        url.searchParams.set(\"state\", \"disable\");\n\n        const res = await fetch(url, {\n            method: \"GET\", // XXX: Actions shouldn't be GET requests\n        });\n\n        if (!res.ok) {\n            throw new Error(`Scalar request failed: ${res.status}`);\n        }\n\n        const body = await res.text();\n        if (!body) {\n            throw new Error(\"Failed to set widget assets state\");\n        }\n    }\n\n    public getScalarInterfaceUrlForRoom(room: Room, screen?: string, id?: string): string {\n        const roomId = room.roomId;\n        const roomName = room.name;\n        let url = this.uiUrl;\n        if (this.scalarToken) url += \"?scalar_token=\" + encodeURIComponent(this.scalarToken);\n        url += \"&room_id=\" + encodeURIComponent(roomId);\n        url += \"&room_name=\" + encodeURIComponent(roomName);\n        url += \"&theme=\" + encodeURIComponent(SettingsStore.getValue(\"theme\"));\n        if (id) {\n            url += \"&integ_id=\" + encodeURIComponent(id);\n        }\n        if (screen) {\n            url += \"&screen=\" + encodeURIComponent(screen);\n        }\n        return url;\n    }\n\n    public getStarterLink(starterLinkUrl: string): string {\n        if (!this.scalarToken) return starterLinkUrl;\n        return starterLinkUrl + \"?scalar_token=\" + encodeURIComponent(this.scalarToken);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { type ActionPayload } from \"../../../dispatcher/payloads\";\nimport Spinner from \"../elements/Spinner\";\nimport { getKeyBindingsManager } from \"../../../KeyBindingsManager\";\nimport { KeyBindingAction } from \"../../../accessibility/KeyboardShortcuts\";\nimport Heading from \"../typography/Heading\";\n\ninterface IProps {\n    // false to display an error saying that we couldn't connect to the integration manager\n    connected?: boolean;\n\n    // true to display a loading spinner\n    loading?: boolean;\n\n    // The source URL to load\n    url?: string;\n\n    // callback when the manager is dismissed\n    onFinished: () => void;\n}\n\ninterface IState {\n    errored: boolean;\n}\n\nexport default class IntegrationManager extends React.Component<IProps, IState> {\n    private dispatcherRef?: string;\n\n    public static defaultProps: Partial<IProps> = {\n        connected: true,\n        loading: false,\n    };\n\n    public state = {\n        errored: false,\n    };\n\n    public componentDidMount(): void {\n        this.dispatcherRef = dis.register(this.onAction);\n        document.addEventListener(\"keydown\", this.onKeyDown);\n    }\n\n    public componentWillUnmount(): void {\n        dis.unregister(this.dispatcherRef);\n        document.removeEventListener(\"keydown\", this.onKeyDown);\n    }\n\n    private onKeyDown = (ev: KeyboardEvent): void => {\n        const action = getKeyBindingsManager().getAccessibilityAction(ev);\n        switch (action) {\n            case KeyBindingAction.Escape:\n                ev.stopPropagation();\n                ev.preventDefault();\n                this.props.onFinished();\n                break;\n        }\n    };\n\n    private onAction = (payload: ActionPayload): void => {\n        if (payload.action === \"close_scalar\") {\n            this.props.onFinished();\n        }\n    };\n\n    private onError = (): void => {\n        this.setState({ errored: true });\n    };\n\n    public render(): React.ReactNode {\n        if (this.props.loading) {\n            return (\n                <div className=\"mx_IntegrationManager_loading\">\n                    <Heading size=\"3\">{_t(\"integration_manager|connecting\")}</Heading>\n                    <Spinner />\n                </div>\n            );\n        }\n\n        if (!this.props.connected || this.state.errored) {\n            return (\n                <div className=\"mx_IntegrationManager_error\">\n                    <Heading size=\"3\">{_t(\"integration_manager|error_connecting_heading\")}</Heading>\n                    <p>{_t(\"integration_manager|error_connecting\")}</p>\n                </div>\n            );\n        }\n\n        return <iframe title={_t(\"common|integration_manager\")} src={this.props.url} onError={this.onError} />;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ComponentProps } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport type { Room } from \"matrix-js-sdk/src/matrix\";\nimport ScalarAuthClient from \"../ScalarAuthClient\";\nimport { dialogTermsInteractionCallback, TermsNotSignedError } from \"../Terms\";\nimport Modal from \"../Modal\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport IntegrationManager from \"../components/views/settings/IntegrationManager\";\nimport { IntegrationManagers } from \"./IntegrationManagers\";\nimport { parseUrl } from \"../utils/UrlUtils\";\n\nexport enum Kind {\n    Account = \"account\",\n    Config = \"config\",\n    Homeserver = \"homeserver\",\n}\n\nexport class IntegrationManagerInstance {\n    // Per the spec: UI URL is optional.\n    public constructor(\n        public readonly kind: string,\n        public readonly apiUrl: string,\n        public readonly uiUrl: string = apiUrl,\n        public readonly id?: string, // only applicable in some cases\n    ) {}\n\n    public get name(): string {\n        const parsed = parseUrl(this.uiUrl);\n        return parsed.host ?? \"\";\n    }\n\n    public get trimmedApiUrl(): string {\n        const parsed = parseUrl(this.apiUrl);\n        parsed.pathname = \"\";\n        return parsed.toString();\n    }\n\n    public getScalarClient(): ScalarAuthClient {\n        return new ScalarAuthClient(this.apiUrl, this.uiUrl);\n    }\n\n    public async open(room: Room, screen?: string, integrationId?: string): Promise<void> {\n        if (!SettingsStore.getValue(\"integrationProvisioning\")) {\n            return IntegrationManagers.sharedInstance().showDisabledDialog();\n        }\n\n        const dialog = Modal.createDialog(IntegrationManager, { loading: true }, \"mx_IntegrationManager\");\n\n        const client = this.getScalarClient();\n        client.setTermsInteractionCallback((policyInfo, agreedUrls) => {\n            // To avoid visual glitching of two modals stacking briefly, we customise the\n            // terms dialog sizing when it will appear for the integration manager so that\n            // it gets the same basic size as the integration manager's own modal.\n            return dialogTermsInteractionCallback(policyInfo, agreedUrls, \"mx_TermsDialog_forIntegrationManager\");\n        });\n\n        const newProps: Partial<ComponentProps<typeof IntegrationManager>> = {};\n        try {\n            await client.connect();\n            if (!client.hasCredentials()) {\n                newProps[\"connected\"] = false;\n            } else {\n                newProps[\"url\"] = client.getScalarInterfaceUrlForRoom(room, screen, integrationId);\n            }\n        } catch (e) {\n            if (e instanceof TermsNotSignedError) {\n                dialog.close();\n                return;\n            }\n\n            logger.error(e);\n            newProps[\"connected\"] = false;\n        }\n\n        // Close the old dialog and open a new one\n        dialog.close();\n        Modal.createDialog(IntegrationManager, newProps, \"mx_IntegrationManager\");\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\nimport SdkConfig from \"../../../SdkConfig\";\nimport BaseDialog from \"./BaseDialog\";\nimport DialogButtons from \"../elements/DialogButtons\";\n\ninterface IProps {\n    onFinished(): void;\n}\n\nexport default class IntegrationsImpossibleDialog extends React.Component<IProps> {\n    private onAcknowledgeClick = (): void => {\n        this.props.onFinished();\n    };\n\n    public render(): React.ReactNode {\n        const brand = SdkConfig.get().brand;\n\n        return (\n            <BaseDialog\n                className=\"mx_IntegrationsImpossibleDialog\"\n                hasCancel={false}\n                onFinished={this.props.onFinished}\n                title={_t(\"integrations|impossible_dialog_title\")}\n            >\n                <div className=\"mx_IntegrationsImpossibleDialog_content\">\n                    <p>{_t(\"integrations|impossible_dialog_description\", { brand })}</p>\n                </div>\n                <DialogButtons\n                    primaryButton={_t(\"action|ok\")}\n                    onPrimaryButtonClick={this.onAcknowledgeClick}\n                    hasCancel={false}\n                />\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024, 2025 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useCallback } from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\nimport dis from \"../../../dispatcher/dispatcher\";\nimport { Action } from \"../../../dispatcher/actions\";\nimport BaseDialog from \"./BaseDialog\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport { UserTab } from \"./UserTab\";\n\ninterface IProps {\n    onFinished(): void;\n}\n\nexport const IntegrationsDisabledDialog: React.FC<IProps> = ({ onFinished }) => {\n    const onOpenSettingsClick = useCallback(() => {\n        onFinished();\n        dis.dispatch({\n            action: Action.ViewUserSettings,\n            initialTabId: UserTab.Security,\n        });\n    }, [onFinished]);\n\n    return (\n        <BaseDialog\n            className=\"mx_IntegrationsDisabledDialog\"\n            hasCancel={true}\n            onFinished={onFinished}\n            title={_t(\"integrations|disabled_dialog_title\")}\n        >\n            <div className=\"mx_IntegrationsDisabledDialog_content\">\n                <p>\n                    {_t(\"integrations|disabled_dialog_description\", {\n                        manageIntegrations: _t(\"integration_manager|manage_title\"),\n                    })}\n                </p>\n            </div>\n            <DialogButtons\n                primaryButton={_t(\"common|settings\")}\n                onPrimaryButtonClick={onOpenSettingsClick}\n                cancelButton={_t(\"action|ok\")}\n                onCancel={onFinished}\n            />\n        </BaseDialog>\n    );\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { ClientEvent, type IClientWellKnown, type MatrixClient, type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport SdkConfig from \"../SdkConfig\";\nimport Modal from \"../Modal\";\nimport { IntegrationManagerInstance, Kind } from \"./IntegrationManagerInstance\";\nimport IntegrationsImpossibleDialog from \"../components/views/dialogs/IntegrationsImpossibleDialog\";\nimport { IntegrationsDisabledDialog } from \"../components/views/dialogs/IntegrationsDisabledDialog\";\nimport WidgetUtils from \"../utils/WidgetUtils\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\n\nconst KIND_PREFERENCE = [\n    // Ordered: first is most preferred, last is least preferred.\n    Kind.Account,\n    Kind.Homeserver,\n    Kind.Config,\n];\n\nexport class IntegrationManagers {\n    private static instance?: IntegrationManagers;\n\n    private managers: IntegrationManagerInstance[] = [];\n    private client?: MatrixClient;\n    private primaryManager: IntegrationManagerInstance | null = null;\n\n    public static sharedInstance(): IntegrationManagers {\n        if (!IntegrationManagers.instance) {\n            IntegrationManagers.instance = new IntegrationManagers();\n        }\n        return IntegrationManagers.instance;\n    }\n\n    public constructor() {\n        this.compileManagers();\n    }\n\n    public startWatching(): void {\n        this.stopWatching();\n        this.client = MatrixClientPeg.safeGet();\n        this.client.on(ClientEvent.AccountData, this.onAccountData);\n        this.client.on(ClientEvent.ClientWellKnown, this.setupHomeserverManagers);\n        this.compileManagers();\n    }\n\n    public stopWatching(): void {\n        if (!this.client) return;\n        this.client.removeListener(ClientEvent.AccountData, this.onAccountData);\n        this.client.removeListener(ClientEvent.ClientWellKnown, this.setupHomeserverManagers);\n    }\n\n    private compileManagers(): void {\n        this.managers = [];\n        this.setupConfiguredManager();\n        this.setupAccountManagers();\n    }\n\n    private setupConfiguredManager(): void {\n        const apiUrl = SdkConfig.get(\"integrations_rest_url\");\n        const uiUrl = SdkConfig.get(\"integrations_ui_url\");\n\n        if (apiUrl && uiUrl) {\n            this.managers.push(new IntegrationManagerInstance(Kind.Config, apiUrl, uiUrl));\n            this.primaryManager = null; // reset primary\n        }\n    }\n\n    private setupHomeserverManagers = async (discoveryResponse: IClientWellKnown): Promise<void> => {\n        logger.log(\"Updating homeserver-configured integration managers...\");\n        if (discoveryResponse && discoveryResponse[\"m.integrations\"]) {\n            let managers = discoveryResponse[\"m.integrations\"][\"managers\"];\n            if (!Array.isArray(managers)) managers = []; // make it an array so we can wipe the HS managers\n\n            logger.log(`Homeserver has ${managers.length} integration managers`);\n\n            // Clear out any known managers for the homeserver\n            // TODO: Log out of the scalar clients\n            this.managers = this.managers.filter((m) => m.kind !== Kind.Homeserver);\n\n            // Now add all the managers the homeserver wants us to have\n            for (const hsManager of managers) {\n                if (!hsManager[\"api_url\"]) continue;\n                this.managers.push(\n                    new IntegrationManagerInstance(\n                        Kind.Homeserver,\n                        hsManager[\"api_url\"],\n                        hsManager[\"ui_url\"], // optional\n                    ),\n                );\n            }\n\n            this.primaryManager = null; // reset primary\n        } else {\n            logger.log(\"Homeserver has no integration managers\");\n        }\n    };\n\n    private setupAccountManagers(): void {\n        if (!this.client || !this.client.getUserId()) return; // not logged in\n        const widgets = WidgetUtils.getIntegrationManagerWidgets(this.client);\n        widgets.forEach((w) => {\n            const data = w.content[\"data\"];\n            if (!data) return;\n\n            const uiUrl = w.content[\"url\"];\n            const apiUrl = data[\"api_url\"] as string;\n            if (!apiUrl || !uiUrl) return;\n\n            const manager = new IntegrationManagerInstance(\n                Kind.Account,\n                apiUrl,\n                uiUrl,\n                w[\"id\"] || w[\"state_key\"] || \"\",\n            );\n            this.managers.push(manager);\n        });\n        this.primaryManager = null; // reset primary\n    }\n\n    private onAccountData = (ev: MatrixEvent): void => {\n        if (ev.getType() === \"m.widgets\") {\n            this.compileManagers();\n        }\n    };\n\n    public hasManager(): boolean {\n        return this.managers.length > 0;\n    }\n\n    public getOrderedManagers(): IntegrationManagerInstance[] {\n        const collator = new Intl.Collator();\n        const ordered: IntegrationManagerInstance[] = [];\n        for (const kind of KIND_PREFERENCE) {\n            const managers = this.managers.filter((m) => m.kind === kind);\n            if (!managers || !managers.length) continue;\n\n            if (kind === Kind.Account) {\n                // Order by state_keys (IDs)\n                managers.sort((a, b) => collator.compare(a.id ?? \"\", b.id ?? \"\"));\n            }\n\n            ordered.push(...managers);\n        }\n        return ordered;\n    }\n\n    public getPrimaryManager(): IntegrationManagerInstance | null {\n        if (this.hasManager()) {\n            if (this.primaryManager) return this.primaryManager;\n\n            this.primaryManager = this.getOrderedManagers()[0];\n            return this.primaryManager;\n        } else {\n            return null;\n        }\n    }\n\n    public openNoManagerDialog(): void {\n        Modal.createDialog(IntegrationsImpossibleDialog);\n    }\n\n    public showDisabledDialog(): void {\n        Modal.createDialog(IntegrationsDisabledDialog);\n    }\n}\n\n// For debugging\nwindow.mxIntegrationManagers = IntegrationManagers;\n","/*\n * Copyright 2025 New Vector Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { MapWithDefault } from \"matrix-js-sdk/src/utils\";\nimport { type TranslationStringsObject } from \"@matrix-org/react-sdk-module-api\";\nimport _ from \"lodash\";\nimport {\n    _t,\n    normalizeLanguageKey,\n    type IVariables,\n    KEY_SEPARATOR,\n    getLangsJson,\n    registerTranslations,\n    setLocale,\n    getLocale,\n    setMissingEntryGenerator as setMissingEntryGeneratorSharedComponents,\n} from \"@element-hq/web-shared-components\";\n\nimport SettingsStore from \"./settings/SettingsStore\";\nimport PlatformPeg from \"./PlatformPeg\";\nimport { SettingLevel } from \"./settings/SettingLevel\";\nimport { retry } from \"./utils/promise\";\nimport SdkConfig from \"./SdkConfig\";\nimport { ModuleRunner } from \"./modules/ModuleRunner\";\n\nexport {\n    _t,\n    type IVariables,\n    type Tags,\n    type TranslatedString,\n    _td,\n    _tDom,\n    lookupString,\n    sanitizeForTranslation,\n    normalizeLanguageKey,\n    getNormalizedLanguageKeys,\n    substitute,\n} from \"@element-hq/web-shared-components\";\n\nconst i18nFolder = \"i18n/\";\n\nexport interface ErrorOptions {\n    // Because we're mixing the substitution variables and `cause` into the same object\n    // below, we want them to always explicitly say whether there is an underlying error\n    // or not to avoid typos of \"cause\" slipping through unnoticed.\n    cause: unknown | undefined;\n}\n\n/**\n * Used to rethrow an error with a user-friendly translatable message while maintaining\n * access to that original underlying error. Downstream consumers can display the\n * `translatedMessage` property in the UI and inspect the underlying error with the\n * `cause` property.\n *\n * The error message will display as English in the console and logs so Element\n * developers can easily understand the error and find the source in the code. It also\n * helps tools like Sentry deduplicate the error, or just generally searching in\n * rageshakes to find all instances regardless of the users locale.\n *\n * @param message - The untranslated error message text, e.g \"Something went wrong with %(foo)s\".\n * @param substitutionVariablesAndCause - Variable substitutions for the translation and\n * original cause of the error. If there is no cause, just pass `undefined`, e.g { foo:\n * 'bar', cause: err || undefined }\n */\nexport class UserFriendlyError extends Error {\n    public readonly translatedMessage: string;\n\n    public constructor(\n        message: TranslationKey,\n        substitutionVariablesAndCause?: Omit<IVariables, keyof ErrorOptions> | ErrorOptions,\n    ) {\n        // Prevent \"Could not find /%\\(cause\\)s/g in x\" logs to the console by removing it from the list\n        const { cause, ...substitutionVariables } = substitutionVariablesAndCause ?? {};\n        const errorOptions = { cause };\n\n        // Create the error with the English version of the message that we want to show up in the logs\n        const englishTranslatedMessage = _t(message, { ...substitutionVariables, locale: \"en\" });\n        super(englishTranslatedMessage, errorOptions);\n\n        // Also provide a translated version of the error in the users locale to display\n        this.translatedMessage = _t(message, substitutionVariables);\n    }\n}\n\nexport function getUserLanguage(): string {\n    const language = SettingsStore.getValue(\"language\", null, /*excludeDefault:*/ true);\n    if (typeof language === \"string\" && language !== \"\") {\n        return language;\n    } else {\n        return normalizeLanguageKey(getLanguageFromBrowser());\n    }\n}\n\n// Allow overriding the text displayed when no translation exists\n// Currently only used in unit tests to avoid having to load\n// the translations in element-web\nexport function setMissingEntryGenerator(f: (value: string) => void): void {\n    setMissingEntryGeneratorSharedComponents(f);\n}\n\nexport async function setLanguage(...preferredLangs: string[]): Promise<void> {\n    PlatformPeg.get()?.setLanguage(preferredLangs);\n\n    const availableLanguages = await getLangsJson();\n    let chosenLanguage = preferredLangs.find((lang) => availableLanguages.hasOwnProperty(lang));\n    if (!chosenLanguage) {\n        // Fallback to en_EN if none is found\n        chosenLanguage = \"en\";\n        logger.error(\"Unable to find an appropriate language, preferred: \", preferredLangs);\n    }\n\n    const languageData = await getLanguageRetry(i18nFolder + availableLanguages[chosenLanguage]);\n\n    registerTranslations(chosenLanguage, languageData);\n    setLocale(chosenLanguage);\n\n    await SettingsStore.setValue(\"language\", null, SettingLevel.DEVICE, chosenLanguage);\n    // Adds a lot of noise to test runs, so disable logging there.\n    if (process.env.NODE_ENV !== \"test\") {\n        logger.log(\"set language to \" + chosenLanguage);\n    }\n\n    // Set 'en' as fallback language:\n    if (chosenLanguage !== \"en\") {\n        const fallbackLanguageData = await getLanguageRetry(i18nFolder + availableLanguages[\"en\"]);\n        registerTranslations(\"en\", fallbackLanguageData);\n    }\n\n    await registerCustomTranslations();\n}\n\ntype Language = {\n    value: string;\n    label: string; // translated\n    labelInTargetLanguage: string; // translated\n};\n\nexport async function getAllLanguagesFromJson(): Promise<string[]> {\n    return Object.keys(await getLangsJson());\n}\n\nexport async function getAllLanguagesWithLabels(): Promise<Language[]> {\n    const languageNames = new Intl.DisplayNames([getUserLanguage()], { type: \"language\", style: \"short\" });\n    const languages = await getAllLanguagesFromJson();\n    return languages.map<Language>((langKey) => {\n        return {\n            value: langKey,\n            label: languageNames.of(langKey)!,\n            labelInTargetLanguage: new Intl.DisplayNames([langKey], { type: \"language\", style: \"short\" }).of(langKey)!,\n        };\n    });\n}\n\nexport function getLanguagesFromBrowser(): readonly string[] {\n    if (navigator.languages && navigator.languages.length) return navigator.languages;\n    return [navigator.language ?? \"en\"];\n}\n\nexport function getLanguageFromBrowser(): string {\n    return getLanguagesFromBrowser()[0];\n}\n\nexport function getCurrentLanguage(): string {\n    return getLocale();\n}\n\n/**\n * Given a list of language codes, pick the most appropriate one\n * given the current language (ie. getCurrentLanguage())\n * English is assumed to be a reasonable default.\n *\n * @param {string[]} langs List of language codes to pick from\n * @returns {string} The most appropriate language code from langs\n */\nexport function pickBestLanguage(langs: string[]): string {\n    const currentLang = getCurrentLanguage();\n    const normalisedLangs = langs.map(normalizeLanguageKey);\n\n    {\n        // Best is an exact match\n        const currentLangIndex = normalisedLangs.indexOf(currentLang);\n        if (currentLangIndex > -1) return langs[currentLangIndex];\n    }\n\n    {\n        // Failing that, a different dialect of the same language\n        const closeLangIndex = normalisedLangs.findIndex((l) => l.slice(0, 2) === currentLang.slice(0, 2));\n        if (closeLangIndex > -1) return langs[closeLangIndex];\n    }\n\n    {\n        // Neither of those? Try an english variant.\n        const enIndex = normalisedLangs.findIndex((l) => l.startsWith(\"en\"));\n        if (enIndex > -1) return langs[enIndex];\n    }\n\n    // if nothing else, use the first\n    return langs[0];\n}\n\ninterface ICounterpartTranslation {\n    [key: string]:\n        | string\n        | {\n              [pluralisation: string]: string;\n          };\n}\n\nasync function getLanguageRetry(langPath: string, num = 3): Promise<ICounterpartTranslation> {\n    return retry(\n        () => getLanguage(langPath),\n        num,\n        (e) => {\n            logger.log(\"Failed to load i18n\", langPath);\n            logger.error(e);\n            return true; // always retry\n        },\n    );\n}\n\nasync function getLanguage(langPath: string): Promise<ICounterpartTranslation> {\n    const res = await fetch(langPath, { method: \"GET\" });\n\n    if (!res.ok) {\n        throw new Error(`Failed to load ${langPath}, got ${res.status}`);\n    }\n\n    return res.json();\n}\n\nlet cachedCustomTranslations: TranslationStringsObject | undefined;\nlet cachedCustomTranslationsExpire = 0; // zero to trigger expiration right away\n\n// This awkward class exists so the test runner can get at the function. It is\n// not intended for practical or realistic usage.\nexport class CustomTranslationOptions {\n    public static lookupFn?: (url: string) => TranslationStringsObject;\n\n    private constructor() {\n        // static access for tests only\n    }\n}\n\nfunction doRegisterTranslations(customTranslations: TranslationStringsObject): void {\n    // We convert the operator-friendly version into something counterpart can consume.\n    // Map: lang → Record: string → translation\n    const langs: MapWithDefault<string, Record<string, string>> = new MapWithDefault(() => ({}));\n    for (const [translationKey, translations] of Object.entries(customTranslations)) {\n        for (const [lang, translation] of Object.entries(translations)) {\n            _.set(langs.getOrCreate(lang), translationKey.split(KEY_SEPARATOR), translation);\n        }\n    }\n\n    // Finally, tell counterpart about our translations\n    for (const [lang, translations] of langs) {\n        registerTranslations(lang, translations);\n    }\n}\n\n/**\n * Any custom modules with translations to load are parsed first, followed by an\n * optionally defined translations file in the config. If no customization is made,\n * or the file can't be parsed, no action will be taken.\n *\n * This function should be called *after* registering other translations data to\n * ensure it overrides strings properly.\n */\nexport async function registerCustomTranslations({\n    testOnlyIgnoreCustomTranslationsCache = false,\n}: {\n    testOnlyIgnoreCustomTranslationsCache?: boolean;\n} = {}): Promise<void> {\n    const moduleTranslations = ModuleRunner.instance.allTranslations;\n    doRegisterTranslations(moduleTranslations);\n\n    const lookupUrl = SdkConfig.get().custom_translations_url;\n    if (!lookupUrl) return; // easy - nothing to do\n\n    try {\n        let json: TranslationStringsObject | undefined;\n        if (testOnlyIgnoreCustomTranslationsCache || Date.now() >= cachedCustomTranslationsExpire) {\n            json = CustomTranslationOptions.lookupFn\n                ? CustomTranslationOptions.lookupFn(lookupUrl)\n                : ((await (await fetch(lookupUrl)).json()) as TranslationStringsObject);\n            cachedCustomTranslations = json;\n\n            // Set expiration to the future, but not too far. Just trying to avoid\n            // repeated, successive, calls to the server rather than anything long-term.\n            cachedCustomTranslationsExpire = Date.now() + 5 * 60 * 1000;\n        } else {\n            json = cachedCustomTranslations;\n        }\n\n        // If the (potentially cached) json is invalid, don't use it.\n        if (!json) return;\n\n        // Finally, register it.\n        doRegisterTranslations(json);\n    } catch (e) {\n        // We consume all exceptions because it's considered non-fatal for custom\n        // translations to break. Most failures will be during initial development\n        // of the json file and not (hopefully) at runtime.\n        logger.warn(\"Ignoring error while registering custom translations: \", e);\n\n        // Like above: trigger a cache of the json to avoid successive calls.\n        cachedCustomTranslationsExpire = Date.now() + 5 * 60 * 1000;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport * as linkifyjs from \"linkifyjs\";\nimport { type EventListeners, type Opts, registerCustomProtocol, registerPlugin } from \"linkifyjs\";\nimport linkifyString from \"linkify-string\";\nimport linkifyHtml from \"linkify-html\";\nimport { getHttpUriForMxc, User } from \"matrix-js-sdk/src/matrix\";\n\nimport {\n    parsePermalink,\n    tryTransformEntityToPermalink,\n    tryTransformPermalinkToLocalHref,\n} from \"./utils/permalinks/Permalinks\";\nimport dis from \"./dispatcher/dispatcher\";\nimport { Action } from \"./dispatcher/actions\";\nimport { type ViewUserPayload } from \"./dispatcher/payloads/ViewUserPayload\";\nimport { type ViewRoomPayload } from \"./dispatcher/payloads/ViewRoomPayload\";\nimport { MatrixClientPeg } from \"./MatrixClientPeg\";\nimport { PERMITTED_URL_SCHEMES } from \"./utils/UrlUtils\";\n\nexport enum Type {\n    URL = \"url\",\n    UserId = \"userid\",\n    RoomAlias = \"roomalias\",\n}\n\nfunction matrixOpaqueIdLinkifyParser({\n    scanner,\n    parser,\n    token,\n    name,\n}: {\n    scanner: linkifyjs.ScannerInit;\n    parser: linkifyjs.ParserInit;\n    token: \"#\" | \"+\" | \"@\";\n    name: Type;\n}): void {\n    const {\n        DOT,\n        // IPV4 necessity\n        NUM,\n        COLON,\n        SYM,\n        SLASH,\n        EQUALS,\n        HYPHEN,\n        UNDERSCORE,\n    } = scanner.tokens;\n\n    // Contains NUM, WORD, UWORD, EMOJI, TLD, UTLD, SCHEME, SLASH_SCHEME and LOCALHOST plus custom protocols (e.g. \"matrix\")\n    const { domain } = scanner.tokens.groups;\n\n    // Tokens we need that are not contained in the domain group\n    const additionalLocalpartTokens = [DOT, SYM, SLASH, EQUALS, UNDERSCORE, HYPHEN];\n    const additionalDomainpartTokens = [HYPHEN];\n\n    const matrixToken = linkifyjs.createTokenClass(name, { isLink: true });\n    const matrixTokenState = new linkifyjs.State(matrixToken) as any as linkifyjs.State<linkifyjs.MultiToken>; // linkify doesn't appear to type this correctly\n\n    const matrixTokenWithPort = linkifyjs.createTokenClass(name, { isLink: true });\n    const matrixTokenWithPortState = new linkifyjs.State(\n        matrixTokenWithPort,\n    ) as any as linkifyjs.State<linkifyjs.MultiToken>; // linkify doesn't appear to type this correctly\n\n    const INITIAL_STATE = parser.start.tt(token);\n\n    // Localpart\n    const LOCALPART_STATE = new linkifyjs.State<linkifyjs.MultiToken>();\n    INITIAL_STATE.ta(domain, LOCALPART_STATE);\n    INITIAL_STATE.ta(additionalLocalpartTokens, LOCALPART_STATE);\n    LOCALPART_STATE.ta(domain, LOCALPART_STATE);\n    LOCALPART_STATE.ta(additionalLocalpartTokens, LOCALPART_STATE);\n\n    // Domainpart\n    const DOMAINPART_STATE_DOT = LOCALPART_STATE.tt(COLON);\n    DOMAINPART_STATE_DOT.ta(domain, matrixTokenState);\n    DOMAINPART_STATE_DOT.ta(additionalDomainpartTokens, matrixTokenState);\n    matrixTokenState.ta(domain, matrixTokenState);\n    matrixTokenState.ta(additionalDomainpartTokens, matrixTokenState);\n    matrixTokenState.tt(DOT, DOMAINPART_STATE_DOT);\n\n    // Port suffixes\n    matrixTokenState.tt(COLON).tt(NUM, matrixTokenWithPortState);\n}\n\nfunction onUserClick(event: MouseEvent, userId: string): void {\n    event.preventDefault();\n    dis.dispatch<ViewUserPayload>({\n        action: Action.ViewUser,\n        member: new User(userId),\n    });\n}\n\nfunction onAliasClick(event: MouseEvent, roomAlias: string): void {\n    event.preventDefault();\n    dis.dispatch<ViewRoomPayload>({\n        action: Action.ViewRoom,\n        room_alias: roomAlias,\n        metricsTrigger: \"Timeline\",\n        metricsViaKeyboard: false,\n    });\n}\n\nconst escapeRegExp = function (s: string): string {\n    return s.replace(/[.*+?^${}()|[\\]\\\\]/g, \"\\\\$&\");\n};\n\n// Recognise URLs from both our local and official Element deployments.\n// Anyone else really should be using matrix.to. vector:// allowed to support Element Desktop relative links.\nexport const ELEMENT_URL_PATTERN =\n    \"^(?:vector://|https?://)?(?:\" +\n    escapeRegExp(window.location.host + window.location.pathname) +\n    \"|\" +\n    \"(?:www\\\\.)?(?:riot|vector)\\\\.im/(?:app|beta|staging|develop)/|\" +\n    \"(?:app|beta|staging|develop)\\\\.element\\\\.io/\" +\n    \")(#.*)\";\n\n// Attach click handlers to links based on their type\nfunction events(href: string, type: string): EventListeners {\n    switch (type as Type) {\n        case Type.URL: {\n            // intercept local permalinks to users and show them like userids (in userinfo of current room)\n            try {\n                const permalink = parsePermalink(href);\n                if (permalink?.userId) {\n                    return {\n                        click: function (e: MouseEvent) {\n                            onUserClick(e, permalink.userId!);\n                        },\n                    };\n                } else {\n                    // for events, rooms etc. (anything other than users)\n                    const localHref = tryTransformPermalinkToLocalHref(href);\n                    if (localHref !== href) {\n                        // it could be converted to a localHref -> therefore handle locally\n                        return {\n                            click: function (e: MouseEvent) {\n                                e.preventDefault();\n                                window.location.hash = localHref;\n                            },\n                        };\n                    }\n                }\n            } catch {\n                // OK fine, it's not actually a permalink\n            }\n            break;\n        }\n        case Type.UserId:\n            return {\n                click: function (e: MouseEvent) {\n                    e.preventDefault();\n                    const userId = parsePermalink(href)?.userId ?? href;\n                    if (userId) onUserClick(e, userId);\n                },\n            };\n        case Type.RoomAlias:\n            return {\n                click: function (e: MouseEvent) {\n                    e.preventDefault();\n                    const alias = parsePermalink(href)?.roomIdOrAlias ?? href;\n                    if (alias) onAliasClick(e, alias);\n                },\n            };\n    }\n\n    return {};\n}\n\n// linkify-react doesn't respect `events` and needs it mapping to React attributes\n// so we need to manually add the click handler to the attributes\n// https://linkify.js.org/docs/linkify-react.html#events\nfunction attributes(href: string, type: string): Record<string, unknown> {\n    const attrs: Record<string, unknown> = {\n        rel: \"noreferrer noopener\",\n    };\n\n    const options = events(href, type);\n    if (options?.click) {\n        attrs.onClick = options.click;\n    }\n\n    return attrs;\n}\n\nexport const options: Opts = {\n    events,\n\n    formatHref: function (href: string, type: Type | string): string {\n        switch (type) {\n            case \"url\":\n                if (href.startsWith(\"mxc://\") && MatrixClientPeg.get()) {\n                    return getHttpUriForMxc(\n                        MatrixClientPeg.get()!.baseUrl,\n                        href,\n                        undefined,\n                        undefined,\n                        undefined,\n                        false,\n                        true,\n                    );\n                }\n            // fallthrough\n            case Type.RoomAlias:\n            case Type.UserId:\n            default: {\n                return tryTransformEntityToPermalink(MatrixClientPeg.safeGet(), href) ?? \"\";\n            }\n        }\n    },\n\n    attributes,\n\n    ignoreTags: [\"a\", \"pre\", \"code\"],\n\n    className: \"linkified\",\n\n    target: function (href: string, type: Type | string): string {\n        if (type === Type.URL) {\n            try {\n                const transformed = tryTransformPermalinkToLocalHref(href);\n                if (\n                    transformed !== href || // if it could be converted to handle locally for matrix symbols e.g. @user:server.tdl and matrix.to\n                    decodeURIComponent(href).match(ELEMENT_URL_PATTERN) // for https links to Element domains\n                ) {\n                    return \"\";\n                } else {\n                    return \"_blank\";\n                }\n            } catch {\n                // malformed URI\n            }\n        }\n        return \"\";\n    },\n};\n\n// Run the plugins\nregisterPlugin(Type.RoomAlias, ({ scanner, parser }) => {\n    const token = scanner.tokens.POUND as \"#\";\n    matrixOpaqueIdLinkifyParser({\n        scanner,\n        parser,\n        token,\n        name: Type.RoomAlias,\n    });\n});\n\nregisterPlugin(Type.UserId, ({ scanner, parser }) => {\n    const token = scanner.tokens.AT as \"@\";\n    matrixOpaqueIdLinkifyParser({\n        scanner,\n        parser,\n        token,\n        name: Type.UserId,\n    });\n});\n\n// Linkify supports some common protocols but not others, register all permitted url schemes if unsupported\n// https://github.com/Hypercontext/linkifyjs/blob/f4fad9df1870259622992bbfba38bfe3d0515609/packages/linkifyjs/src/scanner.js#L133-L141\n// This also handles registering the `matrix:` protocol scheme\nconst linkifySupportedProtocols = [\"file\", \"mailto\", \"http\", \"https\", \"ftp\", \"ftps\"];\nconst optionalSlashProtocols = [\n    \"bitcoin\",\n    \"geo\",\n    \"im\",\n    \"magnet\",\n    \"mailto\",\n    \"matrix\",\n    \"news\",\n    \"openpgp4fpr\",\n    \"sip\",\n    \"sms\",\n    \"smsto\",\n    \"tel\",\n    \"urn\",\n    \"xmpp\",\n];\n\nPERMITTED_URL_SCHEMES.forEach((scheme) => {\n    if (!linkifySupportedProtocols.includes(scheme)) {\n        registerCustomProtocol(scheme, optionalSlashProtocols.includes(scheme));\n    }\n});\n\nregisterCustomProtocol(\"mxc\", false);\n\nexport const linkify = linkifyjs;\nexport const _linkifyString = linkifyString;\nexport const _linkifyHtml = linkifyHtml;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport globToRegexp from \"glob-to-regexp\";\n\n// Taken with permission from matrix-bot-sdk:\n// https://github.com/turt2live/matrix-js-bot-sdk/blob/eb148c2ecec7bf3ade801d73deb43df042d55aef/src/MatrixGlob.ts\n\n/**\n * Represents a common Matrix glob. This is commonly used\n * for server ACLs and similar functions.\n */\nexport class MatrixGlob {\n    private regex: RegExp;\n\n    /**\n     * Creates a new Matrix Glob\n     * @param {string} glob The glob to convert. Eg: \"*.example.org\"\n     */\n    public constructor(glob: string) {\n        const globRegex = globToRegexp(glob, {\n            extended: false,\n            globstar: false,\n        });\n\n        // We need to convert `?` manually because globToRegexp's extended mode\n        // does more than we want it to.\n        const replaced = globRegex.toString().replace(/\\\\\\?/g, \".\");\n        this.regex = new RegExp(replaced.substring(1, replaced.length - 1));\n    }\n\n    /**\n     * Tests the glob against a value, returning true if it matches.\n     * @param {string} val The value to test.\n     * @returns {boolean} True if the value matches the glob, false otherwise.\n     */\n    public test(val: string): boolean {\n        return this.regex.test(val);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// We are using experimental APIs here, so we need to disable the linter\n// eslint-disable-next-line no-restricted-imports\nimport { PolicyRecommendation } from \"matrix-js-sdk/src/models/invites-ignorer\";\n\nimport { MatrixGlob } from \"../utils/MatrixGlob\";\n\n// Inspiration largely taken from Mjolnir itself\n\nexport const RECOMMENDATION_BAN = PolicyRecommendation.Ban;\nexport const RECOMMENDATION_BAN_TYPES: PolicyRecommendation[] = [\n    RECOMMENDATION_BAN,\n    \"org.matrix.mjolnir.ban\" as PolicyRecommendation,\n];\n\nexport function recommendationToStable(\n    recommendation: PolicyRecommendation,\n    unstable = true,\n): PolicyRecommendation | null {\n    if (RECOMMENDATION_BAN_TYPES.includes(recommendation)) {\n        return unstable ? RECOMMENDATION_BAN_TYPES[RECOMMENDATION_BAN_TYPES.length - 1] : RECOMMENDATION_BAN;\n    }\n    return null;\n}\n\nexport class ListRule {\n    private _glob: MatrixGlob;\n    private readonly _entity: string;\n    private readonly _action: string | null;\n    private readonly _reason: string;\n    private readonly _kind: string;\n\n    public constructor(entity: string, action: PolicyRecommendation, reason: string, kind: string) {\n        this._glob = new MatrixGlob(entity);\n        this._entity = entity;\n        this._action = recommendationToStable(action, false);\n        this._reason = reason;\n        this._kind = kind;\n    }\n\n    public get entity(): string {\n        return this._entity;\n    }\n\n    public get reason(): string {\n        return this._reason;\n    }\n\n    public get kind(): string {\n        return this._kind;\n    }\n\n    public get recommendation(): string | null {\n        return this._action;\n    }\n\n    public isMatch(entity: string): boolean {\n        return this._glob.test(entity);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// Inspiration largely taken from Mjolnir itself\n\nimport { EventType } from \"matrix-js-sdk/src/matrix\";\n\nimport { ListRule, RECOMMENDATION_BAN, recommendationToStable } from \"./ListRule\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\n\nexport const RULE_USER = EventType.PolicyRuleUser;\nexport const RULE_ROOM = EventType.PolicyRuleRoom;\nexport const RULE_SERVER = EventType.PolicyRuleServer;\n\n// m.room.* events are legacy from when MSC2313 changed to m.policy.* last minute.\nexport const USER_RULE_TYPES = [RULE_USER, \"m.room.rule.user\", \"org.matrix.mjolnir.rule.user\"];\nexport const ROOM_RULE_TYPES = [RULE_ROOM, \"m.room.rule.room\", \"org.matrix.mjolnir.rule.room\"];\nexport const SERVER_RULE_TYPES = [RULE_SERVER, \"m.room.rule.server\", \"org.matrix.mjolnir.rule.server\"];\nexport const ALL_RULE_TYPES = [...USER_RULE_TYPES, ...ROOM_RULE_TYPES, ...SERVER_RULE_TYPES];\n\nexport function ruleTypeToStable(\n    rule: string,\n): EventType.PolicyRuleUser | EventType.PolicyRuleRoom | EventType.PolicyRuleServer | null {\n    if (USER_RULE_TYPES.includes(rule)) {\n        return RULE_USER;\n    }\n    if (ROOM_RULE_TYPES.includes(rule)) {\n        return RULE_ROOM;\n    }\n    if (SERVER_RULE_TYPES.includes(rule)) {\n        return RULE_SERVER;\n    }\n    return null;\n}\n\nexport class BanList {\n    private _rules: ListRule[] = [];\n    private _roomId: string;\n\n    public constructor(roomId: string) {\n        this._roomId = roomId;\n        this.updateList();\n    }\n\n    public get roomId(): string {\n        return this._roomId;\n    }\n\n    public get serverRules(): ListRule[] {\n        return this._rules.filter((r) => r.kind === RULE_SERVER);\n    }\n\n    public get userRules(): ListRule[] {\n        return this._rules.filter((r) => r.kind === RULE_USER);\n    }\n\n    public async banEntity(kind: string, entity: string, reason: string): Promise<any> {\n        const type = ruleTypeToStable(kind);\n        if (!type) return; // unknown rule type\n        await MatrixClientPeg.safeGet().sendStateEvent(\n            this._roomId,\n            type,\n            {\n                entity: entity,\n                reason: reason,\n                recommendation: recommendationToStable(RECOMMENDATION_BAN, true)!,\n            },\n            \"rule:\" + entity,\n        );\n        this._rules.push(new ListRule(entity, RECOMMENDATION_BAN, reason, type));\n    }\n\n    public async unbanEntity(kind: string, entity: string): Promise<any> {\n        const type = ruleTypeToStable(kind);\n        if (!type) return; // unknown rule type\n        // Empty state event is effectively deleting it.\n        await MatrixClientPeg.safeGet().sendStateEvent(this._roomId, type, {}, \"rule:\" + entity);\n        this._rules = this._rules.filter((r) => {\n            if (r.kind !== ruleTypeToStable(kind)) return true;\n            if (r.entity !== entity) return true;\n            return false; // we just deleted this rule\n        });\n    }\n\n    public updateList(): void {\n        this._rules = [];\n\n        const room = MatrixClientPeg.safeGet().getRoom(this._roomId);\n        if (!room) return;\n\n        for (const eventType of ALL_RULE_TYPES) {\n            const events = room.currentState.getStateEvents(eventType);\n            for (const ev of events) {\n                if (!ev.getStateKey()) continue;\n\n                const kind = ruleTypeToStable(eventType);\n                if (!kind) continue; // unknown type\n\n                const entity = ev.getContent()[\"entity\"];\n                const recommendation = ev.getContent()[\"recommendation\"];\n                const reason = ev.getContent()[\"reason\"];\n                if (!entity || !recommendation || !reason) continue;\n\n                this._rules.push(new ListRule(entity, recommendation, reason, kind));\n            }\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, RoomStateEvent, Preset } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { ALL_RULE_TYPES, BanList } from \"./BanList\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { _t } from \"../languageHandler\";\nimport dis from \"../dispatcher/dispatcher\";\nimport { SettingLevel } from \"../settings/SettingLevel\";\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport { type DoAfterSyncPreparedPayload } from \"../dispatcher/payloads/DoAfterSyncPreparedPayload\";\nimport { Action } from \"../dispatcher/actions\";\n\n// TODO: Move this and related files to the js-sdk or something once finalized.\n\nexport class Mjolnir {\n    private static instance?: Mjolnir;\n\n    private _lists: BanList[] = []; // eslint-disable-line @typescript-eslint/naming-convention\n    private _roomIds: string[] = []; // eslint-disable-line @typescript-eslint/naming-convention\n    private mjolnirWatchRef?: string;\n    private dispatcherRef?: string;\n\n    public get roomIds(): string[] {\n        return this._roomIds;\n    }\n\n    public get lists(): BanList[] {\n        return this._lists;\n    }\n\n    public start(): void {\n        this.mjolnirWatchRef = SettingsStore.watchSetting(\"mjolnirRooms\", null, this.onListsChanged.bind(this));\n\n        this.dispatcherRef = dis.register(this.onAction);\n        dis.dispatch<DoAfterSyncPreparedPayload<ActionPayload>>({\n            action: Action.DoAfterSyncPrepared,\n            deferred_action: { action: \"setup_mjolnir\" },\n        });\n    }\n\n    private onAction = (payload: ActionPayload): void => {\n        if (payload[\"action\"] === \"setup_mjolnir\") {\n            logger.log(\"Setting up Mjolnir: after sync\");\n            this.setup();\n        }\n    };\n\n    public setup(): void {\n        if (!MatrixClientPeg.get()) return;\n        this.updateLists(SettingsStore.getValue(\"mjolnirRooms\"));\n        MatrixClientPeg.get()!.on(RoomStateEvent.Events, this.onEvent);\n    }\n\n    public stop(): void {\n        SettingsStore.unwatchSetting(this.mjolnirWatchRef);\n        this.mjolnirWatchRef = undefined;\n\n        dis.unregister(this.dispatcherRef);\n        this.dispatcherRef = undefined;\n\n        MatrixClientPeg.get()?.removeListener(RoomStateEvent.Events, this.onEvent);\n    }\n\n    public async getOrCreatePersonalList(): Promise<BanList> {\n        let personalRoomId = SettingsStore.getValue(\"mjolnirPersonalRoom\");\n        if (!personalRoomId) {\n            const resp = await MatrixClientPeg.safeGet().createRoom({\n                name: _t(\"labs_mjolnir|room_name\"),\n                topic: _t(\"labs_mjolnir|room_topic\"),\n                preset: Preset.PrivateChat,\n            });\n            personalRoomId = resp[\"room_id\"];\n            await SettingsStore.setValue(\"mjolnirPersonalRoom\", null, SettingLevel.ACCOUNT, personalRoomId);\n            await SettingsStore.setValue(\"mjolnirRooms\", null, SettingLevel.ACCOUNT, [\n                personalRoomId,\n                ...this._roomIds,\n            ]);\n        }\n        if (!personalRoomId) {\n            throw new Error(\"Error finding a room ID to use\");\n        }\n\n        let list = this._lists.find((b) => b.roomId === personalRoomId);\n        if (!list) list = new BanList(personalRoomId);\n        // we don't append the list to the tracked rooms because it should already be there.\n        // we're just trying to get the caller some utility access to the list\n\n        return list;\n    }\n\n    // get without creating the list\n    public getPersonalList(): BanList | null {\n        const personalRoomId = SettingsStore.getValue(\"mjolnirPersonalRoom\");\n        if (!personalRoomId) return null;\n\n        let list = this._lists.find((b) => b.roomId === personalRoomId);\n        if (!list) list = new BanList(personalRoomId);\n        // we don't append the list to the tracked rooms because it should already be there.\n        // we're just trying to get the caller some utility access to the list\n\n        return list;\n    }\n\n    public async subscribeToList(roomId: string): Promise<void> {\n        const roomIds = [...this._roomIds, roomId];\n        await SettingsStore.setValue(\"mjolnirRooms\", null, SettingLevel.ACCOUNT, roomIds);\n        this._lists.push(new BanList(roomId));\n    }\n\n    public async unsubscribeFromList(roomId: string): Promise<void> {\n        const roomIds = this._roomIds.filter((r) => r !== roomId);\n        await SettingsStore.setValue(\"mjolnirRooms\", null, SettingLevel.ACCOUNT, roomIds);\n        this._lists = this._lists.filter((b) => b.roomId !== roomId);\n    }\n\n    private onEvent = (event: MatrixEvent): void => {\n        if (!MatrixClientPeg.get()) return;\n        if (!this._roomIds.includes(event.getRoomId()!)) return;\n        if (!ALL_RULE_TYPES.includes(event.getType())) return;\n\n        this.updateLists(this._roomIds);\n    };\n\n    private onListsChanged(\n        settingName: string,\n        roomId: string | null,\n        atLevel: SettingLevel,\n        newValue: string[],\n    ): void {\n        // We know that ban lists are only recorded at one level so we don't need to re-eval them\n        this.updateLists(newValue);\n    }\n\n    private updateLists(listRoomIds: string[]): void {\n        if (!MatrixClientPeg.get()) return;\n\n        logger.log(\"Updating Mjolnir ban lists to: \" + listRoomIds);\n        this._lists = [];\n        this._roomIds = listRoomIds || [];\n        if (!listRoomIds) return;\n\n        for (const roomId of listRoomIds) {\n            // Creating the list updates it\n            this._lists.push(new BanList(roomId));\n        }\n    }\n\n    public isServerBanned(serverName: string): boolean {\n        for (const list of this._lists) {\n            for (const rule of list.serverRules) {\n                if (rule.isMatch(serverName)) {\n                    return true;\n                }\n            }\n        }\n        return false;\n    }\n\n    public isUserBanned(userId: string): boolean {\n        for (const list of this._lists) {\n            for (const rule of list.userRules) {\n                if (rule.isMatch(userId)) {\n                    return true;\n                }\n            }\n        }\n        return false;\n    }\n\n    public static sharedInstance(): Mjolnir {\n        if (!Mjolnir.instance) {\n            Mjolnir.instance = new Mjolnir();\n        }\n        return Mjolnir.instance;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    TypedEventEmitter,\n    RoomEvent,\n    RoomStateEvent,\n    type MatrixClient,\n    type IMyDevice,\n    type Room,\n    type RoomMember,\n} from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership, type Membership } from \"matrix-js-sdk/src/types\";\nimport { logger as rootLogger } from \"matrix-js-sdk/src/logger\";\nimport { secureRandomString } from \"matrix-js-sdk/src/randomstring\";\nimport { CallType } from \"matrix-js-sdk/src/webrtc/call\";\nimport { type IWidgetApiRequest, type ClientWidgetApi, type IWidgetData } from \"matrix-widget-api\";\nimport {\n    type MatrixRTCSession,\n    MatrixRTCSessionEvent,\n    MatrixRTCSessionManagerEvents,\n} from \"matrix-js-sdk/src/matrixrtc\";\n\nimport type EventEmitter from \"events\";\nimport type { IApp } from \"../stores/WidgetStore\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { timeout } from \"../utils/promise\";\nimport WidgetUtils from \"../utils/WidgetUtils\";\nimport { WidgetType } from \"../widgets/WidgetType\";\nimport { ElementWidgetActions } from \"../stores/widgets/ElementWidgetActions\";\nimport WidgetStore from \"../stores/WidgetStore\";\nimport { WidgetMessagingStore, WidgetMessagingStoreEvent } from \"../stores/widgets/WidgetMessagingStore\";\nimport ActiveWidgetStore, { ActiveWidgetStoreEvent } from \"../stores/ActiveWidgetStore\";\nimport { getCurrentLanguage } from \"../languageHandler\";\nimport { Anonymity, PosthogAnalytics } from \"../PosthogAnalytics\";\nimport { isVideoRoom } from \"../utils/video-rooms\";\nimport { FontWatcher } from \"../settings/watchers/FontWatcher\";\nimport { type JitsiCallMemberContent, JitsiCallMemberEventType } from \"../call-types\";\nimport SdkConfig from \"../SdkConfig.ts\";\nimport DMRoomMap from \"../utils/DMRoomMap.ts\";\nimport { type WidgetMessaging, WidgetMessagingEvent } from \"../stores/widgets/WidgetMessaging.ts\";\nimport { BugReportEndpointURLLocal } from \"../IConfigOptions.ts\";\n\nconst TIMEOUT_MS = 16000;\nconst logger = rootLogger.getChild(\"models/Call\");\n\n// Waits until an event is emitted satisfying the given predicate\nconst waitForEvent = async (\n    emitter: EventEmitter,\n    event: string,\n    pred: (...args: any[]) => boolean = () => true,\n    customTimeout?: number | false,\n): Promise<void> => {\n    let listener: (...args: any[]) => void;\n    const wait = new Promise<void>((resolve) => {\n        listener = (...args) => {\n            if (pred(...args)) resolve();\n        };\n        emitter.on(event, listener);\n    });\n\n    if (customTimeout !== false) {\n        const timedOut = (await timeout(wait, false, customTimeout ?? TIMEOUT_MS)) === false;\n        if (timedOut) throw new Error(\"Timed out\");\n    } else {\n        await wait;\n    }\n    emitter.off(event, listener!);\n};\n\nexport enum ConnectionState {\n    Disconnected = \"disconnected\",\n    Connected = \"connected\",\n    Disconnecting = \"disconnecting\",\n}\n\nexport const isConnected = (state: ConnectionState): boolean =>\n    state === ConnectionState.Connected || state === ConnectionState.Disconnecting;\n\nexport enum CallEvent {\n    ConnectionState = \"connection_state\",\n    Participants = \"participants\",\n    Close = \"close\",\n    Destroy = \"destroy\",\n    CallTypeChanged = \"call_type_changed\",\n}\n\ninterface CallEventHandlerMap {\n    [CallEvent.ConnectionState]: (state: ConnectionState, prevState: ConnectionState) => void;\n    [CallEvent.Participants]: (\n        participants: Map<RoomMember, Set<string>>,\n        prevParticipants: Map<RoomMember, Set<string>>,\n    ) => void;\n    [CallEvent.Close]: () => void;\n    [CallEvent.Destroy]: () => void;\n    [CallEvent.CallTypeChanged]: (callType: CallType) => void;\n}\n\n/**\n * A group call accessed through a widget.\n */\nexport abstract class Call extends TypedEventEmitter<CallEvent, CallEventHandlerMap> {\n    protected readonly widgetUid: string;\n    protected readonly room: Room;\n\n    private _callType: CallType = CallType.Video;\n    public get callType(): CallType {\n        return this._callType;\n    }\n\n    protected set callType(callType: CallType) {\n        if (this._callType !== callType) {\n            this.emit(CallEvent.CallTypeChanged, callType);\n        }\n        this._callType = callType;\n    }\n\n    /**\n     * The time after which device member state should be considered expired.\n     */\n    public abstract readonly STUCK_DEVICE_TIMEOUT_MS: number;\n\n    private _widgetApi: ClientWidgetApi | null = null;\n    /**\n     * The widget API interface to the widget, or null if disconnected.\n     */\n    protected get widgetApi(): ClientWidgetApi | null {\n        return this._widgetApi;\n    }\n    private set widgetApi(value: ClientWidgetApi | null) {\n        this._widgetApi = value;\n    }\n\n    public get roomId(): string {\n        return this.widget.roomId;\n    }\n\n    private _connectionState = ConnectionState.Disconnected;\n    public get connectionState(): ConnectionState {\n        return this._connectionState;\n    }\n    protected set connectionState(value: ConnectionState) {\n        const prevValue = this._connectionState;\n        this._connectionState = value;\n        this.emit(CallEvent.ConnectionState, value, prevValue);\n    }\n\n    public get connected(): boolean {\n        return isConnected(this.connectionState);\n    }\n\n    private _participants = new Map<RoomMember, Set<string>>();\n    /**\n     * The participants in the call, as a map from members to device IDs.\n     */\n    public get participants(): Map<RoomMember, Set<string>> {\n        return this._participants;\n    }\n    protected set participants(value: Map<RoomMember, Set<string>>) {\n        const prevValue = this._participants;\n        this._participants = value;\n        this.emit(CallEvent.Participants, value, prevValue);\n    }\n\n    private _presented = false;\n    /**\n     * Whether the call widget is currently being presented in the user interface.\n     */\n    public get presented(): boolean {\n        return this._presented;\n    }\n    public set presented(value: boolean) {\n        this._presented = value;\n    }\n\n    protected constructor(\n        /**\n         * The widget used to access this call.\n         */\n        public readonly widget: IApp,\n        protected readonly client: MatrixClient,\n    ) {\n        super();\n        this.widgetUid = WidgetUtils.getWidgetUid(this.widget);\n        this.room = this.client.getRoom(this.roomId)!;\n        WidgetMessagingStore.instance.on(WidgetMessagingStoreEvent.StopMessaging, this.onStopMessaging);\n    }\n\n    /**\n     * Gets the call associated with the given room, if any.\n     * @param {Room} room The room.\n     * @returns {Call | null} The call.\n     */\n    public static get(room: Room): Call | null {\n        return ElementCall.get(room) ?? JitsiCall.get(room);\n    }\n\n    /**\n     * Performs a routine check of the call's associated room state, cleaning up\n     * any data left over from an unclean disconnection.\n     */\n    public abstract clean(): Promise<void>;\n\n    /**\n     * Contacts the widget to disconnect from the call.\n     */\n    protected abstract performDisconnection(): Promise<void>;\n\n    /**\n     * Starts the communication between the widget and the call.\n     * The widget associated with the call must be active for this to succeed.\n     * Only call this if the call state is: ConnectionState.Disconnected.\n     * @param _params Widget generation parameters are unused in this abstract class.\n     * @returns The ClientWidgetApi for this call.\n     */\n    public async start(_params?: WidgetGenerationParameters): Promise<ClientWidgetApi> {\n        const messagingStore = WidgetMessagingStore.instance;\n        const startTime = performance.now();\n        let messaging: WidgetMessaging | undefined = messagingStore.getMessagingForUid(this.widgetUid);\n        // The widget might still be initializing, so wait for it in an async\n        // event loop. We need the messaging to be both present and started\n        // (have a connected widget API), so register listeners for both cases.\n        while (!messaging?.widgetApi) {\n            if (messaging) logger.debug(`Messaging present but not yet started for ${this.widgetUid}`);\n            else logger.debug(`No messaging yet for ${this.widgetUid}`);\n            const recheck = Promise.withResolvers<void>();\n            const currentMessaging = messaging;\n\n            // Maybe the messaging is present but not yet started. In this case,\n            // check again for a widget API as soon as it starts.\n            const onStart = (): void => recheck.resolve();\n            currentMessaging?.on(WidgetMessagingEvent.Start, onStart);\n\n            // Maybe the messaging is not present at all. It's also entirely\n            // possible (as shown in React strict mode) that the messaging could\n            // be abandoned and replaced by an entirely new messaging object\n            // while we were waiting for the original one to start. We need to\n            // react to store updates in either case.\n            const onStoreMessaging = (uid: string, m: WidgetMessaging): void => {\n                if (uid === this.widgetUid) {\n                    messagingStore.off(WidgetMessagingStoreEvent.StoreMessaging, onStoreMessaging);\n                    messaging = m; // Check the new messaging object on the next iteration of the loop\n                    recheck.resolve();\n                }\n            };\n            messagingStore.on(WidgetMessagingStoreEvent.StoreMessaging, onStoreMessaging);\n\n            // Race both of the above recheck signals against a timeout.\n            const timeout = setTimeout(\n                () => recheck.reject(new Error(`Widget for call in ${this.roomId} not started; timed out`)),\n                TIMEOUT_MS - (performance.now() - startTime),\n            );\n\n            try {\n                await recheck.promise;\n            } finally {\n                currentMessaging?.off(WidgetMessagingEvent.Start, onStart);\n                messagingStore.off(WidgetMessagingStoreEvent.StoreMessaging, onStoreMessaging);\n                clearTimeout(timeout);\n            }\n        }\n\n        logger.debug(`Widget ${this.widgetUid} now ready`);\n        return (this.widgetApi = messaging.widgetApi);\n    }\n\n    protected setConnected(): void {\n        this.room.on(RoomEvent.MyMembership, this.onMyMembership);\n        window.addEventListener(\"beforeunload\", this.beforeUnload);\n        this.connectionState = ConnectionState.Connected;\n    }\n\n    /**\n     * Manually marks the call as disconnected.\n     */\n    protected setDisconnected(): void {\n        this.room.off(RoomEvent.MyMembership, this.onMyMembership);\n        window.removeEventListener(\"beforeunload\", this.beforeUnload);\n        this.connectionState = ConnectionState.Disconnected;\n    }\n\n    /**\n     * Disconnects the user from the call.\n     */\n    public async disconnect(): Promise<void> {\n        if (!this.connected) throw new Error(\"Not connected\");\n\n        this.connectionState = ConnectionState.Disconnecting;\n        await this.performDisconnection();\n        this.setDisconnected();\n        this.close();\n    }\n\n    /**\n     * Stops further communication with the widget and tells the UI to close.\n     */\n    protected close(): void {\n        this.widgetApi = null;\n        this.emit(CallEvent.Close);\n    }\n\n    /**\n     * Stops all internal timers and tasks to prepare for garbage collection.\n     */\n    public destroy(): void {\n        if (this.connected) {\n            this.setDisconnected();\n            this.close();\n        }\n        WidgetMessagingStore.instance.off(WidgetMessagingStoreEvent.StopMessaging, this.onStopMessaging);\n        this.emit(CallEvent.Destroy);\n    }\n\n    private readonly onMyMembership = async (_room: Room, membership: Membership): Promise<void> => {\n        if (membership !== KnownMembership.Join) this.setDisconnected();\n    };\n\n    private readonly onStopMessaging = (uid: string): void => {\n        if (uid === this.widgetUid && this.connected) {\n            logger.debug(\"The widget died; treating this as a user hangup\");\n            this.setDisconnected();\n            this.close();\n        }\n    };\n\n    private beforeUnload = (): void => {\n        this.setDisconnected();\n        this.close();\n    };\n}\n\nexport type { JitsiCallMemberContent };\n\n/**\n * A group call using Jitsi as a backend.\n */\nexport class JitsiCall extends Call {\n    public static readonly MEMBER_EVENT_TYPE = JitsiCallMemberEventType;\n    public readonly STUCK_DEVICE_TIMEOUT_MS = 1000 * 60 * 60; // 1 hour\n\n    private resendDevicesTimer: number | null = null;\n    private participantsExpirationTimer: number | null = null;\n\n    private constructor(widget: IApp, client: MatrixClient) {\n        super(widget, client);\n\n        this.room.on(RoomStateEvent.Update, this.onRoomState);\n        this.on(CallEvent.ConnectionState, this.onConnectionState);\n        this.updateParticipants();\n    }\n\n    public static get(room: Room): JitsiCall | null {\n        // Only supported in video rooms\n        if (room.isElementVideoRoom()) {\n            const apps = WidgetStore.instance.getApps(room.roomId);\n            // The isVideoChannel field differentiates rich Jitsi calls from bare Jitsi widgets\n            const jitsiWidget = apps.find((app) => WidgetType.JITSI.matches(app.type) && app.data?.isVideoChannel);\n            if (jitsiWidget) return new JitsiCall(jitsiWidget, room.client);\n        }\n\n        return null;\n    }\n\n    public static async create(room: Room): Promise<void> {\n        await WidgetUtils.addJitsiWidget(room.client, room.roomId, CallType.Video, \"Group call\", true, room.name);\n    }\n\n    private updateParticipants(): void {\n        if (this.participantsExpirationTimer !== null) {\n            clearTimeout(this.participantsExpirationTimer);\n            this.participantsExpirationTimer = null;\n        }\n\n        const participants = new Map<RoomMember, Set<string>>();\n        const now = Date.now();\n        let allExpireAt = Infinity;\n\n        for (const e of this.room.currentState.getStateEvents(JitsiCall.MEMBER_EVENT_TYPE)) {\n            const member = this.room.getMember(e.getStateKey()!);\n            const content = e.getContent<JitsiCallMemberContent>();\n            const expiresAt = typeof content.expires_ts === \"number\" ? content.expires_ts : -Infinity;\n            let devices =\n                expiresAt > now && Array.isArray(content.devices)\n                    ? content.devices.filter((d) => typeof d === \"string\")\n                    : [];\n\n            // Apply local echo for the disconnected case\n            if (!this.connected && member?.userId === this.client.getUserId()) {\n                devices = devices.filter((d) => d !== this.client.getDeviceId());\n            }\n            // Must have a connected device and still be joined to the room\n            if (devices.length > 0 && member?.membership === KnownMembership.Join) {\n                participants.set(member, new Set(devices));\n                if (expiresAt < allExpireAt) allExpireAt = expiresAt;\n            }\n        }\n\n        // Apply local echo for the connected case\n        if (this.connected) {\n            const localMember = this.room.getMember(this.client.getUserId()!)!;\n            let devices = participants.get(localMember);\n            if (devices === undefined) {\n                devices = new Set();\n                participants.set(localMember, devices);\n            }\n\n            devices.add(this.client.getDeviceId()!);\n        }\n\n        this.participants = participants;\n        if (allExpireAt < Infinity) {\n            this.participantsExpirationTimer = window.setTimeout(() => this.updateParticipants(), allExpireAt - now);\n        }\n    }\n\n    /**\n     * Updates our member state with the devices returned by the given function.\n     * @param fn A function from the current devices to the new devices. If it\n     *     returns null, the update is skipped.\n     */\n    private async updateDevices(fn: (devices: string[]) => string[] | null): Promise<void> {\n        if (this.room.getMyMembership() !== KnownMembership.Join) return;\n\n        const event = this.room.currentState.getStateEvents(JitsiCall.MEMBER_EVENT_TYPE, this.client.getUserId()!);\n        const content = event?.getContent<JitsiCallMemberContent>();\n        const expiresAt = typeof content?.expires_ts === \"number\" ? content.expires_ts : -Infinity;\n        const devices = expiresAt > Date.now() && Array.isArray(content?.devices) ? content!.devices : [];\n        const newDevices = fn(devices);\n\n        if (newDevices !== null) {\n            const newContent: JitsiCallMemberContent = {\n                devices: newDevices,\n                expires_ts: Date.now() + this.STUCK_DEVICE_TIMEOUT_MS,\n            };\n\n            await this.client.sendStateEvent(\n                this.roomId,\n                JitsiCall.MEMBER_EVENT_TYPE,\n                newContent,\n                this.client.getUserId()!,\n            );\n        }\n    }\n\n    public async clean(): Promise<void> {\n        const now = Date.now();\n        const { devices: myDevices } = await this.client.getDevices();\n        const deviceMap = new Map<string, IMyDevice>(myDevices.map((d) => [d.device_id, d]));\n\n        // Clean up our member state by filtering out logged out devices,\n        // inactive devices, and our own device (if we're disconnected)\n        await this.updateDevices((devices) => {\n            const newDevices = devices.filter((d) => {\n                const device = deviceMap.get(d);\n                return (\n                    device?.last_seen_ts !== undefined &&\n                    !(d === this.client.getDeviceId() && !this.connected) &&\n                    now - device.last_seen_ts < this.STUCK_DEVICE_TIMEOUT_MS\n                );\n            });\n\n            // Skip the update if the devices are unchanged\n            return newDevices.length === devices.length ? null : newDevices;\n        });\n    }\n\n    private async addOurDevice(): Promise<void> {\n        await this.updateDevices((devices) => Array.from(new Set(devices).add(this.client.getDeviceId()!)));\n    }\n\n    private async removeOurDevice(): Promise<void> {\n        await this.updateDevices((devices) => {\n            const devicesSet = new Set(devices);\n            devicesSet.delete(this.client.getDeviceId()!);\n            return Array.from(devicesSet);\n        });\n    }\n\n    public async start(): Promise<ClientWidgetApi> {\n        const widgetApi = await super.start();\n        widgetApi.on(`action:${ElementWidgetActions.JoinCall}`, this.onJoin);\n        widgetApi.on(`action:${ElementWidgetActions.HangupCall}`, this.onHangup);\n        ActiveWidgetStore.instance.on(ActiveWidgetStoreEvent.Dock, this.onDock);\n        ActiveWidgetStore.instance.on(ActiveWidgetStoreEvent.Undock, this.onUndock);\n        return widgetApi;\n    }\n\n    protected async performDisconnection(): Promise<void> {\n        const response = waitForEvent(\n            this.widgetApi!,\n            `action:${ElementWidgetActions.HangupCall}`,\n            (ev: CustomEvent<IWidgetApiRequest>) => {\n                ev.preventDefault();\n                this.widgetApi!.transport.reply(ev.detail, {}); // ack\n                return true;\n            },\n        );\n        const request = this.widgetApi!.transport.send(ElementWidgetActions.HangupCall, {});\n        try {\n            await Promise.all([request, response]);\n        } catch (e) {\n            throw new Error(`Failed to hangup call in room ${this.roomId}: ${e}`);\n        }\n    }\n\n    public close(): void {\n        this.widgetApi!.off(`action:${ElementWidgetActions.JoinCall}`, this.onJoin);\n        this.widgetApi!.off(`action:${ElementWidgetActions.HangupCall}`, this.onHangup);\n        ActiveWidgetStore.instance.off(ActiveWidgetStoreEvent.Dock, this.onDock);\n        ActiveWidgetStore.instance.off(ActiveWidgetStoreEvent.Undock, this.onUndock);\n        super.close();\n    }\n\n    public destroy(): void {\n        this.room.off(RoomStateEvent.Update, this.onRoomState);\n        this.off(CallEvent.ConnectionState, this.onConnectionState);\n        if (this.participantsExpirationTimer !== null) {\n            clearTimeout(this.participantsExpirationTimer);\n            this.participantsExpirationTimer = null;\n        }\n        if (this.resendDevicesTimer !== null) {\n            clearInterval(this.resendDevicesTimer);\n            this.resendDevicesTimer = null;\n        }\n\n        super.destroy();\n    }\n\n    private readonly onRoomState = (): void => this.updateParticipants();\n\n    private readonly onConnectionState = async (state: ConnectionState, prevState: ConnectionState): Promise<void> => {\n        if (state === ConnectionState.Connected && !isConnected(prevState)) {\n            this.updateParticipants(); // Local echo\n\n            // Tell others that we're connected, by adding our device to room state\n            await this.addOurDevice();\n            // Re-add this device every so often so our video member event doesn't become stale\n            this.resendDevicesTimer = window.setInterval(\n                async (): Promise<void> => {\n                    logger.debug(`Resending video member event for ${this.roomId}`);\n                    await this.addOurDevice();\n                },\n                (this.STUCK_DEVICE_TIMEOUT_MS * 3) / 4,\n            );\n        } else if (state === ConnectionState.Disconnected && isConnected(prevState)) {\n            this.updateParticipants(); // Local echo\n\n            if (this.resendDevicesTimer !== null) {\n                clearInterval(this.resendDevicesTimer);\n                this.resendDevicesTimer = null;\n            }\n            // Tell others that we're disconnected, by removing our device from room state\n            await this.removeOurDevice();\n        }\n    };\n\n    private readonly onDock = async (): Promise<void> => {\n        // The widget is no longer a PiP, so let's restore the default layout\n        await this.widgetApi!.transport.send(ElementWidgetActions.TileLayout, {});\n    };\n\n    private readonly onUndock = async (): Promise<void> => {\n        // The widget has become a PiP, so let's switch Jitsi to spotlight mode\n        // to only show the active speaker and economize on space\n        await this.widgetApi!.transport.send(ElementWidgetActions.SpotlightLayout, {});\n    };\n\n    private readonly onJoin = (ev: CustomEvent<IWidgetApiRequest>): void => {\n        ev.preventDefault();\n        this.widgetApi!.transport.reply(ev.detail, {}); // ack\n        this.setConnected();\n    };\n\n    private readonly onHangup = async (ev: CustomEvent<IWidgetApiRequest>): Promise<void> => {\n        // If we're already in the middle of a client-initiated disconnection,\n        // ignore the event\n        if (this.connectionState === ConnectionState.Disconnecting) return;\n\n        ev.preventDefault();\n        this.widgetApi!.transport.reply(ev.detail, {}); // ack\n        this.setDisconnected();\n        if (!isVideoRoom(this.room)) this.close();\n    };\n}\n\nexport enum ElementCallIntent {\n    StartCall = \"start_call\",\n    JoinExisting = \"join_existing\",\n    StartCallDM = \"start_call_dm\",\n    StartCallDMVoice = \"start_call_dm_voice\",\n    JoinExistingDM = \"join_existing_dm\",\n    JoinExistingDMVoice = \"join_existing_dm_voice\",\n}\n\n/**\n * Parameters to be passed during widget creation.\n * These parameters are hints only, and may not be accepted by the implementation.\n */\nexport interface WidgetGenerationParameters {\n    /**\n     * Skip showing the lobby screen of a call.\n     */\n    skipLobby?: boolean;\n    /**\n     * Does the user intent to start a voice call?\n     */\n    voiceOnly?: boolean;\n}\n\n/**\n * Parameters to be passed during widget creation.\n * These parameters are hints only, and may not be accepted by the implementation.\n */\nexport interface WidgetGenerationParameters {\n    /**\n     * Skip showing the lobby screen of a call.\n     */\n    skipLobby?: boolean;\n}\n\n/**\n * A group call using MSC3401 and Element Call as a backend.\n * (somewhat cheekily named)\n */\nexport class ElementCall extends Call {\n    public readonly STUCK_DEVICE_TIMEOUT_MS = 1000 * 60 * 60; // 1 hour\n\n    private settingsStoreCallEncryptionWatcher?: string;\n    private terminationTimer?: number;\n\n    public get presented(): boolean {\n        return super.presented;\n    }\n    public set presented(value: boolean) {\n        super.presented = value;\n        this.checkDestroy();\n    }\n\n    public widgetGenerationParameters: WidgetGenerationParameters = {};\n\n    /**\n     * Calculate the correct intent (and associated parameters) for an Element Call room. Paarameters\n     * will be applied to the `params` instance.\n     *\n     * @param params Existing URL parameters\n     * @param client The current client.\n     * @param roomId The room ID for the call.\n     */\n    private static appendRoomParams(\n        params: URLSearchParams,\n        client: MatrixClient,\n        roomId: string,\n        { voiceOnly }: WidgetGenerationParameters,\n    ): void {\n        const room = client.getRoom(roomId);\n        if (!room) {\n            // If the room isn't known, or the room is a video room then skip setting an intent.\n            return;\n        } else if (isVideoRoom(room)) {\n            // Video rooms already exist, so just treat as if we're joining a group call.\n            params.append(\"intent\", ElementCallIntent.JoinExisting);\n            // Video rooms should always return to lobby.\n            params.append(\"returnToLobby\", \"true\");\n            // Never skip the lobby, we always want to give the caller a chance to explicitly join.\n            params.append(\"skipLobby\", \"false\");\n            // Never preload, as per below warning.\n            params.append(\"preload\", \"false\");\n            return;\n        }\n        const isDM = !!DMRoomMap.shared().getUserIdForRoomId(room.roomId);\n        const oldestCallMember = client.matrixRTC.getRoomSession(room).getOldestMembership();\n        const hasCallStarted = !!oldestCallMember && oldestCallMember.sender !== client.getSafeUserId();\n        // XXX: @element-hq/element-call-embedded <= 0.15.0 sets the wrong parameter for\n        // preload by default so we override here. This can be removed when that package\n        // is released and upgraded.\n        if (isDM) {\n            if (hasCallStarted) {\n                params.append(\n                    \"intent\",\n                    voiceOnly ? ElementCallIntent.JoinExistingDMVoice : ElementCallIntent.JoinExistingDM,\n                );\n                params.append(\"preload\", \"false\");\n            } else {\n                params.append(\"intent\", voiceOnly ? ElementCallIntent.StartCallDMVoice : ElementCallIntent.StartCallDM);\n                params.append(\"preload\", \"false\");\n            }\n        } else {\n            // Group chats do not have a voice option.\n            if (hasCallStarted) {\n                params.append(\"intent\", ElementCallIntent.JoinExisting);\n                params.append(\"preload\", \"false\");\n            } else {\n                params.append(\"intent\", ElementCallIntent.StartCall);\n                params.append(\"preload\", \"false\");\n            }\n        }\n    }\n\n    /**\n     * Calculate the correct analytics parameters for an Element Call room. Paarameters\n     * will be applied to the `params` instance.\n     *\n     * @param params Existing URL parameters\n     * @param client The current client.\n     */\n    private static appendAnalyticsParams(params: URLSearchParams, client: MatrixClient): void {\n        const posthogConfig = SdkConfig.get(\"posthog\");\n        if (!posthogConfig || PosthogAnalytics.instance.getAnonymity() === Anonymity.Disabled) {\n            return;\n        }\n\n        const accountAnalyticsData = client.getAccountData(PosthogAnalytics.ANALYTICS_EVENT_TYPE)?.getContent();\n        // The analyticsID is passed directly to element call (EC) since this codepath is only for EC and no other widget.\n        // We really don't want the same analyticID's for the EC and EW posthog instances (Data on posthog should be limited/anonymized as much as possible).\n        // This is prohibited in EC where a hashed version of the analyticsID is used for the actual posthog identification.\n        // We can pass the raw EW analyticsID here since we need to trust EC with not sending sensitive data to posthog (EC has access to more sensible data than the analyticsID e.g. the username)\n        const analyticsID: string = accountAnalyticsData?.pseudonymousAnalyticsOptIn ? accountAnalyticsData?.id : \"\";\n\n        params.append(\"analyticsID\", analyticsID); // Legacy, deprecated in favour of posthogUserId\n        params.append(\"posthogUserId\", analyticsID);\n        params.append(\"posthogApiHost\", posthogConfig.api_host);\n        params.append(\"posthogApiKey\", posthogConfig.project_api_key);\n\n        // We gate passing sentry behind analytics consent as EC shares data automatically without user-consent,\n        // unlike EW where data is shared upon an intentional user action (rageshake).\n        const sentryConfig = SdkConfig.get(\"sentry\");\n        if (sentryConfig) {\n            params.append(\"sentryDsn\", sentryConfig.dsn);\n            params.append(\"sentryEnvironment\", sentryConfig.environment ?? \"\");\n        }\n    }\n\n    /**\n     * Generate the correct Element Call widget URL for creating or joining a call in this room.\n     * Unless `Developer.elementCallUrl` is set, the widget will use the embedded Element Call package.\n     *\n     * @param client\n     * @param roomId\n     * @param opts\n     * @returns\n     */\n    private static generateWidgetUrl(client: MatrixClient, roomId: string, opts: WidgetGenerationParameters = {}): URL {\n        const elementCallUrlOverride = SettingsStore.getValue(\"Developer.elementCallUrl\");\n        const url = elementCallUrlOverride\n            ? new URL(elementCallUrlOverride)\n            : // this strips hash fragment from baseUrl\n              new URL(\"./widgets/element-call/index.html#\", window.location.href);\n\n        // Splice together the Element Call URL for this call\n        // Parameters can be found in https://github.com/element-hq/element-call/blob/livekit/src/UrlParams.ts.\n        const params = new URLSearchParams({\n            // Template variables are used, so that this can be configured using the widget data.\n            perParticipantE2EE: \"$perParticipantE2EE\",\n            userId: client.getUserId()!,\n            deviceId: client.getDeviceId()!,\n            roomId: roomId,\n            baseUrl: client.baseUrl,\n            lang: getCurrentLanguage().replace(\"_\", \"-\"),\n            fontScale: (FontWatcher.getRootFontSize() / FontWatcher.getBrowserDefaultFontSize()).toString(),\n            theme: \"$org.matrix.msc2873.client_theme\",\n        });\n\n        if (typeof opts.skipLobby === \"boolean\") {\n            params.set(\"skipLobby\", opts.skipLobby.toString());\n        }\n\n        const rageshakeSubmitUrl = SdkConfig.get(\"bug_report_endpoint_url\");\n        if (rageshakeSubmitUrl && rageshakeSubmitUrl !== BugReportEndpointURLLocal) {\n            params.append(\"rageshakeSubmitUrl\", rageshakeSubmitUrl);\n        }\n\n        if (SettingsStore.getValue(\"fallbackICEServerAllowed\")) {\n            params.append(\"allowIceFallback\", \"true\");\n        }\n\n        const echoCancellation = SettingsStore.getValue(\"webrtc_audio_echoCancellation\");\n        if (!echoCancellation) {\n            // the default is true, so only set if false\n            params.append(\"echoCancellation\", \"false\");\n        }\n        const noiseSuppression = SettingsStore.getValue(\"webrtc_audio_noiseSuppression\");\n        if (!noiseSuppression) {\n            // the default is true, so only set if false\n            params.append(\"noiseSuppression\", \"false\");\n        }\n\n        // Set custom fonts\n        if (SettingsStore.getValue(\"useSystemFont\")) {\n            SettingsStore.getValue(\"systemFont\")\n                .split(\",\")\n                .map((font) => {\n                    // Strip whitespace and quotes\n                    font = font.trim();\n                    if (font.startsWith('\"') && font.endsWith('\"')) font = font.slice(1, -1);\n                    return font;\n                })\n                .forEach((font) => params.append(\"font\", font));\n        }\n        this.appendAnalyticsParams(params, client);\n        this.appendRoomParams(params, client, roomId, opts);\n\n        const replacedUrl = params.toString().replace(/%24/g, \"$\");\n        url.hash = `#?${replacedUrl}`;\n        return url;\n    }\n\n    // Creates a new widget if there isn't any widget of typ Call in this room.\n    private static createOrGetCallWidget(roomId: string, client: MatrixClient): IApp {\n        const ecWidget = WidgetStore.instance.getApps(roomId).find((app) => WidgetType.CALL.matches(app.type));\n        if (ecWidget) {\n            // Always update the widget data because even if the widget is already created,\n            // we might have settings changes that update the widget.\n            ecWidget.data = ElementCall.getWidgetData(client, roomId, ecWidget?.data ?? {}, {});\n            return ecWidget;\n        }\n\n        // To use Element Call without touching room state, we create a virtual\n        // widget (one that doesn't have a corresponding state event)\n        const url = ElementCall.generateWidgetUrl(client, roomId);\n        return WidgetStore.instance.addVirtualWidget(\n            {\n                id: secureRandomString(24), // So that it's globally unique\n                creatorUserId: client.getUserId()!,\n                name: \"Element Call\",\n                type: WidgetType.CALL.preferred,\n                url: url.toString(),\n                waitForIframeLoad: false,\n                data: ElementCall.getWidgetData(client, roomId, {}, {}),\n            },\n            roomId,\n        );\n    }\n\n    /**\n     * Get the correct intent for a widget, so that Element Call presents the correct\n     * default config.\n     * @param client The matrix client.\n     * @param roomId\n     * @param voiceOnly Should the call be voice-only, or video (default).\n     */\n    public static getWidgetIntent(client: MatrixClient, roomId: string, voiceOnly?: boolean): ElementCallIntent {\n        const room = client.getRoom(roomId);\n        if (room !== null && !isVideoRoom(room)) {\n            const isDM = !!DMRoomMap.shared().getUserIdForRoomId(room.roomId);\n            const oldestCallMember = client.matrixRTC.getRoomSession(room).getOldestMembership();\n            const hasCallStarted = !!oldestCallMember && oldestCallMember.sender !== client.getSafeUserId();\n            if (isDM) {\n                if (hasCallStarted) {\n                    return voiceOnly ? ElementCallIntent.JoinExistingDMVoice : ElementCallIntent.JoinExistingDM;\n                } else {\n                    return voiceOnly ? ElementCallIntent.StartCallDMVoice : ElementCallIntent.StartCallDM;\n                }\n            } else {\n                if (hasCallStarted) {\n                    return ElementCallIntent.JoinExisting;\n                } else {\n                    return ElementCallIntent.StartCall;\n                }\n            }\n        }\n        // If unknown, default to joining an existing call.\n        return ElementCallIntent.JoinExisting;\n    }\n\n    private static getWidgetData(\n        client: MatrixClient,\n        roomId: string,\n        currentData: IWidgetData,\n        overwriteData: IWidgetData,\n        voiceOnly?: boolean,\n    ): IWidgetData {\n        let perParticipantE2EE = false;\n        if (\n            client.getRoom(roomId)?.hasEncryptionStateEvent() &&\n            !SettingsStore.getValue(\"feature_disable_call_per_sender_encryption\")\n        )\n            perParticipantE2EE = true;\n\n        const intent = ElementCall.getWidgetIntent(client, roomId, voiceOnly);\n\n        return {\n            ...currentData,\n            ...overwriteData,\n            intent,\n            perParticipantE2EE,\n        };\n    }\n\n    private onCallEncryptionSettingsChange(): void {\n        this.widget.data = ElementCall.getWidgetData(this.client, this.roomId, this.widget.data ?? {}, {});\n    }\n\n    private constructor(\n        public session: MatrixRTCSession,\n        widget: IApp,\n        client: MatrixClient,\n    ) {\n        super(widget, client);\n\n        this.session.on(MatrixRTCSessionEvent.MembershipsChanged, this.onMembershipChanged);\n        this.client.matrixRTC.on(MatrixRTCSessionManagerEvents.SessionEnded, this.checkDestroy);\n        SettingsStore.watchSetting(\n            \"feature_disable_call_per_sender_encryption\",\n            null,\n            this.onCallEncryptionSettingsChange.bind(this),\n        );\n        this.updateParticipants();\n    }\n\n    public static get(room: Room, voiceOnly?: boolean): ElementCall | null {\n        const apps = WidgetStore.instance.getApps(room.roomId);\n        const hasEcWidget = apps.some((app) => WidgetType.CALL.matches(app.type));\n        const session = room.client.matrixRTC.getRoomSession(room);\n\n        // A call is present if we\n        // - have a widget: This means the create function was called.\n        // - or there is a running session where we have not yet created a widget for.\n        // - or this is a call room. Then we also always want to show a call.\n        if (hasEcWidget || session.memberships.length !== 0 || room.isCallRoom()) {\n            // create a widget for the case we are joining a running call and don't have on yet.\n            const availableOrCreatedWidget = ElementCall.createOrGetCallWidget(room.roomId, room.client);\n            return new ElementCall(session, availableOrCreatedWidget, room.client);\n        }\n\n        return null;\n    }\n\n    public static create(room: Room): void {\n        ElementCall.createOrGetCallWidget(room.roomId, room.client);\n    }\n\n    public async start(widgetGenerationParameters: WidgetGenerationParameters): Promise<ClientWidgetApi> {\n        // Some parameters may only be set once the user has chosen to interact with the call, regenerate the URL\n        // at this point in case any of the parameters have changed.\n        this.widgetGenerationParameters = { ...this.widgetGenerationParameters, ...widgetGenerationParameters };\n        this.widget.url = ElementCall.generateWidgetUrl(\n            this.client,\n            this.roomId,\n            this.widgetGenerationParameters,\n        ).toString();\n        const widgetApi = await super.start();\n        widgetApi.on(`action:${ElementWidgetActions.JoinCall}`, this.onJoin);\n        widgetApi.on(`action:${ElementWidgetActions.HangupCall}`, this.onHangup);\n        widgetApi.on(`action:${ElementWidgetActions.Close}`, this.onClose);\n        widgetApi.on(`action:${ElementWidgetActions.DeviceMute}`, this.onDeviceMute);\n        return widgetApi;\n    }\n\n    protected async performDisconnection(): Promise<void> {\n        const response = waitForEvent(\n            this.widgetApi!,\n            `action:${ElementWidgetActions.HangupCall}`,\n            (ev: CustomEvent<IWidgetApiRequest>) => {\n                ev.preventDefault();\n                this.widgetApi!.transport.reply(ev.detail, {}); // ack\n                return true;\n            },\n        );\n        const request = this.widgetApi!.transport.send(ElementWidgetActions.HangupCall, {});\n        try {\n            await Promise.all([request, response]);\n        } catch (e) {\n            throw new Error(`Failed to hangup call in room ${this.roomId}: ${e}`);\n        }\n    }\n\n    public close(): void {\n        this.widgetApi!.off(`action:${ElementWidgetActions.JoinCall}`, this.onJoin);\n        this.widgetApi!.off(`action:${ElementWidgetActions.HangupCall}`, this.onHangup);\n        this.widgetApi!.off(`action:${ElementWidgetActions.Close}`, this.onClose);\n        this.widgetApi!.off(`action:${ElementWidgetActions.DeviceMute}`, this.onDeviceMute);\n        super.close();\n    }\n\n    public destroy(): void {\n        ActiveWidgetStore.instance.destroyPersistentWidget(this.widget.id, this.widget.roomId);\n        WidgetStore.instance.removeVirtualWidget(this.widget.id, this.widget.roomId);\n        this.session.off(MatrixRTCSessionEvent.MembershipsChanged, this.onMembershipChanged);\n        this.client.matrixRTC.off(MatrixRTCSessionManagerEvents.SessionEnded, this.checkDestroy);\n\n        SettingsStore.unwatchSetting(this.settingsStoreCallEncryptionWatcher);\n        clearTimeout(this.terminationTimer);\n        this.terminationTimer = undefined;\n\n        super.destroy();\n    }\n\n    private checkDestroy = (): void => {\n        // A call ceases to exist as soon as all participants leave and also the\n        // user isn't looking at it (for example, waiting in an empty lobby)\n        if (this.session.memberships.length === 0 && !this.presented && !this.room.isCallRoom()) this.destroy();\n    };\n\n    private readonly onMembershipChanged = (): void => {\n        this.updateParticipants();\n        this.callType = this.session.getConsensusCallIntent() === \"audio\" ? CallType.Voice : CallType.Video;\n    };\n\n    private updateParticipants(): void {\n        const participants = new Map<RoomMember, Set<string>>();\n\n        for (const m of this.session.memberships) {\n            if (!m.sender) continue;\n            const member = this.room.getMember(m.sender);\n            if (member) {\n                if (participants.has(member)) {\n                    participants.get(member)?.add(m.deviceId);\n                } else {\n                    participants.set(member, new Set([m.deviceId]));\n                }\n            }\n        }\n\n        this.participants = participants;\n    }\n\n    private readonly onDeviceMute = (ev: CustomEvent<IWidgetApiRequest>): void => {\n        ev.preventDefault();\n        this.widgetApi!.transport.reply(ev.detail, {}); // ack\n    };\n\n    private readonly onJoin = (ev: CustomEvent<IWidgetApiRequest>): void => {\n        ev.preventDefault();\n        this.widgetApi!.transport.reply(ev.detail, {}); // ack\n        this.setConnected();\n    };\n\n    private readonly onHangup = async (ev: CustomEvent<IWidgetApiRequest>): Promise<void> => {\n        // If we're already in the middle of a client-initiated disconnection,\n        // ignore the event\n        if (this.connectionState === ConnectionState.Disconnecting) return;\n\n        ev.preventDefault();\n        this.widgetApi!.transport.reply(ev.detail, {}); // ack\n        this.setDisconnected();\n    };\n\n    private readonly onClose = async (ev: CustomEvent<IWidgetApiRequest>): Promise<void> => {\n        ev.preventDefault();\n        this.widgetApi!.transport.reply(ev.detail, {}); // ack\n        this.setDisconnected(); // Just in case the widget forgot to emit a hangup action (maybe it's in an error state)\n        this.close(); // User is done with the call; tell the UI to close it\n    };\n\n    public clean(): Promise<void> {\n        return Promise.resolve();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type MatrixClient,\n    Room,\n    PendingEventOrdering,\n    MatrixEvent,\n    Direction,\n    EventType,\n} from \"matrix-js-sdk/src/matrix\";\n\nimport { type Member } from \"../utils/direct-messages\";\n\nexport const LOCAL_ROOM_ID_PREFIX = \"local+\";\n\nexport enum LocalRoomState {\n    NEW, // new local room; only known to the client\n    CREATING, // real room is being created\n    CREATED, // real room has been created via API; events applied\n    ERROR, // error during room creation\n}\n\n/**\n * A local room that only exists client side.\n * Its main purpose is to be used for temporary rooms when creating a DM.\n */\nexport class LocalRoom extends Room {\n    /** Whether the actual room should be encrypted. */\n    public encrypted = false;\n    /** If the actual room has been created, this holds its ID. */\n    public actualRoomId?: string;\n    /** DM chat partner */\n    public targets: Member[] = [];\n    /** Callbacks that should be invoked after the actual room has been created. */\n    public afterCreateCallbacks: ((roomId: string) => void)[] = [];\n    public state: LocalRoomState = LocalRoomState.NEW;\n\n    public constructor(roomId: string, client: MatrixClient, myUserId: string) {\n        super(roomId, client, myUserId, { pendingEventOrdering: PendingEventOrdering.Detached });\n        this.name = this.getDefaultRoomName(myUserId);\n    }\n\n    public get isNew(): boolean {\n        return this.state === LocalRoomState.NEW;\n    }\n\n    public get isCreated(): boolean {\n        return this.state === LocalRoomState.CREATED;\n    }\n\n    public get isError(): boolean {\n        return this.state === LocalRoomState.ERROR;\n    }\n\n    /**\n     * Check if encryption is enabled in this room.\n     * True if the room has any encryption state event\n     */\n    public isEncryptionEnabled(): boolean {\n        const roomState = this.getLiveTimeline().getState(Direction.Forward);\n        if (!roomState) return false;\n\n        const stateEvents = roomState.getStateEvents(EventType.RoomEncryption);\n        if (stateEvents.length === 0) return false;\n\n        // if there is an encryption state event, it is encrypted.\n        // Regardless of the content/algorithm, we assume it is encrypted.\n        return stateEvents[0] instanceof MatrixEvent;\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type { ConfigApi as IConfigApi, Config } from \"@element-hq/element-web-module-api\";\nimport SdkConfig from \"../SdkConfig.ts\";\n\nexport class ConfigApi implements IConfigApi {\n    public get(): Config;\n    public get<K extends keyof Config>(key: K): Config[K];\n    public get<K extends keyof Config = never>(key?: K): Config | Config[K] {\n        if (key === undefined) {\n            return SdkConfig.get() as Config;\n        }\n        return SdkConfig.get(key);\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport type {\n    CustomComponentsApi as ICustomComponentsApi,\n    CustomMessageRenderFunction,\n    CustomMessageComponentProps as ModuleCustomMessageComponentProps,\n    OriginalMessageComponentProps,\n    CustomMessageRenderHints as ModuleCustomCustomMessageRenderHints,\n    MatrixEvent as ModuleMatrixEvent,\n    CustomRoomPreviewBarRenderFunction,\n} from \"@element-hq/element-web-module-api\";\nimport type React from \"react\";\n\ntype EventTypeOrFilter = Parameters<ICustomComponentsApi[\"registerMessageRenderer\"]>[0];\n\ntype EventRenderer = {\n    eventTypeOrFilter: EventTypeOrFilter;\n    renderer: CustomMessageRenderFunction;\n    hints: ModuleCustomCustomMessageRenderHints;\n};\n\ninterface CustomMessageComponentProps extends Omit<ModuleCustomMessageComponentProps, \"mxEvent\"> {\n    mxEvent: MatrixEvent;\n}\n\ninterface CustomMessageRenderHints extends Omit<ModuleCustomCustomMessageRenderHints, \"allowDownloadingMedia\"> {\n    // Note. This just makes it easier to use this API on Element Web as we already have the moduleized event stored.\n    allowDownloadingMedia?: () => Promise<boolean>;\n}\n\nexport class CustomComponentsApi implements ICustomComponentsApi {\n    /**\n     * Convert a matrix-js-sdk event into a ModuleMatrixEvent.\n     * @param mxEvent\n     * @returns An event object, or `null` if the event was not a message event.\n     */\n    private static getModuleMatrixEvent(mxEvent: MatrixEvent): ModuleMatrixEvent | null {\n        const eventId = mxEvent.getId();\n        const roomId = mxEvent.getRoomId();\n        const sender = mxEvent.sender;\n        // Typically we wouldn't expect messages without these keys to be rendered\n        // by the timeline, but for the sake of type safety.\n        if (!eventId || !roomId || !sender) {\n            // Not a message event.\n            return null;\n        }\n        return {\n            content: mxEvent.getContent(),\n            eventId,\n            originServerTs: mxEvent.getTs(),\n            roomId,\n            sender: sender.userId,\n            stateKey: mxEvent.getStateKey(),\n            type: mxEvent.getType(),\n            unsigned: mxEvent.getUnsigned(),\n        };\n    }\n\n    private readonly registeredMessageRenderers: EventRenderer[] = [];\n\n    public registerMessageRenderer(\n        eventTypeOrFilter: EventTypeOrFilter,\n        renderer: CustomMessageRenderFunction,\n        hints: ModuleCustomCustomMessageRenderHints = {},\n    ): void {\n        this.registeredMessageRenderers.push({ eventTypeOrFilter: eventTypeOrFilter, renderer, hints });\n    }\n\n    /**\n     * Select the correct renderer based on the event information.\n     * @param mxEvent The message event being rendered.\n     * @returns The registered renderer.\n     */\n    private selectRenderer(mxEvent: ModuleMatrixEvent): EventRenderer | undefined {\n        return this.registeredMessageRenderers.find((renderer) => {\n            if (typeof renderer.eventTypeOrFilter === \"string\") {\n                return renderer.eventTypeOrFilter === mxEvent.type;\n            } else {\n                try {\n                    return renderer.eventTypeOrFilter(mxEvent);\n                } catch (ex) {\n                    logger.warn(\"Message renderer failed to process filter\", ex);\n                    return false; // Skip erroring renderers.\n                }\n            }\n        });\n    }\n\n    /**\n     * Render the component for a message event.\n     * @param props Props to be passed to the custom renderer.\n     * @param originalComponent Function that will be rendered if no custom renderers are present, or as a child of a custom component.\n     * @returns A component if a custom renderer exists, or originalComponent returns a value. Otherwise null.\n     */\n    public renderMessage(\n        props: CustomMessageComponentProps,\n        originalComponent?: (props?: OriginalMessageComponentProps) => React.JSX.Element,\n    ): React.JSX.Element | null {\n        const moduleEv = CustomComponentsApi.getModuleMatrixEvent(props.mxEvent);\n        const renderer = moduleEv && this.selectRenderer(moduleEv);\n        if (renderer) {\n            try {\n                return renderer.renderer({ ...props, mxEvent: moduleEv }, originalComponent);\n            } catch (ex) {\n                logger.warn(\"Message renderer failed to render\", ex);\n                // Fall through to original component. If the module encounters an error we still want to display messages to the user!\n            }\n        }\n        return originalComponent?.() ?? null;\n    }\n\n    /**\n     * Get hints about an message before rendering it.\n     * @param mxEvent The message event being rendered.\n     * @returns A component if a custom renderer exists, or originalComponent returns a value. Otherwise null.\n     */\n    public getHintsForMessage(mxEvent: MatrixEvent): CustomMessageRenderHints | null {\n        const moduleEv = CustomComponentsApi.getModuleMatrixEvent(mxEvent);\n        const renderer = moduleEv && this.selectRenderer(moduleEv);\n        if (renderer) {\n            return {\n                ...renderer.hints,\n                // Convert from js-sdk style events to module events automatically.\n                allowDownloadingMedia: renderer.hints.allowDownloadingMedia\n                    ? () => renderer.hints.allowDownloadingMedia!(moduleEv)\n                    : undefined,\n            };\n        }\n        return null;\n    }\n\n    private _roomPreviewBarRenderer?: CustomRoomPreviewBarRenderFunction;\n\n    /**\n     * Get the custom room preview bar renderer, if any has been registered.\n     */\n    public get roomPreviewBarRenderer(): CustomRoomPreviewBarRenderFunction | undefined {\n        return this._roomPreviewBarRenderer;\n    }\n\n    /**\n     * Register a custom room preview bar renderer.\n     * @param renderer - the function that will render the custom room preview bar.\n     */\n    public registerRoomPreviewBar(renderer: CustomRoomPreviewBarRenderFunction): void {\n        this._roomPreviewBarRenderer = renderer;\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Profile, Watchable } from \"@element-hq/element-web-module-api\";\n\nimport { OwnProfileStore } from \"../stores/OwnProfileStore.ts\";\nimport { UPDATE_EVENT } from \"../stores/AsyncStore.ts\";\n\nexport class WatchableProfile extends Watchable<Profile> {\n    public constructor() {\n        super({});\n        this.value = this.profile;\n\n        OwnProfileStore.instance.on(UPDATE_EVENT, this.onProfileChange);\n    }\n\n    private get profile(): Profile {\n        return {\n            isGuest: OwnProfileStore.instance.matrixClient?.isGuest() ?? false,\n            userId: OwnProfileStore.instance.matrixClient?.getUserId() ?? undefined,\n            displayName: OwnProfileStore.instance.displayName ?? undefined,\n        };\n    }\n\n    private readonly onProfileChange = (): void => {\n        this.value = this.profile;\n    };\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type {\n    LocationRenderFunction,\n    NavigationApi as INavigationApi,\n    OpenRoomOptions,\n} from \"@element-hq/element-web-module-api\";\nimport { navigateToPermalink } from \"../utils/permalinks/navigator.ts\";\nimport { parsePermalink } from \"../utils/permalinks/Permalinks.ts\";\nimport dispatcher from \"../dispatcher/dispatcher.ts\";\nimport { Action } from \"../dispatcher/actions.ts\";\nimport type { ViewRoomPayload } from \"../dispatcher/payloads/ViewRoomPayload.ts\";\n\nexport class NavigationApi implements INavigationApi {\n    public locationRenderers = new Map<string, LocationRenderFunction>();\n\n    public async toMatrixToLink(link: string, join = false): Promise<void> {\n        navigateToPermalink(link);\n\n        const parts = parsePermalink(link);\n        if (parts?.roomIdOrAlias) {\n            this.openRoom(parts.roomIdOrAlias, {\n                viaServers: parts.viaServers ?? undefined,\n                autoJoin: join,\n            });\n        }\n    }\n\n    public registerLocationRenderer(path: string, renderer: LocationRenderFunction): void {\n        this.locationRenderers.set(path, renderer);\n    }\n\n    public openRoom(roomIdOrAlias: string, opts: OpenRoomOptions = {}): void {\n        const key = roomIdOrAlias.startsWith(\"#\") ? \"room_alias\" : \"room_id\";\n        dispatcher.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            [key]: roomIdOrAlias,\n            via_servers: opts.viaServers,\n            auto_join: opts.autoJoin,\n            metricsTrigger: undefined,\n        });\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ComponentType, type JSX, useCallback } from \"react\";\nimport { type DialogProps, type DialogOptions, type DialogHandle } from \"@element-hq/element-web-module-api\";\n\nimport Modal from \"../Modal\";\nimport BaseDialog from \"../components/views/dialogs/BaseDialog.tsx\";\n\nconst OuterDialog = <M, P extends object>({\n    title,\n    Dialog,\n    props,\n    onFinished,\n}: {\n    title: string;\n    Dialog: ComponentType<DialogProps<M> & P>;\n    props: P;\n    onFinished(ok: boolean, model: M | null): void;\n}): JSX.Element => {\n    const close = useCallback(() => onFinished(false, null), [onFinished]);\n    const submit = useCallback((model: M) => onFinished(true, model), [onFinished]);\n    return (\n        <BaseDialog onFinished={close} title={title}>\n            <Dialog {...props} onSubmit={submit} onCancel={close} />\n        </BaseDialog>\n    );\n};\n\nexport function openDialog<M, P extends object>(\n    initialOptions: DialogOptions,\n    Dialog: ComponentType<P & DialogProps<M>>,\n    props: P,\n): DialogHandle<M> {\n    const { close, finished } = Modal.createDialog(OuterDialog<M, P>, {\n        title: initialOptions.title,\n        Dialog,\n        props,\n    });\n\n    return {\n        finished: finished.then(([ok, model]) => ({\n            ok: ok ?? false,\n            model: model ?? null,\n        })),\n        close: () => close(false, null),\n    };\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type AccountAuthInfo } from \"@element-hq/element-web-module-api\";\nimport { sleep } from \"matrix-js-sdk/src/utils\";\n\nimport type { OverwriteLoginPayload } from \"../dispatcher/payloads/OverwriteLoginPayload.ts\";\nimport { Action } from \"../dispatcher/actions.ts\";\nimport defaultDispatcher from \"../dispatcher/dispatcher.ts\";\nimport type { ActionPayload } from \"../dispatcher/payloads.ts\";\n\nexport async function overwriteAccountAuth(accountInfo: AccountAuthInfo): Promise<void> {\n    const { promise, resolve } = Promise.withResolvers<void>();\n\n    const onAction = (payload: ActionPayload): void => {\n        if (payload.action === Action.OnLoggedIn) {\n            // We want to wait for the new login to complete before returning.\n            // See `Action.OnLoggedIn` in dispatcher.\n            resolve();\n        }\n    };\n    const dispatcherRef = defaultDispatcher.register(onAction);\n\n    defaultDispatcher.dispatch<OverwriteLoginPayload>(\n        {\n            action: Action.OverwriteLogin,\n            credentials: {\n                ...accountInfo,\n                guest: false,\n            },\n        },\n        true,\n    ); // require to be sync to match inherited interface behaviour\n\n    // wait for login to complete\n    await promise;\n    defaultDispatcher.unregister(dispatcherRef);\n    await sleep(0); // wait for the next tick to ensure the login is fully processed\n}\n","/*\nCopyright 2025 Element Creations Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type RoomViewProps, type BuiltinsApi } from \"@element-hq/element-web-module-api\";\n\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport type { Room } from \"matrix-js-sdk/src/matrix\";\nimport type { ModuleNotificationDecorationProps } from \"./components/ModuleNotificationDecoration\";\n\ninterface RoomViewPropsWithRoomId extends RoomViewProps {\n    /**\n     * The ID of the room to display\n     */\n    roomId?: string;\n}\n\ninterface RoomAvatarProps {\n    room: Room;\n    size?: string;\n}\n\ninterface Components {\n    roomView: React.ComponentType<RoomViewPropsWithRoomId>;\n    roomAvatar: React.ComponentType<RoomAvatarProps>;\n    notificationDecoration: React.ComponentType<ModuleNotificationDecorationProps>;\n}\n\nexport class ElementWebBuiltinsApi implements BuiltinsApi {\n    private _roomView?: Components[\"roomView\"];\n    private _roomAvatar?: Components[\"roomAvatar\"];\n    private _notificationDecoration?: Components[\"notificationDecoration\"];\n\n    /**\n     * Sets the components used by the API.\n     *\n     * This only really exists here because referencing these components directly causes a nightmare of\n     * circular dependencies that break the whole app, so instead we avoid referencing it here\n     * and pass it in from somewhere it's already referenced (see related comment in app.tsx).\n     *\n     * @param component The components used by the api, see {@link Components}\n     */\n    public setComponents(components: Components): void {\n        this._roomView = components.roomView;\n        this._roomAvatar = components.roomAvatar;\n        this._notificationDecoration = components.notificationDecoration;\n    }\n\n    public getRoomViewComponent(): React.ComponentType<RoomViewPropsWithRoomId> {\n        if (!this._roomView) {\n            throw new Error(\"No RoomView component has been set\");\n        }\n        return this._roomView;\n    }\n\n    public getRoomAvatarComponent(): React.ComponentType<RoomAvatarProps> {\n        if (!this._roomAvatar) {\n            throw new Error(\"No RoomAvatar component has been set\");\n        }\n        return this._roomAvatar;\n    }\n\n    public getNotificationDecorationComponent(): React.ComponentType<ModuleNotificationDecorationProps> {\n        if (!this._notificationDecoration) {\n            throw new Error(\"No NotificationDecoration component has been set\");\n        }\n        return this._notificationDecoration;\n    }\n\n    public renderRoomView(roomId: string, props?: RoomViewProps): React.ReactNode {\n        const Component = this.getRoomViewComponent();\n        return <Component roomId={roomId} {...props} />;\n    }\n\n    public renderRoomAvatar(roomId: string, size?: string): React.ReactNode {\n        const room = MatrixClientPeg.safeGet().getRoom(roomId);\n        if (!room) {\n            throw new Error(`No room such room: ${roomId}`);\n        }\n        const Component = this.getRoomAvatarComponent();\n        return <Component room={room} size={size} />;\n    }\n\n    public renderNotificationDecoration(roomId: string): React.ReactNode {\n        const room = MatrixClientPeg.safeGet().getRoom(roomId);\n        if (!room) {\n            throw new Error(`No room such room: ${roomId}`);\n        }\n        const Component = this.getNotificationDecorationComponent();\n        return <Component room={room} />;\n    }\n}\n","/*\nCopyright 2025 Element Creations Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room as IRoom, Watchable } from \"@element-hq/element-web-module-api\";\nimport { RoomEvent, type Room as SdkRoom } from \"matrix-js-sdk/src/matrix\";\n\nexport class Room implements IRoom {\n    public name: Watchable<string>;\n\n    public constructor(private sdkRoom: SdkRoom) {\n        this.name = new WatchableName(sdkRoom);\n    }\n\n    public getLastActiveTimestamp(): number {\n        return this.sdkRoom.getLastActiveTimestamp();\n    }\n\n    public get id(): string {\n        return this.sdkRoom.roomId;\n    }\n}\n\n/**\n * A custom watchable for room name.\n */\nclass WatchableName extends Watchable<string> {\n    public constructor(private sdkRoom: SdkRoom) {\n        super(sdkRoom.name);\n    }\n\n    private onNameUpdate = (): void => {\n        super.value = this.sdkRoom.name;\n    };\n    protected onFirstWatch(): void {\n        this.sdkRoom.on(RoomEvent.Name, this.onNameUpdate);\n    }\n\n    protected onLastWatch(): void {\n        this.sdkRoom.off(RoomEvent.Name, this.onNameUpdate);\n    }\n}\n","/*\nCopyright 2025 Element Creations Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { Watchable, type AccountDataApi as IAccountDataApi } from \"@element-hq/element-web-module-api\";\nimport { ClientEvent, type MatrixEvent, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\n\nexport class AccountDataApi implements IAccountDataApi {\n    public get(eventType: string): Watchable<unknown> {\n        const cli = MatrixClientPeg.safeGet();\n        return new AccountDataWatchable(cli, eventType);\n    }\n\n    public async set(eventType: string, content: any): Promise<void> {\n        const cli = MatrixClientPeg.safeGet();\n        //@ts-expect-error: JS-SDK accepts known event-types, intentionally allow arbitrary types.\n        await cli.setAccountData(eventType, content);\n    }\n\n    public async delete(eventType: string): Promise<void> {\n        const cli = MatrixClientPeg.safeGet();\n        //@ts-expect-error: JS-SDK accepts known event-types, intentionally allow arbitrary types.\n        await cli.deleteAccountData(eventType);\n    }\n}\n\nclass AccountDataWatchable extends Watchable<unknown> {\n    public constructor(\n        private cli: MatrixClient,\n        private eventType: string,\n    ) {\n        //@ts-expect-error: JS-SDK accepts known event-types, intentionally allow arbitrary types.\n        super(cli.getAccountData(eventType)?.getContent());\n    }\n\n    private onAccountData = (event: MatrixEvent): void => {\n        if (event.getType() === this.eventType) {\n            this.value = event.getContent();\n        }\n    };\n\n    protected onFirstWatch(): void {\n        this.cli.on(ClientEvent.AccountData, this.onAccountData);\n    }\n\n    protected onLastWatch(): void {\n        this.cli.off(ClientEvent.AccountData, this.onAccountData);\n    }\n}\n","/*\nCopyright 2025 Element Creations Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\nimport type { ClientApi as IClientApi, Room } from \"@element-hq/element-web-module-api\";\nimport { Room as ModuleRoom } from \"./models/Room\";\nimport { AccountDataApi } from \"./AccountDataApi\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\n\nexport class ClientApi implements IClientApi {\n    public readonly accountData = new AccountDataApi();\n\n    public getRoom(roomId: string): Room | null {\n        const sdkRoom = MatrixClientPeg.safeGet().getRoom(roomId);\n        if (sdkRoom) return new ModuleRoom(sdkRoom);\n        return null;\n    }\n}\n","/*\nCopyright 2025 Element Creations Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\nimport {\n    type StoresApi as IStoresApi,\n    type RoomListStoreApi as IRoomListStore,\n    type Room,\n    Watchable,\n} from \"@element-hq/element-web-module-api\";\n\nimport type { RoomListStoreV3Class, RoomListStoreV3Event } from \"../stores/room-list-v3/RoomListStoreV3\";\nimport { Room as ModuleRoom } from \"./models/Room\";\n\ninterface RlsEvents {\n    LISTS_LOADED_EVENT: RoomListStoreV3Event.ListsLoaded;\n    LISTS_UPDATE_EVENT: RoomListStoreV3Event.ListsUpdate;\n}\n\nexport class RoomListStoreApi implements IRoomListStore {\n    private rls?: RoomListStoreV3Class;\n    private LISTS_LOADED_EVENT?: RoomListStoreV3Event.ListsLoaded;\n    private LISTS_UPDATE_EVENT?: RoomListStoreV3Event.ListsUpdate;\n    public readonly moduleLoadPromise: Promise<void>;\n\n    public constructor() {\n        this.moduleLoadPromise = this.init();\n    }\n\n    /**\n     * Load the RLS through a dynamic import. This is necessary to prevent\n     * circular dependency issues.\n     */\n    private async init(): Promise<void> {\n        const module = await import(\"../stores/room-list-v3/RoomListStoreV3\");\n        this.rls = module.default.instance;\n        this.LISTS_LOADED_EVENT = module.LISTS_LOADED_EVENT;\n        this.LISTS_UPDATE_EVENT = module.LISTS_UPDATE_EVENT;\n    }\n\n    public getRooms(): RoomsWatchable {\n        return new RoomsWatchable(this.roomListStore, this.events);\n    }\n\n    private get events(): RlsEvents {\n        if (!this.LISTS_LOADED_EVENT || !this.LISTS_UPDATE_EVENT) {\n            throw new Error(\"Event type was not loaded correctly, did you forget to await waitForReady()?\");\n        }\n        return { LISTS_LOADED_EVENT: this.LISTS_LOADED_EVENT, LISTS_UPDATE_EVENT: this.LISTS_UPDATE_EVENT };\n    }\n\n    private get roomListStore(): RoomListStoreV3Class {\n        if (!this.rls) {\n            throw new Error(\"rls is undefined, did you forget to await waitForReady()?\");\n        }\n        return this.rls;\n    }\n\n    public async waitForReady(): Promise<void> {\n        // Wait for the module to load first\n        await this.moduleLoadPromise;\n\n        // Check if RLS is already loaded\n        if (!this.roomListStore.isLoadingRooms) return;\n\n        // Await a promise that resolves when RLS has loaded\n        const { promise, resolve } = Promise.withResolvers<void>();\n        const { LISTS_LOADED_EVENT } = this.events;\n        this.roomListStore.once(LISTS_LOADED_EVENT, resolve);\n        await promise;\n    }\n}\n\nclass RoomsWatchable extends Watchable<Room[]> {\n    public constructor(\n        private readonly rls: RoomListStoreV3Class,\n        private readonly events: RlsEvents,\n    ) {\n        super(rls.getSortedRooms().map((sdkRoom) => new ModuleRoom(sdkRoom)));\n    }\n\n    private onRlsUpdate = (): void => {\n        this.value = this.rls.getSortedRooms().map((sdkRoom) => new ModuleRoom(sdkRoom));\n    };\n\n    protected onFirstWatch(): void {\n        this.rls.on(this.events.LISTS_UPDATE_EVENT, this.onRlsUpdate);\n    }\n\n    protected onLastWatch(): void {\n        this.rls.off(this.events.LISTS_UPDATE_EVENT, this.onRlsUpdate);\n    }\n}\n\nexport class StoresApi implements IStoresApi {\n    private roomListStoreApi?: IRoomListStore;\n\n    public get roomListStore(): IRoomListStore {\n        if (!this.roomListStoreApi) {\n            this.roomListStoreApi = new RoomListStoreApi();\n        }\n        return this.roomListStoreApi;\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { createRoot, type Root } from \"react-dom/client\";\nimport { type Api, type RuntimeModuleConstructor } from \"@element-hq/element-web-module-api\";\nimport { I18nApi } from \"@element-hq/web-shared-components\";\n\nimport { ModuleRunner } from \"./ModuleRunner.ts\";\nimport AliasCustomisations from \"../customisations/Alias.ts\";\nimport { RoomListCustomisations } from \"../customisations/RoomList.ts\";\nimport ChatExportCustomisations from \"../customisations/ChatExport.ts\";\nimport { ComponentVisibilityCustomisations } from \"../customisations/ComponentVisibility.ts\";\nimport DirectoryCustomisations from \"../customisations/Directory.ts\";\nimport LifecycleCustomisations from \"../customisations/Lifecycle.ts\";\nimport * as MediaCustomisations from \"../customisations/Media.ts\";\nimport UserIdentifierCustomisations from \"../customisations/UserIdentifier.ts\";\nimport { WidgetPermissionCustomisations } from \"../customisations/WidgetPermissions.ts\";\nimport { WidgetVariableCustomisations } from \"../customisations/WidgetVariables.ts\";\nimport { ConfigApi } from \"./ConfigApi.ts\";\nimport { CustomComponentsApi } from \"./customComponentApi\";\nimport { WatchableProfile } from \"./Profile.ts\";\nimport { NavigationApi } from \"./Navigation.ts\";\nimport { openDialog } from \"./Dialog.tsx\";\nimport { overwriteAccountAuth } from \"./Auth.ts\";\nimport { ElementWebExtrasApi } from \"./ExtrasApi.ts\";\nimport { ElementWebBuiltinsApi } from \"./BuiltinsApi.tsx\";\nimport { ClientApi } from \"./ClientApi.ts\";\nimport { StoresApi } from \"./StoresApi.ts\";\n\nconst legacyCustomisationsFactory = <T extends object>(baseCustomisations: T) => {\n    let used = false;\n    return (customisations: T) => {\n        if (used) throw new Error(\"Legacy customisations can only be registered by one module\");\n        Object.assign(baseCustomisations, customisations);\n        used = true;\n    };\n};\n\n/**\n * Implementation of the @element-hq/element-web-module-api runtime module API.\n */\nexport class ModuleApi implements Api {\n    private static _instance: ModuleApi;\n\n    public static get instance(): ModuleApi {\n        if (!ModuleApi._instance) {\n            ModuleApi._instance = new ModuleApi();\n            window.mxModuleApi = ModuleApi._instance;\n        }\n        return ModuleApi._instance;\n    }\n\n    /* eslint-disable @typescript-eslint/naming-convention */\n    public async _registerLegacyModule(LegacyModule: RuntimeModuleConstructor): Promise<void> {\n        ModuleRunner.instance.registerModule((api) => new LegacyModule(api));\n    }\n    public readonly _registerLegacyAliasCustomisations = legacyCustomisationsFactory(AliasCustomisations);\n    public readonly _registerLegacyChatExportCustomisations = legacyCustomisationsFactory(ChatExportCustomisations);\n    public readonly _registerLegacyComponentVisibilityCustomisations = legacyCustomisationsFactory(\n        ComponentVisibilityCustomisations,\n    );\n    public readonly _registerLegacyDirectoryCustomisations = legacyCustomisationsFactory(DirectoryCustomisations);\n    public readonly _registerLegacyLifecycleCustomisations = legacyCustomisationsFactory(LifecycleCustomisations);\n    public readonly _registerLegacyMediaCustomisations = legacyCustomisationsFactory(MediaCustomisations);\n    public readonly _registerLegacyRoomListCustomisations = legacyCustomisationsFactory(RoomListCustomisations);\n    public readonly _registerLegacyUserIdentifierCustomisations =\n        legacyCustomisationsFactory(UserIdentifierCustomisations);\n    public readonly _registerLegacyWidgetPermissionsCustomisations =\n        legacyCustomisationsFactory(WidgetPermissionCustomisations);\n    public readonly _registerLegacyWidgetVariablesCustomisations =\n        legacyCustomisationsFactory(WidgetVariableCustomisations);\n    /* eslint-enable @typescript-eslint/naming-convention */\n\n    public readonly navigation = new NavigationApi();\n    public readonly openDialog = openDialog;\n    public readonly overwriteAccountAuth = overwriteAccountAuth;\n    public readonly profile = new WatchableProfile();\n\n    public readonly config = new ConfigApi();\n    public readonly i18n = new I18nApi();\n    public readonly customComponents = new CustomComponentsApi();\n    public readonly extras = new ElementWebExtrasApi();\n    public readonly builtins = new ElementWebBuiltinsApi();\n    public readonly rootNode = document.getElementById(\"matrixchat\")!;\n    public readonly client = new ClientApi();\n    public readonly stores = new StoresApi();\n\n    public createRoot(element: Element): Root {\n        return createRoot(element);\n    }\n}\n\nexport type ModuleApiType = ModuleApi;\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useState } from \"react\";\nimport { type SpacePanelItemProps, type ExtrasApi } from \"@element-hq/element-web-module-api\";\nimport { TypedEventEmitter } from \"matrix-js-sdk/src/matrix\";\n\nimport { useTypedEventEmitter } from \"../hooks/useEventEmitter\";\n\nexport interface ModuleSpacePanelItem extends SpacePanelItemProps {\n    spaceKey: string;\n}\n\nenum ExtrasApiEvent {\n    SpacePanelItemsChanged = \"SpacePanelItemsChanged\",\n}\n\ninterface EmittedEvents {\n    [ExtrasApiEvent.SpacePanelItemsChanged]: () => void;\n}\n\nexport class ElementWebExtrasApi extends TypedEventEmitter<keyof EmittedEvents, EmittedEvents> implements ExtrasApi {\n    public spacePanelItems = new Map<string, SpacePanelItemProps>();\n    public visibleRoomBySpaceKey = new Map<string, () => string[]>();\n\n    public setSpacePanelItem(spacekey: string, item: SpacePanelItemProps): void {\n        this.spacePanelItems.set(spacekey, item);\n        this.emit(ExtrasApiEvent.SpacePanelItemsChanged);\n    }\n\n    public getVisibleRoomBySpaceKey(spaceKey: string, cb: () => string[]): void {\n        this.visibleRoomBySpaceKey.set(spaceKey, cb);\n    }\n}\n\nexport function useModuleSpacePanelItems(api: ElementWebExtrasApi): ModuleSpacePanelItem[] {\n    const getItems = (): ModuleSpacePanelItem[] => {\n        return Array.from(api.spacePanelItems.entries()).map(([spaceKey, item]) => ({\n            spaceKey,\n            ...item,\n        }));\n    };\n\n    const [items, setItems] = useState<ModuleSpacePanelItem[]>(getItems);\n\n    useTypedEventEmitter(api, ExtrasApiEvent.SpacePanelItemsChanged, () => {\n        setItems(getItems());\n    });\n\n    return items;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { createRef, type RefObject } from \"react\";\nimport { type DialogContent, type DialogProps } from \"@matrix-org/react-sdk-module-api/lib/components/DialogContent\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type ModuleApi } from \"@matrix-org/react-sdk-module-api/lib/ModuleApi\";\nimport { type ModuleUiDialogOptions } from \"@matrix-org/react-sdk-module-api/lib/types/ModuleUiDialogOptions\";\n\nimport ScrollableBaseModal, { type IScrollableBaseState } from \"./ScrollableBaseModal\";\nimport { _t } from \"../../../languageHandler\";\n\ninterface IProps<P extends DialogProps, C extends DialogContent<P>> {\n    contentFactory: (props: P, ref: React.RefObject<C | null>) => React.ReactNode;\n    additionalContentProps: Omit<P, keyof DialogProps> | undefined;\n    initialOptions: ModuleUiDialogOptions;\n    moduleApi: ModuleApi;\n    onFinished(ok?: boolean, model?: Awaited<ReturnType<DialogContent<P & DialogProps>[\"trySubmit\"]>>): void;\n}\n\ninterface IState extends IScrollableBaseState {\n    // nothing special\n}\n\nexport class ModuleUiDialog<\n    P extends DialogProps = DialogProps,\n    C extends DialogContent<P> = DialogContent<P>,\n> extends ScrollableBaseModal<IProps<P, C>, IState> {\n    private contentRef = createRef<C>();\n\n    public constructor(props: IProps<P, C>) {\n        super(props);\n\n        this.state = {\n            title: this.props.initialOptions.title,\n            actionLabel: this.props.initialOptions.actionLabel ?? _t(\"action|ok\"),\n            cancelLabel: this.props.initialOptions.cancelLabel,\n            canSubmit: this.props.initialOptions.canSubmit ?? true,\n        };\n    }\n\n    protected async submit(): Promise<void> {\n        try {\n            const model = await this.contentRef.current!.trySubmit();\n            this.props.onFinished(true, model);\n        } catch (e) {\n            logger.error(\"Error during submission of module dialog:\", e);\n        }\n    }\n\n    protected cancel(): void {\n        this.props.onFinished(false);\n    }\n\n    private setOptions(options: ModuleUiDialogOptions): void {\n        this.setState((state) => ({ ...state, ...options }));\n    }\n\n    protected renderContent(): React.ReactNode {\n        const dialogProps: DialogProps = {\n            moduleApi: this.props.moduleApi,\n            setOptions: this.setOptions.bind(this),\n            cancel: this.cancel.bind(this),\n        };\n\n        // Typescript isn't very happy understanding that `contentProps` satisfies `P`\n        const contentProps: P = {\n            ...this.props.additionalContentProps,\n            ...dialogProps,\n        } as unknown as P;\n\n        // XXX: we have to fudge the types here a little as the react-sdk-module-api lacks React 19 support\n        return (\n            <div className=\"mx_ModuleUiDialog\">\n                {this.props.contentFactory(contentProps, this.contentRef as RefObject<C>)}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ModuleApi } from \"@matrix-org/react-sdk-module-api/lib/ModuleApi\";\nimport {\n    type TranslationStringsObject,\n    type PlainSubstitution,\n} from \"@matrix-org/react-sdk-module-api/lib/types/translations\";\nimport { type DialogContent, type DialogProps } from \"@matrix-org/react-sdk-module-api/lib/components/DialogContent\";\nimport { type AccountAuthInfo } from \"@matrix-org/react-sdk-module-api/lib/types/AccountAuthInfo\";\nimport * as Matrix from \"matrix-js-sdk/src/matrix\";\nimport { type IRegisterRequestParams } from \"matrix-js-sdk/src/matrix\";\nimport { type ModuleUiDialogOptions } from \"@matrix-org/react-sdk-module-api/lib/types/ModuleUiDialogOptions\";\n\nimport type React from \"react\";\nimport Modal from \"../Modal\";\nimport { _t } from \"../languageHandler\";\nimport { ModuleUiDialog } from \"../components/views/dialogs/ModuleUiDialog\";\nimport SdkConfig from \"../SdkConfig\";\nimport PlatformPeg from \"../PlatformPeg\";\nimport dispatcher from \"../dispatcher/dispatcher\";\nimport { navigateToPermalink } from \"../utils/permalinks/navigator\";\nimport { parsePermalink } from \"../utils/permalinks/Permalinks\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { Action } from \"../dispatcher/actions\";\nimport { type OverwriteLoginPayload } from \"../dispatcher/payloads/OverwriteLoginPayload\";\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport WidgetStore, { type IApp } from \"../stores/WidgetStore\";\nimport { type Container, WidgetLayoutStore } from \"../stores/widgets/WidgetLayoutStore\";\nimport type { ViewRoomPayload } from \"../dispatcher/payloads/ViewRoomPayload.ts\";\n\n/**\n * Glue between the `ModuleApi` interface and the react-sdk. Anticipates one instance\n * to be assigned to a single module.\n */\nexport class ProxiedModuleApi implements ModuleApi {\n    private cachedTranslations?: TranslationStringsObject;\n\n    private overrideLoginResolve?: () => void;\n\n    public constructor() {\n        dispatcher.register(this.onAction);\n    }\n\n    private onAction = (payload: ActionPayload): void => {\n        if (payload.action === Action.OnLoggedIn) {\n            this.overrideLoginResolve?.();\n        }\n    };\n\n    /**\n     * All custom translations used by the associated module.\n     */\n    public get translations(): TranslationStringsObject | undefined {\n        return this.cachedTranslations;\n    }\n\n    /**\n     * @override\n     */\n    public registerTranslations(translations: TranslationStringsObject): void {\n        this.cachedTranslations = translations;\n    }\n\n    /**\n     * @override\n     */\n    public translateString(s: TranslationKey, variables?: Record<string, PlainSubstitution>): string {\n        return _t(s, variables);\n    }\n\n    /**\n     * @override\n     */\n    public openDialog<M extends object, P extends DialogProps, C extends DialogContent<P>>(\n        initialTitleOrOptions: string | ModuleUiDialogOptions,\n        body: (props: P, ref: React.RefObject<C | null>) => React.ReactNode,\n        props?: Omit<P, keyof DialogProps>,\n    ): Promise<{ didOkOrSubmit: boolean; model: M }> {\n        const initialOptions: ModuleUiDialogOptions =\n            typeof initialTitleOrOptions === \"string\" ? { title: initialTitleOrOptions } : initialTitleOrOptions;\n\n        return new Promise<{ didOkOrSubmit: boolean; model: M }>((resolve) => {\n            Modal.createDialog(\n                ModuleUiDialog<P, C>,\n                {\n                    initialOptions,\n                    contentFactory: body,\n                    moduleApi: this,\n                    additionalContentProps: props,\n                },\n                \"mx_CompoundDialog\",\n            ).finished.then(([didOkOrSubmit, model]) => {\n                resolve({ didOkOrSubmit: !!didOkOrSubmit, model: model as M });\n            });\n        });\n    }\n\n    /**\n     * @override\n     */\n    public async registerSimpleAccount(\n        username: string,\n        password: string,\n        displayName?: string,\n    ): Promise<AccountAuthInfo> {\n        const hsUrl = SdkConfig.get(\"validated_server_config\")?.hsUrl;\n        if (!hsUrl) throw new Error(\"Could not get homeserver url\");\n        const client = Matrix.createClient({ baseUrl: hsUrl });\n        const deviceName =\n            SdkConfig.get(\"default_device_display_name\") || PlatformPeg.get()?.getDefaultDeviceDisplayName();\n        const req: IRegisterRequestParams = {\n            username,\n            password,\n            initial_device_display_name: deviceName,\n            auth: undefined,\n            inhibit_login: false,\n        };\n        const creds = await client.registerRequest(req).catch((resp) =>\n            client.registerRequest({\n                ...req,\n                auth: {\n                    session: resp.data.session,\n                    type: \"m.login.dummy\",\n                },\n            }),\n        );\n\n        if (displayName) {\n            const profileClient = Matrix.createClient({\n                baseUrl: hsUrl,\n                userId: creds.user_id,\n                deviceId: creds.device_id,\n                accessToken: creds.access_token,\n            });\n            await profileClient.setDisplayName(displayName);\n        }\n\n        return {\n            homeserverUrl: hsUrl,\n            userId: creds.user_id!,\n            deviceId: creds.device_id!,\n            accessToken: creds.access_token!,\n        };\n    }\n\n    /**\n     * @override\n     */\n    public async overwriteAccountAuth(accountInfo: AccountAuthInfo): Promise<void> {\n        // We want to wait for the new login to complete before returning.\n        // See `Action.OnLoggedIn` in dispatcher.\n        const awaitNewLogin = new Promise<void>((resolve) => {\n            this.overrideLoginResolve = resolve;\n        });\n\n        dispatcher.dispatch<OverwriteLoginPayload>(\n            {\n                action: Action.OverwriteLogin,\n                credentials: {\n                    ...accountInfo,\n                    guest: false,\n                },\n            },\n            true,\n        ); // require to be sync to match inherited interface behaviour\n\n        // wait for login to complete\n        await awaitNewLogin;\n    }\n\n    /**\n     * @override\n     */\n    public async navigatePermalink(uri: string, andJoin?: boolean): Promise<void> {\n        navigateToPermalink(uri);\n\n        const parts = parsePermalink(uri);\n        if (parts?.roomIdOrAlias) {\n            if (parts.roomIdOrAlias.startsWith(\"#\")) {\n                dispatcher.dispatch<ViewRoomPayload>({\n                    action: Action.ViewRoom,\n                    room_alias: parts.roomIdOrAlias,\n                    via_servers: parts.viaServers ?? undefined,\n                    auto_join: andJoin ?? false,\n                    metricsTrigger: undefined,\n                });\n            } else {\n                dispatcher.dispatch<ViewRoomPayload>({\n                    action: Action.ViewRoom,\n                    room_id: parts.roomIdOrAlias,\n                    via_servers: parts.viaServers ?? undefined,\n                    auto_join: andJoin ?? false,\n                    metricsTrigger: undefined,\n                });\n            }\n        }\n    }\n\n    /**\n     * @override\n     */\n    public getConfigValue<T>(namespace: string, key: string): T | undefined {\n        // Force cast to `any` because the namespace won't be known to the SdkConfig types\n        const maybeObj = SdkConfig.get(namespace as any);\n        if (!maybeObj || !(typeof maybeObj === \"object\")) return undefined;\n        return maybeObj[key];\n    }\n\n    /**\n     * @override\n     */\n    public getApps(roomId: string): IApp[] {\n        return WidgetStore.instance.getApps(roomId);\n    }\n\n    /**\n     * @override\n     */\n    public getAppAvatarUrl(app: IApp, width?: number, height?: number, resizeMethod?: string): string | null {\n        if (!app.avatar_url) return null;\n        // eslint-disable-next-line no-restricted-properties\n        return MatrixClientPeg.safeGet().mxcUrlToHttp(app.avatar_url, width, height, resizeMethod);\n    }\n\n    /**\n     * @override\n     */\n    public isAppInContainer(app: IApp, container: Container, roomId: string): boolean {\n        const room = MatrixClientPeg.safeGet().getRoom(roomId);\n        if (!room) return false;\n        return WidgetLayoutStore.instance.isInContainer(room, app, container);\n    }\n\n    /**\n     * @override\n     */\n    public moveAppToContainer(app: IApp, container: Container, roomId: string): void {\n        const room = MatrixClientPeg.safeGet().getRoom(roomId);\n        if (!room) return;\n        WidgetLayoutStore.instance.moveToContainer(room, app, container);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type RuntimeModule } from \"@matrix-org/react-sdk-module-api/lib/RuntimeModule\";\n\nimport { type ModuleFactory } from \"./ModuleFactory\";\nimport { ProxiedModuleApi } from \"./ProxiedModuleApi\";\n\n/**\n * Wraps a module factory into a usable module. Acts as a simple container\n * for the constructs needed to operate a module.\n */\nexport class AppModule {\n    /**\n     * The module instance.\n     */\n    public readonly module: RuntimeModule;\n\n    /**\n     * The API instance used by the module.\n     */\n    public readonly api = new ProxiedModuleApi();\n\n    /**\n     * Converts a factory into an AppModule. The factory will be called\n     * immediately.\n     * @param factory The module factory.\n     */\n    public constructor(factory: ModuleFactory) {\n        this.module = factory(this.api);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { TextInputField } from \"@matrix-org/react-sdk-module-api/lib/components/TextInputField\";\nimport { Spinner as ModuleSpinner } from \"@matrix-org/react-sdk-module-api/lib/components/Spinner\";\nimport React, { type ChangeEvent } from \"react\";\n\nimport Field from \"../components/views/elements/Field\";\nimport Spinner from \"../components/views/elements/Spinner\";\n\n// Here we define all the render factories for the module API components. This file should be\n// imported by the ModuleRunner to load them into the call stack at runtime.\n//\n// If a new component is added to the module API, it should be added here too.\n//\n// Don't forget to add a test to ensure the renderFactory is overridden! See ModuleComponents-test.tsx\n\nTextInputField.renderFactory = (props) => (\n    <Field\n        type=\"text\"\n        value={props.value}\n        onChange={(e: ChangeEvent<HTMLInputElement>) => props.onChange(e.target.value)}\n        label={props.label}\n        autoComplete=\"off\"\n    />\n);\nModuleSpinner.renderFactory = () => <Spinner />;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { safeSet } from \"matrix-js-sdk/src/utils\";\nimport { type TranslationStringsObject } from \"@matrix-org/react-sdk-module-api/lib/types/translations\";\nimport { type AnyLifecycle } from \"@matrix-org/react-sdk-module-api/lib/lifecycles/types\";\nimport {\n    DefaultCryptoSetupExtensions,\n    type ProvideCryptoSetupExtensions,\n} from \"@matrix-org/react-sdk-module-api/lib/lifecycles/CryptoSetupExtensions\";\nimport {\n    DefaultExperimentalExtensions,\n    type ProvideExperimentalExtensions,\n} from \"@matrix-org/react-sdk-module-api/lib/lifecycles/ExperimentalExtensions\";\n\nimport { AppModule } from \"./AppModule\";\nimport { type ModuleFactory } from \"./ModuleFactory\";\n\nimport \"./ModuleComponents\";\n\n/**\n * Handles and manages extensions provided by modules.\n */\nclass ExtensionsManager {\n    // Private backing fields for extensions\n    private cryptoSetupExtension: ProvideCryptoSetupExtensions;\n    private experimentalExtension: ProvideExperimentalExtensions;\n\n    /** `true` if `cryptoSetupExtension` is the default implementation; `false` if it is implemented by a module. */\n    private hasDefaultCryptoSetupExtension = true;\n\n    /** `true` if `experimentalExtension` is the default implementation; `false` if it is implemented by a module. */\n    private hasDefaultExperimentalExtension = true;\n\n    /**\n     * Create a new instance.\n     */\n    public constructor() {\n        // Set up defaults\n        this.cryptoSetupExtension = new DefaultCryptoSetupExtensions();\n        this.experimentalExtension = new DefaultExperimentalExtensions();\n    }\n\n    /**\n     * Provides a crypto setup extension.\n     *\n     * @returns The registered extension. If no module provides this extension, a default implementation is returned.\n     */\n    public get cryptoSetup(): ProvideCryptoSetupExtensions {\n        return this.cryptoSetupExtension;\n    }\n\n    /**\n     * Provides an experimental extension.\n     *\n     * @remarks\n     * This method extension is provided to simplify experimentation and development, and is not intended for production code.\n     *\n     * @returns The registered extension. If no module provides this extension, a default implementation is returned.\n     */\n    public get experimental(): ProvideExperimentalExtensions {\n        return this.experimentalExtension;\n    }\n\n    /**\n     * Add any extensions provided by the module.\n     *\n     * @param module - The appModule to check for extensions.\n     *\n     * @throws if an extension is provided by more than one module.\n     */\n    public addExtensions(module: AppModule): void {\n        const runtimeModule = module.module;\n\n        /* Add the cryptoSetup extension if any */\n        if (runtimeModule.extensions?.cryptoSetup) {\n            if (this.hasDefaultCryptoSetupExtension) {\n                this.cryptoSetupExtension = runtimeModule.extensions?.cryptoSetup;\n                this.hasDefaultCryptoSetupExtension = false;\n            } else {\n                throw new Error(\n                    `adding cryptoSetup extension implementation from module ${runtimeModule.moduleName} but an implementation was already provided.`,\n                );\n            }\n        }\n\n        /* Add the experimental extension if any */\n        if (runtimeModule.extensions?.experimental) {\n            if (this.hasDefaultExperimentalExtension) {\n                this.experimentalExtension = runtimeModule.extensions?.experimental;\n                this.hasDefaultExperimentalExtension = false;\n            } else {\n                throw new Error(\n                    `adding experimental extension implementation from module ${runtimeModule.moduleName} but an implementation was already provided.`,\n                );\n            }\n        }\n    }\n}\n\n/**\n * Handles and coordinates the operation of modules.\n */\nexport class ModuleRunner {\n    public static readonly instance = new ModuleRunner();\n\n    private extensionsManager = new ExtensionsManager();\n\n    private modules: AppModule[] = [];\n\n    private constructor() {\n        // we only want one instance\n    }\n\n    /**\n     * Exposes all extensions which may be overridden/provided by modules.\n     *\n     * @returns An `ExtensionsManager` which exposes the extensions.\n     */\n    public get extensions(): ExtensionsManager {\n        return this.extensionsManager;\n    }\n\n    /**\n     * Resets the runner, clearing all known modules, and all extensions\n     *\n     * Intended for test usage only.\n     */\n    public reset(): void {\n        this.modules = [];\n        this.extensionsManager = new ExtensionsManager();\n    }\n\n    /**\n     * All custom translations from all registered modules.\n     */\n    public get allTranslations(): TranslationStringsObject {\n        const merged: TranslationStringsObject = {};\n\n        for (const module of this.modules) {\n            const i18n = module.api.translations;\n            if (!i18n) continue;\n\n            for (const [lang, strings] of Object.entries(i18n)) {\n                safeSet(merged, lang, merged[lang] || {});\n\n                for (const [str, val] of Object.entries(strings)) {\n                    safeSet(merged[lang], str, val);\n                }\n            }\n        }\n\n        return merged;\n    }\n\n    /**\n     * Registers a factory which creates a module for later loading. The factory\n     * will be called immediately.\n     * @param factory The module factory.\n     */\n    public registerModule(factory: ModuleFactory): void {\n        const appModule = new AppModule(factory);\n\n        this.modules.push(appModule);\n\n        // Check if the new module provides any extensions, and also ensure a given extension is only provided by a single runtime module.\n        this.extensionsManager.addExtensions(appModule);\n    }\n\n    /**\n     * Invokes a lifecycle event, notifying registered modules.\n     * @param lifecycleEvent The lifecycle event.\n     * @param args The arguments for the lifecycle event.\n     */\n    public invoke(lifecycleEvent: AnyLifecycle, ...args: any[]): void {\n        for (const module of this.modules) {\n            module.module.emit(lifecycleEvent, ...args);\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\ntype StringifyReplacer = (this: any, key: string, value: any) => any;\n\n// From https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Errors/Cyclic_object_value#circular_references\n// Injects `<$ cycle-trimmed $>` wherever it cuts a cyclical object relationship\nexport const getCircularReplacer = (): StringifyReplacer => {\n    const seen = new WeakSet();\n    return (key: string, value: any): any => {\n        if (typeof value === \"object\" && value !== null) {\n            if (seen.has(value)) {\n                return \"<$ cycle-trimmed $>\";\n            }\n            seen.add(value);\n        }\n        return value;\n    };\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2017 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// This module contains all the code needed to log the console, persist it to\n// disk and submit bug reports. Rationale is as follows:\n//  - Monkey-patching the console is preferable to having a log library because\n//    we can catch logs by other libraries more easily, without having to all\n//    depend on the same log framework / pass the logger around.\n//  - We use IndexedDB to persists logs because it has generous disk space\n//    limits compared to local storage. IndexedDB does not work in incognito\n//    mode, in which case this module will not be able to write logs to disk.\n//    However, the logs will still be stored in-memory, so can still be\n//    submitted in a bug report should the user wish to: we can also store more\n//    logs in-memory than in local storage, which does work in incognito mode.\n//    We also need to handle the case where there are 2+ tabs. Each JS runtime\n//    generates a random string which serves as the \"ID\" for that tab/session.\n//    These IDs are stored along with the log lines.\n//  - Bug reports are sent as a POST over HTTPS: it purposefully does not use\n//    Matrix as bug reports may be made when Matrix is not responsive (which may\n//    be the cause of the bug). We send the most recent N MB of UTF-8 log data,\n//    starting with the most recent, which we know because the \"ID\"s are\n//    actually timestamps. We then purge the remaining logs. We also do this\n//    purge on startup to prevent logs from accumulating.\n\n// the frequency with which we flush to indexeddb\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { secureRandomString } from \"matrix-js-sdk/src/randomstring\";\n\nimport { getCircularReplacer } from \"../utils/JSON\";\n\nconst FLUSH_RATE_MS = 30 * 1000;\n\n/** the length of log data we keep in indexeddb (and include in the reports), if there are more than 24 hours of logs */\nconst MAX_LOG_SIZE = 1024 * 1024 * 5; // 5 MB\n\n/** the length of log data we keep in indexeddb (and include in the reports), if there are less than 24 hours of logs */\nconst MAX_LOG_SIZE_24H = 1024 * 1024 * 100; // 100 MB\n\ntype LogFunction = (...args: (Error | DOMException | object | string)[]) => void;\nconst consoleFunctionsToLevels = {\n    log: \"I\",\n    info: \"I\",\n    warn: \"W\",\n    error: \"E\",\n    debug: \"D\",\n} as const;\ntype LogFunctionName = keyof typeof consoleFunctionsToLevels;\n\n// A class which monkey-patches the global console and stores log lines.\nexport class ConsoleLogger {\n    private logs = \"\";\n    private originalFunctions: { [key in LogFunctionName]?: LogFunction } = {};\n\n    public monkeyPatch(consoleObj: Console): void {\n        // Monkey-patch console logging\n        (Object.keys(consoleFunctionsToLevels) as LogFunctionName[]).forEach((fnName: LogFunctionName) => {\n            const level = consoleFunctionsToLevels[fnName];\n            const originalFn = consoleObj[fnName].bind(consoleObj);\n            this.originalFunctions[fnName] = originalFn;\n            consoleObj[fnName] = (...args) => {\n                this.log(level, ...args);\n                originalFn(...args);\n            };\n        });\n    }\n\n    public bypassRageshake(fnName: LogFunctionName, ...args: (Error | DOMException | object | string)[]): void {\n        this.originalFunctions[fnName]?.(...args);\n    }\n\n    public log(level: string, ...args: (Error | DOMException | object | string)[]): void {\n        // We don't know what locale the user may be running so use ISO strings\n        const ts = new Date().toISOString();\n\n        // Convert objects and errors to helpful things\n        args = args.map((arg) => {\n            if (arg instanceof DOMException) {\n                return arg.message + ` (${arg.name} | ${arg.code})`;\n            } else if (arg instanceof Error) {\n                return arg.message + (arg.stack ? `\\n${arg.stack}` : \"\");\n            } else if (typeof arg === \"object\") {\n                return JSON.stringify(arg, getCircularReplacer());\n            } else {\n                return arg;\n            }\n        });\n\n        // Some browsers support string formatting which we're not doing here\n        // so the lines are a little more ugly but easy to implement / quick to\n        // run.\n        // Example line:\n        // 2017-01-18T11:23:53.214Z W Failed to set badge count\n        // eslint-disable-next-line @typescript-eslint/no-base-to-string\n        let line = `${ts} ${level} ${args.join(\" \")}\\n`;\n        // Do some cleanup\n        line = line.replace(/token=[a-zA-Z0-9-]+/gm, \"token=xxxxx\");\n        // Using + really is the quickest way in JS\n        // http://jsperf.com/concat-vs-plus-vs-join\n        this.logs += line;\n    }\n\n    /**\n     * Retrieve log lines to flush to disk.\n     * @param {boolean} keepLogs True to not delete logs after flushing.\n     * @return {string} \\n delimited log lines to flush.\n     */\n    public flush(keepLogs?: boolean): string {\n        // The ConsoleLogger doesn't care how these end up on disk, it just\n        // flushes them to the caller.\n        if (keepLogs) {\n            return this.logs;\n        }\n        const logsToFlush = this.logs;\n        this.logs = \"\";\n        return logsToFlush;\n    }\n}\n\n// A class which stores log lines in an IndexedDB instance.\nexport class IndexedDBLogStore {\n    private id: string;\n    private index = 0;\n    private db: IDBDatabase | null = null;\n    private flushPromise: Promise<void> | null = null;\n    private flushAgainPromise: Promise<void> | null = null;\n\n    public constructor(\n        private indexedDB: IDBFactory,\n        private logger: ConsoleLogger,\n    ) {\n        this.id = \"instance-\" + secureRandomString(16);\n    }\n\n    /**\n     * @return {Promise} Resolves when the store is ready.\n     */\n    public connect(): Promise<void> {\n        const req = this.indexedDB.open(\"logs\");\n        return new Promise((resolve, reject) => {\n            req.onsuccess = () => {\n                this.db = req.result;\n                // Periodically flush logs to local storage / indexeddb\n                window.setInterval(this.flush.bind(this), FLUSH_RATE_MS);\n                resolve();\n            };\n\n            req.onerror = () => {\n                const err = \"Failed to open log database: \" + req.error?.name;\n                logger.error(err);\n                reject(new Error(err));\n            };\n\n            // First time: Setup the object store\n            req.onupgradeneeded = () => {\n                const db = req.result;\n                const logObjStore = db.createObjectStore(\"logs\", {\n                    keyPath: [\"id\", \"index\"],\n                });\n                // Keys in the database look like: [ \"instance-148938490\", 0 ]\n                // Later on we need to query everything based on an instance id.\n                // In order to do this, we need to set up indexes \"id\".\n                logObjStore.createIndex(\"id\", \"id\", { unique: false });\n\n                logObjStore.add(this.generateLogEntry(new Date() + \" ::: Log database was created.\"));\n\n                const lastModifiedStore = db.createObjectStore(\"logslastmod\", {\n                    keyPath: \"id\",\n                });\n                lastModifiedStore.add(this.generateLastModifiedTime());\n            };\n        });\n    }\n\n    /**\n     * Flush logs to disk.\n     *\n     * There are guards to protect against race conditions in order to ensure\n     * that all previous flushes have completed before the most recent flush.\n     * Consider without guards:\n     *  - A calls flush() periodically.\n     *  - B calls flush() and wants to send logs immediately afterwards.\n     *  - If B doesn't wait for A's flush to complete, B will be missing the\n     *    contents of A's flush.\n     * To protect against this, we set 'flushPromise' when a flush is ongoing.\n     * Subsequent calls to flush() during this period will chain another flush,\n     * then keep returning that same chained flush.\n     *\n     * This guarantees that we will always eventually do a flush when flush() is\n     * called.\n     *\n     * @return {Promise} Resolved when the logs have been flushed.\n     */\n    public flush(): Promise<void> {\n        // check if a flush() operation is ongoing\n        if (this.flushPromise) {\n            if (this.flushAgainPromise) {\n                // this is the 3rd+ time we've called flush() : return the same promise.\n                return this.flushAgainPromise;\n            }\n            // queue up a flush to occur immediately after the pending one completes.\n            this.flushAgainPromise = this.flushPromise\n                .then(() => {\n                    return this.flush();\n                })\n                .then(() => {\n                    this.flushAgainPromise = null;\n                });\n            return this.flushAgainPromise;\n        }\n        // there is no flush promise or there was but it has finished, so do\n        // a brand new one, destroying the chain which may have been built up.\n        this.flushPromise = new Promise<void>((resolve, reject) => {\n            if (!this.db) {\n                // not connected yet or user rejected access for us to r/w to the db.\n                reject(new Error(\"No connected database\"));\n                return;\n            }\n            const lines = this.logger.flush();\n            if (lines.length === 0) {\n                resolve();\n                return;\n            }\n            const txn = this.db.transaction([\"logs\", \"logslastmod\"], \"readwrite\");\n            const objStore = txn.objectStore(\"logs\");\n            txn.oncomplete = (event) => {\n                resolve();\n            };\n            txn.onerror = () => {\n                logger.error(\"Failed to flush logs : \", txn.error);\n                reject(new Error(\"Failed to write logs: \" + txn.error?.message));\n            };\n            objStore.add(this.generateLogEntry(lines));\n            const lastModStore = txn.objectStore(\"logslastmod\");\n            lastModStore.put(this.generateLastModifiedTime());\n        }).then(() => {\n            this.flushPromise = null;\n        });\n        return this.flushPromise;\n    }\n\n    /**\n     * Consume the most recent logs and return them. Older logs which are not\n     * returned are deleted at the same time, so this can be called at startup\n     * to do house-keeping to keep the logs from growing too large.\n     *\n     * @return {Promise<Object[]>} Resolves to an array of objects. The array is\n     * sorted in time (oldest first) based on when the log file was created (the\n     * log ID). The objects have said log ID in an \"id\" field and \"lines\" which\n     * is a big string with all the new-line delimited logs.\n     */\n    public async consume(): Promise<{ lines: string; id: string }[]> {\n        const allLogIds = await this.fetchLogIds();\n        let removeLogIds: string[] = [];\n        const logs: { lines: string; id: string }[] = [];\n        let size = 0;\n        for (let i = 0; i < allLogIds.length; i++) {\n            const instanceId = allLogIds[i];\n            const { lines, truncated } = await this.fetchLogs(instanceId, size);\n\n            // always add the returned logs: fetchLogs will truncate once it hits the size limit,\n            // so we'll go over the max but only by one fragment's worth.\n            logs.push({ lines, id: instanceId });\n            size += lines.length;\n\n            // If fetchLogs truncated we'll now be at or over the size limit,\n            // in which case we should stop and remove the rest of the log files.\n            if (truncated) {\n                logger.log(\n                    `rageshake: reached size limit while processing instance ${i + 1}/${\n                        allLogIds.length\n                    } (${instanceId}), with ${size} bytes of logs: will drop further instances`,\n                );\n                // the remaining log IDs should be removed. If we go out of\n                // bounds this is just []\n                removeLogIds = allLogIds.slice(i + 1);\n                break;\n            }\n        }\n        if (removeLogIds.length > 0) {\n            logger.log(`rageshake: removing logs: ${removeLogIds}`);\n            // Don't await this because it's non-fatal if we can't clean up\n            // logs.\n            Promise.all(removeLogIds.map((id) => this.deleteLogs(id))).then(\n                () => {\n                    logger.log(`Removed ${removeLogIds.length} old logs.`);\n                },\n                (err) => {\n                    logger.error(err);\n                },\n            );\n        }\n        return logs;\n    }\n\n    /**\n     * Fetch all the application instance names from the database.\n     */\n    private fetchLogIds(): Promise<string[]> {\n        const db = this.db;\n        if (!db) return Promise.reject(\"DB unavailable\");\n\n        // To gather all the log IDs, query for all records in logslastmod.\n        const o = db.transaction(\"logslastmod\", \"readonly\").objectStore(\"logslastmod\");\n        return selectQuery(o, undefined, (cursor) => {\n            return {\n                id: cursor.value.id,\n                ts: cursor.value.ts,\n            };\n        }).then((res) => {\n            // Sort IDs by timestamp (newest first)\n            return res\n                .sort((a, b) => {\n                    return b.ts - a.ts;\n                })\n                .map((a) => a.id);\n        });\n    }\n\n    /**\n     * Fetch logs for a given application instance from the database, stopping once we hit the size limit.\n     *\n     * @param id - Application instance to fetch logs for.\n     * @param sizeSoFar - Amount of logs we have already retrieved from other instances.\n     *\n     * @returns An object with the properties:\n     *  * `lines`: the concatenated logs for this ID\n     *  * `truncated`: whether the output was truncated due to hitting the size limit.\n     */\n    private fetchLogs(\n        id: string,\n        sizeSoFar: number,\n    ): Promise<{\n        lines: string;\n        truncated: boolean;\n    }> {\n        const db = this.db;\n        if (!db) return Promise.reject(\"DB unavailable\");\n\n        const objectStore = db.transaction(\"logs\", \"readonly\").objectStore(\"logs\");\n\n        /** Determine whether we should stop collecting logs after this batch.\n         *\n         * @param sizeSoFar - The total amount of logs collected so far.\n         * @param logBatchTimestamp - The timestamp of the most recent batch of logs collected.\n         *\n         * @returns `true` if we should stop after this batch.\n         */\n        function shouldTruncateAfterLogBatch(sizeSoFar: number, logBatchTimestamp: number): boolean {\n            // First check if we have exceeded the absolute limit\n            if (sizeSoFar >= MAX_LOG_SIZE_24H) {\n                return true;\n            }\n\n            // Otherwise, check if the most recent batch is more than 24H old, and we have exceeded the limit for logs over 24H\n            if (Date.now() - logBatchTimestamp >= 24 * 3600 * 1000 && sizeSoFar >= MAX_LOG_SIZE) {\n                return true;\n            }\n\n            // Otherwise, we're good.\n            return false;\n        }\n\n        return new Promise((resolve, reject) => {\n            const query = objectStore.index(\"id\").openCursor(IDBKeyRange.only(id), \"prev\");\n            let lines = \"\";\n            query.onerror = () => {\n                reject(new Error(\"Query failed: \" + query.error?.message));\n            };\n            query.onsuccess = () => {\n                const cursor = query.result;\n                if (!cursor) {\n                    // end of results\n                    resolve({ lines, truncated: false });\n                    return;\n                }\n                const newLines = cursor.value.lines;\n                // The query returns log chunks in reverse time order, so prepend this new chunk to the buffer.\n                lines = newLines + lines;\n                sizeSoFar += newLines.length;\n\n                // If we have now exceeded the size limit, stop.\n                if (shouldTruncateAfterLogBatch(sizeSoFar, cursor.value.ts ?? 0)) {\n                    resolve({ lines, truncated: true });\n                } else {\n                    cursor.continue();\n                }\n            };\n        });\n    }\n\n    /**\n     * Delete logs for a given application instance.\n     *\n     * @param id - Application instance to delete logs for.\n     */\n    private deleteLogs(id: string): Promise<void> {\n        const db = this.db;\n        if (!db) return Promise.reject(\"DB unavailable\");\n\n        return new Promise<void>((resolve, reject) => {\n            const txn = db.transaction([\"logs\", \"logslastmod\"], \"readwrite\");\n            const o = txn.objectStore(\"logs\");\n            // only load the key path, not the data which may be huge\n            const query = o.index(\"id\").openKeyCursor(IDBKeyRange.only(id));\n            query.onsuccess = () => {\n                const cursor = query.result;\n                if (!cursor) {\n                    return;\n                }\n                o.delete(cursor.primaryKey);\n                cursor.continue();\n            };\n            txn.oncomplete = () => {\n                resolve();\n            };\n            txn.onerror = () => {\n                reject(new Error(\"Failed to delete logs for \" + `'${id}' : ${query.error?.message}`));\n            };\n            // delete last modified entries\n            const lastModStore = txn.objectStore(\"logslastmod\");\n            lastModStore.delete(id);\n        });\n    }\n\n    /** Generate the object to be stored in the `logs` store */\n    private generateLogEntry(lines: string): { id: string; lines: string; index: number; ts: number } {\n        return {\n            id: this.id,\n            lines: lines,\n            index: this.index++,\n            /** The timestamp at which the line was *flushed* (not necessarily when it was written). */\n            ts: Date.now(),\n        };\n    }\n\n    private generateLastModifiedTime(): { id: string; ts: number } {\n        return {\n            id: this.id,\n            ts: Date.now(),\n        };\n    }\n}\n\n/**\n * Helper method to collect results from a Cursor and promiseify it.\n * @param {ObjectStore|Index} store The store to perform openCursor on.\n * @param {IDBKeyRange=} keyRange Optional key range to apply on the cursor.\n * @param {Function} resultMapper A function which is repeatedly called with a\n * Cursor.\n * Return the data you want to keep.\n * @return {Promise<T[]>} Resolves to an array of whatever you returned from\n * resultMapper.\n */\nfunction selectQuery<T>(\n    store: IDBIndex | IDBObjectStore,\n    keyRange: IDBKeyRange | undefined,\n    resultMapper: (cursor: IDBCursorWithValue) => T,\n): Promise<T[]> {\n    const query = store.openCursor(keyRange);\n    return new Promise((resolve, reject) => {\n        const results: T[] = [];\n        query.onerror = () => {\n            reject(new Error(\"Query failed: \" + query.error?.message));\n        };\n        // collect results\n        query.onsuccess = () => {\n            const cursor = query.result;\n            if (!cursor) {\n                resolve(results);\n                return; // end of results\n            }\n            results.push(resultMapper(cursor));\n            cursor.continue();\n        };\n    });\n}\n\n/**\n * Configure rage shaking support for sending bug reports.\n * Modifies globals.\n * @param {boolean} setUpPersistence When true (default), the persistence will\n * be set up immediately for the logs.\n * @return {Promise} Resolves when set up.\n */\nexport function init(setUpPersistence = true): Promise<void> {\n    if (global.mx_rage_initPromise) {\n        return global.mx_rage_initPromise;\n    }\n    global.mx_rage_logger = new ConsoleLogger();\n    global.mx_rage_logger.monkeyPatch(window.console);\n\n    // log unhandled rejections in the rageshake\n    window.addEventListener(\"unhandledrejection\", (event) => {\n        global.mx_rage_logger.log(\"error\", `Unhandled promise rejection: ${event.reason}`);\n    });\n\n    if (setUpPersistence) {\n        return tryInitStorage();\n    }\n\n    global.mx_rage_initPromise = Promise.resolve();\n    return global.mx_rage_initPromise;\n}\n\n/**\n * Try to start up the rageshake storage for logs. If not possible (client unsupported)\n * then this no-ops.\n * @return {Promise} Resolves when complete.\n */\nexport function tryInitStorage(): Promise<void> {\n    if (global.mx_rage_initStoragePromise) {\n        return global.mx_rage_initStoragePromise;\n    }\n\n    logger.log(\"Configuring rageshake persistence...\");\n\n    // just *accessing* indexedDB throws an exception in firefox with\n    // indexeddb disabled.\n    let indexedDB;\n    try {\n        indexedDB = window.indexedDB;\n    } catch {}\n\n    if (indexedDB) {\n        global.mx_rage_store = new IndexedDBLogStore(indexedDB, global.mx_rage_logger);\n        global.mx_rage_initStoragePromise = global.mx_rage_store.connect();\n\n        // Fire off a task in the background which will clean up old logs in the store\n        global.mx_rage_initStoragePromise.then(() => {\n            global.mx_rage_store.consume().catch((e) => {\n                logger.error(\"Error cleaning up rageshake store\", e);\n            });\n        });\n\n        return global.mx_rage_initStoragePromise;\n    }\n    global.mx_rage_initStoragePromise = Promise.resolve();\n    return global.mx_rage_initStoragePromise;\n}\n\nexport function flush(): void {\n    if (!global.mx_rage_store) {\n        return;\n    }\n    global.mx_rage_store.flush();\n}\n\n/**\n * Clean up old logs.\n *\n * @deprecated There is no need to call this explicitly: it will be done as a side-effect of {@link tryInitStorage},\n * or {@link init} with `setUpPersistence: true`.\n *\n * @return {Promise} Resolves if cleaned logs.\n */\nexport async function cleanup(): Promise<void> {\n    if (!global.mx_rage_store) {\n        return;\n    }\n    await global.mx_rage_store.consume();\n}\n\n/**\n * Get a recent snapshot of the logs, ready for attaching to a bug report\n *\n * @return {Array<{lines: string, id, string}>}  list of log data\n */\nexport async function getLogsForReport(): Promise<{ lines: string; id: string }[]> {\n    if (!global.mx_rage_logger) {\n        throw new Error(\"No console logger, did you forget to call init()?\");\n    }\n    // If in incognito mode, store is null, but we still want bug report\n    // sending to work going off the in-memory console logs.\n    if (global.mx_rage_store) {\n        // flush most recent logs\n        await global.mx_rage_store.flush();\n        return global.mx_rage_store.consume();\n    } else {\n        return [\n            {\n                lines: global.mx_rage_logger.flush(true),\n                id: \"-\",\n            },\n        ];\n    }\n}\n","/*\nCopyright 2024, 2025 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\nCopyright 2017 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { Method, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { type CryptoApi } from \"matrix-js-sdk/src/crypto-api\";\n\nimport type * as Pako from \"pako\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport PlatformPeg from \"../PlatformPeg\";\nimport { _t } from \"../languageHandler\";\nimport * as rageshake from \"./rageshake\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport SdkConfig from \"../SdkConfig\";\nimport { getServerVersionFromFederationApi } from \"../components/views/dialogs/devtools/ServerInfo\";\nimport type * as Tar from \"tar-js\";\nimport { BugReportEndpointURLLocal } from \"../IConfigOptions\";\n\ninterface IOpts {\n    labels?: string[];\n    userText?: string;\n    sendLogs?: boolean;\n    progressCallback?: (s: string) => void;\n    customApp?: string;\n    customFields?: Record<string, string>;\n}\n\nexport class RageshakeError extends Error {\n    /**\n     * This error is thrown when the rageshake server cannot process the request.\n     * @param errorcode Machine-readable error code. See https://github.com/matrix-org/rageshake/blob/main/docs/api.md\n     * @param error A human-readable error.\n     * @param statusCode The HTTP status code.\n     * @param policyURL Optional policy URL that can be presented to the user.\n     */\n    public constructor(\n        public readonly errorcode: string,\n        public readonly error: string,\n        public readonly statusCode: number,\n        public readonly policyURL?: string,\n    ) {\n        super(`The rageshake server responded with an error ${errorcode} (${statusCode}): ${error}`);\n    }\n}\n\n/**\n * Exported only for testing.\n * @internal public for test\n */\nexport async function collectBugReport(opts: IOpts = {}, gzipLogs = true): Promise<FormData> {\n    const progressCallback = opts.progressCallback;\n\n    progressCallback?.(_t(\"bug_reporting|collecting_information\"));\n\n    logger.log(\"Sending bug report.\");\n\n    const body = new FormData();\n\n    await collectBaseInformation(body, opts);\n\n    const client = MatrixClientPeg.get();\n\n    if (client) {\n        await collectClientInfo(client, body);\n    }\n\n    collectLabels(client, opts, body);\n\n    collectSettings(body);\n\n    await collectStorageStatInfo(body);\n\n    collectMissingFeatures(body);\n\n    if (opts.sendLogs) {\n        await collectLogs(body, gzipLogs, progressCallback);\n    }\n\n    return body;\n}\n\nasync function getAppVersion(): Promise<string | undefined> {\n    try {\n        return await PlatformPeg.get()?.getAppVersion();\n    } catch {\n        // this happens if no version is set i.e. in dev\n    }\n}\n\nfunction matchesMediaQuery(query: string): string {\n    try {\n        return String(window.matchMedia(query).matches);\n    } catch {\n        // if not supported in browser\n    }\n    return \"UNKNOWN\";\n}\n\n/**\n * Collects base information about the user and the app to add to the report.\n */\nasync function collectBaseInformation(body: FormData, opts: IOpts): Promise<void> {\n    const version = await getAppVersion();\n\n    const userAgent = window.navigator?.userAgent ?? \"UNKNOWN\";\n\n    const installedPWA = matchesMediaQuery(\"(display-mode: standalone)\");\n    const touchInput = matchesMediaQuery(\"(pointer: coarse)\");\n\n    body.append(\"text\", opts.userText || \"User did not supply any additional text.\");\n    body.append(\"app\", opts.customApp || \"element-web\");\n    body.append(\"version\", version ?? \"UNKNOWN\");\n    body.append(\"user_agent\", userAgent);\n    body.append(\"installed_pwa\", installedPWA);\n    body.append(\"touch_input\", touchInput);\n\n    if (opts.customFields) {\n        for (const key in opts.customFields) {\n            body.append(key, opts.customFields[key]);\n        }\n    }\n}\n\n/**\n * Collects client and crypto related info.\n */\nasync function collectClientInfo(client: MatrixClient, body: FormData): Promise<void> {\n    body.append(\"user_id\", client.credentials.userId!);\n    body.append(\"device_id\", client.deviceId!);\n\n    const cryptoApi = client.getCrypto();\n\n    if (cryptoApi) {\n        await collectCryptoInfo(cryptoApi, body);\n        await collectRecoveryInfo(client, cryptoApi, body);\n    }\n\n    await collectSynapseSpecific(client, body);\n}\n\n/**\n * Collects information about the home server.\n */\nasync function collectSynapseSpecific(client: MatrixClient, body: FormData): Promise<void> {\n    try {\n        // XXX: This is synapse-specific but better than nothing until MSC support for a server version endpoint\n        const data = await client.http.request<Record<string, any>>(\n            Method.Get,\n            \"/server_version\",\n            undefined,\n            undefined,\n            {\n                prefix: \"/_synapse/admin/v1\",\n            },\n        );\n        Object.keys(data).forEach((key) => {\n            body.append(`matrix_hs_${key}`, data[key]);\n        });\n    } catch {\n        try {\n            // XXX: This relies on the federation listener being delegated via well-known\n            // or at the same place as the client server endpoint\n            const data = await getServerVersionFromFederationApi(client);\n            body.append(\"matrix_hs_name\", data.server.name);\n            body.append(\"matrix_hs_version\", data.server.version);\n        } catch {\n            try {\n                // If that fails we'll hit any endpoint and look at the server response header\n                const res = await fetch(client.http.getUrl(\"/login\"), {\n                    method: \"GET\",\n                    mode: \"cors\",\n                });\n                if (res.headers.has(\"server\")) {\n                    body.append(\"matrix_hs_server\", res.headers.get(\"server\")!);\n                }\n            } catch {\n                // Could not determine server version\n            }\n        }\n    }\n}\n\n/**\n * Collects crypto related information.\n */\nasync function collectCryptoInfo(cryptoApi: CryptoApi, body: FormData): Promise<void> {\n    body.append(\"crypto_version\", cryptoApi.getVersion());\n\n    const ownDeviceKeys = await cryptoApi.getOwnDeviceKeys();\n    const keys = [`curve25519:${ownDeviceKeys.curve25519}`, `ed25519:${ownDeviceKeys.ed25519}`];\n\n    body.append(\"device_keys\", keys.join(\", \"));\n\n    // add cross-signing status information\n    const crossSigningStatus = await cryptoApi.getCrossSigningStatus();\n\n    body.append(\"cross_signing_ready\", String(await cryptoApi.isCrossSigningReady()));\n    body.append(\"cross_signing_key\", (await cryptoApi.getCrossSigningKeyId()) ?? \"n/a\");\n    body.append(\"cross_signing_privkey_in_secret_storage\", String(crossSigningStatus.privateKeysInSecretStorage));\n\n    body.append(\"cross_signing_master_privkey_cached\", String(crossSigningStatus.privateKeysCachedLocally.masterKey));\n    body.append(\n        \"cross_signing_self_signing_privkey_cached\",\n        String(crossSigningStatus.privateKeysCachedLocally.selfSigningKey),\n    );\n    body.append(\n        \"cross_signing_user_signing_privkey_cached\",\n        String(crossSigningStatus.privateKeysCachedLocally.userSigningKey),\n    );\n}\n\n/**\n * Collects information about secret storage and backup.\n */\nasync function collectRecoveryInfo(client: MatrixClient, cryptoApi: CryptoApi, body: FormData): Promise<void> {\n    const secretStorage = client.secretStorage;\n    body.append(\"secret_storage_ready\", String(await cryptoApi.isSecretStorageReady()));\n    body.append(\"secret_storage_key_in_account\", String(await secretStorage.hasKey()));\n\n    body.append(\"session_backup_key_in_secret_storage\", String(!!(await client.isKeyBackupKeyStored())));\n    const sessionBackupKeyFromCache = await cryptoApi.getSessionBackupPrivateKey();\n    body.append(\"session_backup_key_cached\", String(!!sessionBackupKeyFromCache));\n    body.append(\"session_backup_key_well_formed\", String(sessionBackupKeyFromCache instanceof Uint8Array));\n}\n\n/**\n * Collects labels to add to the report.\n */\nexport function collectLabels(client: MatrixClient | null, opts: IOpts, body: FormData): void {\n    if (opts.labels) {\n        for (const label of opts.labels) {\n            body.append(\"label\", label);\n        }\n    }\n}\n\n/**\n * Collects some settings (lab flags and more) to add to the report.\n */\nexport function collectSettings(body: FormData): void {\n    // add labs options\n    const enabledLabs = SettingsStore.getFeatureSettingNames().filter((f) => SettingsStore.getValue(f));\n    if (enabledLabs.length) {\n        body.append(\"enabled_labs\", enabledLabs.join(\", \"));\n    }\n    // if low bandwidth mode is enabled, say so over rageshake, it causes many issues\n    if (SettingsStore.getValue(\"lowBandwidth\")) {\n        body.append(\"lowBandwidth\", \"enabled\");\n    }\n\n    body.append(\"mx_local_settings\", SettingsStore.exportForRageshake());\n}\n\n/**\n * Collects storage statistics to add to the report.\n */\nasync function collectStorageStatInfo(body: FormData): Promise<void> {\n    // add storage persistence/quota information\n    if (navigator.storage && navigator.storage.persisted) {\n        try {\n            body.append(\"storageManager_persisted\", String(await navigator.storage.persisted()));\n        } catch {}\n    } else if (document.hasStorageAccess) {\n        // Safari\n        try {\n            body.append(\"storageManager_persisted\", String(await document.hasStorageAccess()));\n        } catch {}\n    }\n    if (navigator.storage && navigator.storage.estimate) {\n        try {\n            const estimate = await navigator.storage.estimate();\n            body.append(\"storageManager_quota\", String(estimate.quota));\n            body.append(\"storageManager_usage\", String(estimate.usage));\n            if (estimate.usageDetails) {\n                Object.keys(estimate.usageDetails).forEach((k) => {\n                    body.append(`storageManager_usage_${k}`, String(estimate.usageDetails![k]));\n                });\n            }\n        } catch {}\n    }\n}\n\nfunction collectMissingFeatures(body: FormData): void {\n    if (window.Modernizr) {\n        const missingFeatures = (Object.keys(window.Modernizr) as [keyof ModernizrStatic]).filter(\n            (key: keyof ModernizrStatic) => window.Modernizr[key] === false,\n        );\n        if (missingFeatures.length > 0) {\n            body.append(\"modernizr_missing_features\", missingFeatures.join(\", \"));\n        }\n    }\n}\n\n/**\n * Collects logs to add to the report if enabled.\n */\nasync function collectLogs(\n    body: FormData,\n    gzipLogs: boolean,\n    progressCallback: ((s: string) => void) | undefined,\n): Promise<void> {\n    let pako: typeof Pako | undefined;\n    if (gzipLogs) {\n        pako = await import(\"pako\");\n    }\n\n    progressCallback?.(_t(\"bug_reporting|collecting_logs\"));\n    const logs = await rageshake.getLogsForReport();\n    for (const entry of logs) {\n        // encode as UTF-8\n        let buf = new TextEncoder().encode(entry.lines);\n\n        // compress\n        if (gzipLogs) {\n            buf = pako!.gzip(buf);\n        }\n\n        body.append(\"compressed-log\", new Blob([buf]), entry.id);\n    }\n}\n/**\n * Send a bug report.\n *\n * @param {string} bugReportEndpoint HTTP url to send the report to\n *\n * @param {object} opts optional dictionary of options\n *\n * @param {string} opts.userText Any additional user input.\n *\n * @param {boolean} opts.sendLogs True to send logs\n *\n * @param {function(string)} opts.progressCallback Callback to call with progress updates\n *\n * @return {Promise<string>} URL returned by the rageshake server\n *\n * @throws A RageshakeError when the rageshake server responds with an error. This will be `RS_UNKNOWN` if the\n *         the server does not respond with an expected body format.\n */\nexport default async function sendBugReport(bugReportEndpoint?: string, opts: IOpts = {}): Promise<string> {\n    if (!bugReportEndpoint || bugReportEndpoint === BugReportEndpointURLLocal) {\n        throw new Error(\"No bug report endpoint has been set.\");\n    }\n\n    const progressCallback = opts.progressCallback || ((): void => {});\n    const body = await collectBugReport(opts);\n\n    progressCallback(_t(\"bug_reporting|uploading_logs\"));\n    return submitReport(bugReportEndpoint, body, progressCallback);\n}\n\n/**\n * Loads a bug report into a tarball.\n *\n * @param opts optional dictionary of options\n * @return Resolves with a Tarball object.\n */\nexport async function loadBugReport(opts: IOpts = {}): Promise<Tar> {\n    const Tar = (await import(\"tar-js\")).default;\n    const progressCallback = opts.progressCallback || ((): void => {});\n    const body = await collectBugReport(opts, false);\n\n    progressCallback(_t(\"bug_reporting|downloading_logs\"));\n    let metadata = \"\";\n    const tape = new Tar();\n    let i = 0;\n    for (const [key, value] of body.entries()) {\n        if (key === \"compressed-log\") {\n            await new Promise<void>((resolve) => {\n                const reader = new FileReader();\n                reader.addEventListener(\"loadend\", (ev) => {\n                    tape.append(`log-${i++}.log`, new TextDecoder().decode(reader.result as ArrayBuffer));\n                    resolve();\n                });\n                reader.readAsArrayBuffer(value as Blob);\n            });\n        } else {\n            metadata += `${key} = ${value as string}\\n`;\n        }\n    }\n    tape.append(\"issue.txt\", metadata);\n    return tape;\n}\n\n/**\n * Downloads the files from a bug report. This is the same as sendBugReport,\n * but instead causes the browser to download the files locally.\n *\n * @param opts optional dictionary of options\n * @return Resolved when the bug report is downloaded (or started).\n */\nexport async function downloadBugReport(opts: IOpts = {}): Promise<void> {\n    const tape = await loadBugReport(opts);\n    // We have to create a new anchor to download if we want a filename. Otherwise we could\n    // just use window.open.\n    const dl = document.createElement(\"a\");\n    dl.href = `data:application/octet-stream;base64,${btoa(uint8ToString(tape.out))}`;\n    dl.download = \"rageshake.tar\";\n    document.body.appendChild(dl);\n    dl.click();\n    document.body.removeChild(dl);\n}\n\n// Source: https://github.com/beatgammit/tar-js/blob/master/examples/main.js\nfunction uint8ToString(buf: Uint8Array): string {\n    let out = \"\";\n    for (let i = 0; i < buf.length; i += 1) {\n        out += String.fromCharCode(buf[i]);\n    }\n    return out;\n}\n\nexport async function submitFeedback(\n    label: string | undefined,\n    comment: string,\n    canContact = false,\n    extraData: Record<string, any> = {},\n): Promise<void> {\n    const bugReportEndpointUrl = SdkConfig.get().bug_report_endpoint_url;\n    if (!bugReportEndpointUrl || bugReportEndpointUrl === BugReportEndpointURLLocal) {\n        throw new Error(\"Bug report URL is not set or local\");\n    }\n    let version: string | undefined;\n    try {\n        version = await PlatformPeg.get()?.getAppVersion();\n    } catch {} // PlatformPeg already logs this.\n\n    const body = new FormData();\n    if (label) body.append(\"label\", label);\n    body.append(\"text\", comment);\n    body.append(\"can_contact\", canContact ? \"yes\" : \"no\");\n\n    body.append(\"app\", \"element-web\");\n    body.append(\"version\", version || \"UNKNOWN\");\n    body.append(\"platform\", PlatformPeg.get()?.getHumanReadableName() ?? \"n/a\");\n    body.append(\"user_id\", MatrixClientPeg.get()?.getUserId() ?? \"n/a\");\n\n    for (const k in extraData) {\n        body.append(k, JSON.stringify(extraData[k]));\n    }\n\n    await submitReport(bugReportEndpointUrl, body, () => {});\n}\n\n/**\n * Submit a rageshake report to the rageshake server.\n *\n * @param endpoint The endpoint to call.\n * @param body The report body.\n * @param progressCallback A callback that will be called when the upload process has begun.\n * @returns The URL to the public report.\n * @throws A RageshakeError when the rageshake server responds with an error. This will be `RS_UNKNOWN` if the\n *         the server does not respond with an expected body format.\n */\nasync function submitReport(\n    endpoint: string,\n    body: FormData,\n    progressCallback: (str: string) => void,\n): Promise<string> {\n    const req = fetch(endpoint, {\n        method: \"POST\",\n        body,\n        signal: AbortSignal.timeout?.(5 * 60 * 1000),\n    });\n    progressCallback(_t(\"bug_reporting|waiting_for_server\"));\n    const response = await req;\n    if (response.headers.get(\"Content-Type\") !== \"application/json\") {\n        throw new RageshakeError(\"UNKNOWN\", \"Rageshake server responded with unexpected type\", response.status);\n    }\n    const data = await response.json();\n    if (response.status < 200 || response.status >= 400) {\n        if (\"errcode\" in data) {\n            throw new RageshakeError(data.errcode, data.error, response.status, data.policy_url);\n        }\n        throw new RageshakeError(\"UNKNOWN\", \"Rageshake server responded with unexpected type\", response.status);\n    }\n    return data.report_url;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport * as Sentry from \"@sentry/browser\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport SdkConfig from \"./SdkConfig\";\nimport { MatrixClientPeg } from \"./MatrixClientPeg\";\nimport SettingsStore from \"./settings/SettingsStore\";\nimport { type IConfigOptions } from \"./IConfigOptions\";\n\n/* eslint-disable camelcase */\n\ntype StorageContext = {\n    storageManager_persisted?: string;\n    storageManager_quota?: string;\n    storageManager_usage?: string;\n    storageManager_usageDetails?: string;\n};\n\ntype UserContext = {\n    username: string;\n    enabled_labs: string;\n    low_bandwidth: string;\n};\n\ntype CryptoContext = {\n    crypto_version?: string;\n    device_keys?: string;\n    cross_signing_ready?: string;\n    cross_signing_supported_by_hs?: string;\n    cross_signing_key?: string;\n    cross_signing_privkey_in_secret_storage?: string;\n    cross_signing_master_privkey_cached?: string;\n    cross_signing_user_signing_privkey_cached?: string;\n    secret_storage_ready?: string;\n    secret_storage_key_in_account?: string;\n    session_backup_key_in_secret_storage?: string;\n    session_backup_key_cached?: string;\n    session_backup_key_well_formed?: string;\n};\n\ntype DeviceContext = {\n    device_id?: string;\n    mx_local_settings: string | null;\n    modernizr_missing_features?: string;\n};\n\ntype Contexts = {\n    user: UserContext;\n    crypto: CryptoContext;\n    device: DeviceContext;\n    storage: StorageContext;\n};\n\n/* eslint-enable camelcase */\n\nasync function getStorageContext(): Promise<StorageContext> {\n    const result: StorageContext = {};\n\n    // add storage persistence/quota information\n    if (navigator.storage && navigator.storage.persisted) {\n        try {\n            result[\"storageManager_persisted\"] = String(await navigator.storage.persisted());\n        } catch {}\n    } else if (document.hasStorageAccess) {\n        // Safari\n        try {\n            result[\"storageManager_persisted\"] = String(await document.hasStorageAccess());\n        } catch {}\n    }\n    if (navigator.storage && navigator.storage.estimate) {\n        try {\n            const estimate = await navigator.storage.estimate();\n            result[\"storageManager_quota\"] = String(estimate.quota);\n            result[\"storageManager_usage\"] = String(estimate.usage);\n            if (estimate.usageDetails) {\n                const usageDetails: string[] = [];\n                Object.keys(estimate.usageDetails).forEach((k) => {\n                    usageDetails.push(`${k}: ${String(estimate.usageDetails![k])}`);\n                });\n                result[`storageManager_usage`] = usageDetails.join(\", \");\n            }\n        } catch {}\n    }\n\n    return result;\n}\n\nfunction getUserContext(client: MatrixClient): UserContext {\n    return {\n        username: client.credentials.userId!,\n        enabled_labs: getEnabledLabs(),\n        low_bandwidth: SettingsStore.getValue(\"lowBandwidth\") ? \"enabled\" : \"disabled\",\n    };\n}\n\nfunction getEnabledLabs(): string {\n    const enabledLabs = SettingsStore.getFeatureSettingNames().filter((f) => SettingsStore.getValue(f));\n    if (enabledLabs.length) {\n        return enabledLabs.join(\", \");\n    }\n    return \"\";\n}\n\nasync function getCryptoContext(client: MatrixClient): Promise<CryptoContext> {\n    const cryptoApi = client.getCrypto();\n    if (!cryptoApi) {\n        return {};\n    }\n\n    const ownDeviceKeys = await cryptoApi.getOwnDeviceKeys();\n\n    const keys = [`curve25519:${ownDeviceKeys.curve25519}`, `ed25519:${ownDeviceKeys.ed25519}`];\n\n    const crossSigningStatus = await cryptoApi.getCrossSigningStatus();\n    const secretStorage = client.secretStorage;\n    const sessionBackupKeyFromCache = await cryptoApi.getSessionBackupPrivateKey();\n\n    return {\n        crypto_version: cryptoApi.getVersion(),\n        device_keys: keys.join(\", \"),\n        cross_signing_ready: String(await cryptoApi.isCrossSigningReady()),\n        cross_signing_key: (await cryptoApi.getCrossSigningKeyId()) ?? undefined,\n        cross_signing_privkey_in_secret_storage: String(crossSigningStatus.privateKeysInSecretStorage),\n        cross_signing_master_privkey_cached: String(crossSigningStatus.privateKeysCachedLocally.masterKey),\n        cross_signing_user_signing_privkey_cached: String(crossSigningStatus.privateKeysCachedLocally.userSigningKey),\n        secret_storage_ready: String(await cryptoApi.isSecretStorageReady()),\n        secret_storage_key_in_account: String(await secretStorage.hasKey()),\n        session_backup_key_in_secret_storage: String(!!(await client.isKeyBackupKeyStored())),\n        session_backup_key_cached: String(!!sessionBackupKeyFromCache),\n        session_backup_key_well_formed: String(sessionBackupKeyFromCache instanceof Uint8Array),\n    };\n}\n\nfunction getDeviceContext(client: MatrixClient): DeviceContext {\n    const result: DeviceContext = {\n        device_id: client?.deviceId ?? undefined,\n        mx_local_settings: SettingsStore.exportForRageshake(),\n    };\n\n    if (window.Modernizr) {\n        const missingFeatures = Object.keys(window.Modernizr).filter(\n            (key) => window.Modernizr[key as keyof ModernizrStatic] === false,\n        );\n        if (missingFeatures.length > 0) {\n            result[\"modernizr_missing_features\"] = missingFeatures.join(\", \");\n        }\n    }\n\n    return result;\n}\n\nasync function getContexts(): Promise<Contexts> {\n    const client = MatrixClientPeg.safeGet();\n    return {\n        user: getUserContext(client),\n        crypto: await getCryptoContext(client),\n        device: getDeviceContext(client),\n        storage: await getStorageContext(),\n    };\n}\n\nexport async function sendSentryReport(userText: string, issueUrl: string, error?: unknown): Promise<void> {\n    const sentryConfig = SdkConfig.getObject(\"sentry\");\n    if (!sentryConfig) return;\n\n    const captureContext = {\n        contexts: await getContexts(),\n        extra: {\n            user_text: userText,\n            issue_url: issueUrl,\n        },\n    };\n\n    // If there's no error and no issueUrl, the report will just produce non-grouped noise in Sentry, so don't\n    // upload it\n    if (error) {\n        Sentry.captureException(error, captureContext);\n    } else if (issueUrl) {\n        Sentry.captureMessage(`Issue: ${issueUrl}`, captureContext);\n    }\n}\n\nexport function setSentryUser(mxid: string): void {\n    if (!SdkConfig.get().sentry || !SettingsStore.getValue(\"automaticErrorReporting\")) return;\n    Sentry.setUser({ username: mxid });\n}\n\nexport async function initSentry(sentryConfig: IConfigOptions[\"sentry\"]): Promise<void> {\n    if (!sentryConfig) return;\n    // Only enable Integrations.GlobalHandlers, which hooks uncaught exceptions, if automaticErrorReporting is true\n    const integrations = [\n        Sentry.inboundFiltersIntegration(),\n        Sentry.functionToStringIntegration(),\n        Sentry.breadcrumbsIntegration(),\n        Sentry.httpContextIntegration(),\n        Sentry.dedupeIntegration(),\n    ];\n\n    if (SettingsStore.getValue(\"automaticErrorReporting\")) {\n        integrations.push(Sentry.globalHandlersIntegration({ onerror: false, onunhandledrejection: true }));\n        integrations.push(Sentry.browserApiErrorsIntegration());\n    }\n\n    Sentry.init({\n        dsn: sentryConfig.dsn,\n        release: process.env.VERSION,\n        environment: sentryConfig.environment,\n        defaultIntegrations: false,\n        integrations,\n        // Set to 1.0 which is reasonable if we're only submitting Rageshakes; will need to be set < 1.0\n        // if we collect more frequently.\n        tracesSampleRate: 1.0,\n    });\n}\n\nwindow.mxSendSentryReport = sendSentryReport;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\n * Represents the various setting levels supported by the SettingsStore.\n */\nexport enum SettingLevel {\n    // TODO: [TS] Follow naming convention\n    DEVICE = \"device\",\n    ROOM_DEVICE = \"room-device\",\n    ROOM_ACCOUNT = \"room-account\",\n    ACCOUNT = \"account\",\n    ROOM = \"room\",\n    PLATFORM = \"platform\",\n    CONFIG = \"config\",\n    DEFAULT = \"default\",\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingController from \"./SettingController\";\nimport { DEFAULT_THEME, enumerateThemes } from \"../../theme\";\nimport { type SettingLevel } from \"../SettingLevel\";\n\nexport default class ThemeController extends SettingController {\n    public getValueOverride(\n        level: SettingLevel,\n        roomId: string,\n        calculatedValue: any,\n        calculatedAtLevel: SettingLevel | null,\n    ): any {\n        if (!calculatedValue) return null; // Don't override null themes\n\n        const themes = enumerateThemes();\n        // Override in case some no longer supported theme is stored here\n        if (!themes[calculatedValue]) {\n            return DEFAULT_THEME;\n        }\n\n        return null; // no override\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingController from \"./SettingController\";\nimport dis from \"../../dispatcher/dispatcher\";\nimport { type UpdateFontSizeDeltaPayload } from \"../../dispatcher/payloads/UpdateFontSizeDeltaPayload\";\nimport { Action } from \"../../dispatcher/actions\";\nimport { SettingLevel } from \"../SettingLevel\";\n\nexport default class FontSizeController extends SettingController {\n    public constructor() {\n        super();\n    }\n\n    public onChange(level: SettingLevel, roomId: string, newValue: any): void {\n        // In a distant past, `baseFontSize` was set on the account and config\n        // level. This can be accessed only after the initial sync. If we end up\n        // discovering that a logged in user has this kind of setting, we want to\n        // trigger another migration of the base font size.\n        if (level === SettingLevel.ACCOUNT || level === SettingLevel.CONFIG) {\n            dis.fire(Action.MigrateBaseFontSize);\n        } else if (newValue !== \"\") {\n            // Dispatch font size change so that everything open responds to the change.\n            dis.dispatch<UpdateFontSizeDeltaPayload>({\n                action: Action.UpdateFontSizeDelta,\n                delta: newValue,\n            });\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingController from \"./SettingController\";\nimport SettingsStore from \"../SettingsStore\";\nimport dis from \"../../dispatcher/dispatcher\";\nimport { type UpdateSystemFontPayload } from \"../../dispatcher/payloads/UpdateSystemFontPayload\";\nimport { Action } from \"../../dispatcher/actions\";\n\nexport default class SystemFontController extends SettingController {\n    public constructor() {\n        super();\n    }\n\n    public onChange(): void {\n        // Dispatch font size change so that everything open responds to the change.\n        dis.dispatch<UpdateSystemFontPayload>({\n            action: Action.UpdateSystemFont,\n            useBundledEmojiFont: SettingsStore.getValue(\"useBundledEmojiFont\"),\n            useSystemFont: SettingsStore.getValue(\"useSystemFont\"),\n            font: SettingsStore.getValue(\"systemFont\"),\n        });\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingController from \"./SettingController\";\nimport { type SettingLevel } from \"../SettingLevel\";\nimport SettingsStore from \"../SettingsStore\";\nimport { type SettingKey } from \"../Settings.tsx\";\n\n/**\n * Enforces that a boolean setting cannot be enabled if the corresponding\n * UI feature is disabled. If the UI feature is enabled, the setting value\n * is unchanged.\n *\n * Settings using this controller are assumed to return `false` when disabled.\n */\nexport default class UIFeatureController extends SettingController {\n    public constructor(\n        private uiFeatureName: SettingKey,\n        private forcedValue = false,\n    ) {\n        super();\n    }\n\n    public getValueOverride(\n        level: SettingLevel,\n        roomId: string,\n        calculatedValue: any,\n        calculatedAtLevel: SettingLevel | null,\n    ): any {\n        if (this.settingDisabled) {\n            // per the docs: we force a disabled state when the feature isn't active\n            return this.forcedValue;\n        }\n        return null; // no override\n    }\n\n    public get settingDisabled(): boolean {\n        return !SettingsStore.getValue(this.uiFeatureName);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingController from \"./SettingController\";\nimport { type SettingLevel } from \"../SettingLevel\";\n\n/**\n * For animation-like settings, this controller checks whether the user has\n * indicated they prefer reduced motion via browser or OS level settings.\n * If they have, this forces the setting value to false.\n */\nexport default class ReducedMotionController extends SettingController {\n    public getValueOverride(\n        level: SettingLevel,\n        roomId: string,\n        calculatedValue: any,\n        calculatedAtLevel: SettingLevel | null,\n    ): any {\n        if (this.prefersReducedMotion()) {\n            return false;\n        }\n        return null; // no override\n    }\n\n    public get settingDisabled(): boolean {\n        return this.prefersReducedMotion();\n    }\n\n    private prefersReducedMotion(): boolean {\n        return window.matchMedia(\"(prefers-reduced-motion: reduce)\").matches;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingController from \"./SettingController\";\nimport { type SettingLevel } from \"../SettingLevel\";\nimport SettingsStore from \"../SettingsStore\";\nimport { type BooleanSettingKey } from \"../Settings.tsx\";\n\n/**\n * Enforces that a boolean setting cannot be enabled if the incompatible setting\n * is also enabled, to prevent cascading undefined behaviour between conflicting\n * labs flags.\n */\nexport default class IncompatibleController extends SettingController {\n    public constructor(\n        private settingName: BooleanSettingKey,\n        private forcedValue: any = false,\n        private incompatibleValue: any | ((v: any) => boolean) = true,\n    ) {\n        super();\n    }\n\n    public getValueOverride(\n        level: SettingLevel,\n        roomId: string,\n        calculatedValue: any,\n        calculatedAtLevel: SettingLevel | null,\n    ): any {\n        if (this.incompatibleSetting) {\n            return this.forcedValue;\n        }\n        return null; // no override\n    }\n\n    public get settingDisabled(): boolean {\n        return this.incompatibleSetting;\n    }\n\n    public get incompatibleSetting(): boolean {\n        if (typeof this.incompatibleValue === \"function\") {\n            return this.incompatibleValue(SettingsStore.getValue(this.settingName));\n        }\n        return SettingsStore.getValue(this.settingName) === this.incompatibleValue;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 Ed Geraghty <ed@geraghty.family>\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingController from \"./SettingController\";\nimport PlatformPeg from \"../../PlatformPeg\";\nimport SettingsStore from \"../SettingsStore\";\nimport { _t } from \"../../languageHandler\";\nimport { SlidingSyncManager } from \"../../SlidingSyncManager\";\n\nexport default class SlidingSyncController extends SettingController {\n    public async onChange(): Promise<void> {\n        PlatformPeg.get()?.reload();\n    }\n\n    public get settingDisabled(): boolean | string {\n        // Cannot be disabled once enabled, user has been warned and must log out and back in.\n        if (SettingsStore.getValue(\"feature_simplified_sliding_sync\")) {\n            return _t(\"labs|sliding_sync_disabled_notice\");\n        }\n        if (!SlidingSyncManager.serverSupportsSlidingSync) {\n            return _t(\"labs|sliding_sync_server_no_support\");\n        }\n\n        return false;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type SettingLevel } from \"../SettingLevel\";\nimport MatrixClientBackedController from \"./MatrixClientBackedController\";\nimport { type WatchManager } from \"../WatchManager\";\nimport SettingsStore from \"../SettingsStore\";\nimport { type SettingKey } from \"../Settings.tsx\";\nimport { _t } from \"../../languageHandler.tsx\";\n\n/**\n * Disables a given setting if the server unstable feature it requires is not supported\n * When a setting gets disabled or enabled from this controller it notifies the given WatchManager\n */\nexport default class ServerSupportUnstableFeatureController extends MatrixClientBackedController {\n    // Starts off as `undefined` so when we first compare the `newDisabledValue`, it sees\n    // it as a change and updates the watchers.\n    private enabled: boolean | undefined;\n\n    /**\n     * Construct a new ServerSupportUnstableFeatureController.\n     *\n     * @param unstableFeatureGroups - If any one of the feature groups is satisfied,\n     * then the setting is considered enabled. A feature group is satisfied if all of\n     * the features in the group are supported (all features in a group are required).\n     */\n    public constructor(\n        private readonly settingName: SettingKey,\n        private readonly watchers: WatchManager,\n        private readonly unstableFeatureGroups: string[][],\n        private readonly stableVersion?: string,\n        private readonly disabledMessage?: TranslationKey,\n        private readonly forcedValue: any = false,\n    ) {\n        super();\n    }\n\n    public get disabled(): boolean {\n        return !this.enabled;\n    }\n\n    public set disabled(newDisabledValue: boolean) {\n        if (!newDisabledValue === this.enabled) return;\n        this.enabled = !newDisabledValue;\n        const level = SettingsStore.firstSupportedLevel(this.settingName);\n        if (!level) return;\n        const settingValue = SettingsStore.getValue(this.settingName, null);\n        this.watchers.notifyUpdate(this.settingName, null, level, settingValue);\n    }\n\n    protected async initMatrixClient(): Promise<void> {\n        // Check for stable version support first\n        if (this.stableVersion && (await this.client!.isVersionSupported(this.stableVersion))) {\n            this.disabled = false;\n            return;\n        }\n\n        // Otherwise, only one of the unstable feature groups needs to be satisfied in\n        // order for this setting overall to be enabled\n        let isEnabled = false;\n        for (const featureGroup of this.unstableFeatureGroups) {\n            const featureSupportList = await Promise.all(\n                featureGroup.map(async (feature) => {\n                    const isFeatureSupported = await this.client!.doesServerSupportUnstableFeature(feature);\n                    return isFeatureSupported;\n                }),\n            );\n\n            // Every feature in a feature group is required in order\n            // for this setting overall to be enabled.\n            const isFeatureGroupSatisfied = featureSupportList.every((isFeatureSupported) => isFeatureSupported);\n            if (isFeatureGroupSatisfied) {\n                isEnabled = true;\n                break;\n            }\n        }\n\n        this.disabled = !isEnabled;\n    }\n\n    public getValueOverride(\n        level: SettingLevel,\n        roomId: string | null,\n        calculatedValue: any,\n        calculatedAtLevel: SettingLevel | null,\n    ): any {\n        if (this.settingDisabled) {\n            return this.forcedValue;\n        }\n        return null; // no override\n    }\n\n    public get settingDisabled(): boolean | string {\n        if (this.disabled) {\n            return this.disabledMessage ? _t(this.disabledMessage) : true;\n        }\n        return false;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingController from \"./SettingController\";\nimport { type SettingLevel } from \"../SettingLevel\";\nimport PosthogTrackers, { type InteractionName } from \"../../PosthogTrackers\";\n\n/**\n * Controller that sends events to analytics when a setting is changed.\n * Since it will only trigger events when the setting is changed,\n * (and the value isn't reported: only the fact that it's been toggled)\n * it won't be useful for tracking what percentage of a userbase has a given setting\n * enabled, but many of our settings can be set per device and Posthog only supports\n * per-user properties, so this isn't straightforward. This is only for seeing how\n * often people interact with the settings.\n */\nexport default class AnalyticsController extends SettingController {\n    /**\n     *\n     * @param interactionName The name of the event to send to analytics\n     */\n    public constructor(private interactionName: InteractionName) {\n        super();\n    }\n\n    public onChange(_level: SettingLevel, _roomId: string | null, _newValue: any): void {\n        PosthogTrackers.trackInteraction(this.interactionName);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { ClientEvent, type IClientWellKnown, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { type SettingLevel } from \"../SettingLevel\";\nimport SettingsStore from \"../SettingsStore.ts\";\nimport MatrixClientBackedController from \"./MatrixClientBackedController.ts\";\n\n/**\n * Settings controller for the fallback ICE server setting.\n * This setting may be forcibly disabled by well-known value [\"io.element.voip\"][\"disable_fallback_ice\"].\n * This controller will update the MatrixClient's knowledge when the setting is changed.\n */\nexport default class FallbackIceServerController extends MatrixClientBackedController {\n    private disabled = false;\n\n    public constructor() {\n        super();\n    }\n\n    private checkWellKnown = (wellKnown: IClientWellKnown): void => {\n        this.disabled = !!wellKnown[\"io.element.voip\"]?.[\"disable_fallback_ice\"];\n    };\n\n    protected async initMatrixClient(newClient: MatrixClient, oldClient?: MatrixClient): Promise<void> {\n        oldClient?.off(ClientEvent.ClientWellKnown, this.checkWellKnown);\n        newClient.on(ClientEvent.ClientWellKnown, this.checkWellKnown);\n        const wellKnown = newClient.getClientWellKnown();\n        if (wellKnown) this.checkWellKnown(wellKnown);\n    }\n\n    public getValueOverride(): any {\n        if (this.disabled) {\n            return false;\n        }\n\n        return null; // no override\n    }\n\n    public get settingDisabled(): boolean | string {\n        return this.disabled;\n    }\n\n    public onChange(_level: SettingLevel, _roomId: string | null, _newValue: any): void {\n        this.client?.setFallbackICEServerAllowed(!!SettingsStore.getValue(\"fallbackICEServerAllowed\"));\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type IContent } from \"matrix-js-sdk/src/matrix\";\nimport { type AccountDataEvents } from \"matrix-js-sdk/src/types\";\n\nimport {\n    MEDIA_PREVIEW_ACCOUNT_DATA_TYPE,\n    type MediaPreviewConfig,\n    MediaPreviewValue,\n} from \"../../@types/media_preview.ts\";\nimport { type SettingLevel } from \"../SettingLevel.ts\";\nimport MatrixClientBackedController from \"./MatrixClientBackedController.ts\";\n\ndeclare module \"matrix-js-sdk/src/types\" {\n    interface RoomAccountDataEvents {\n        [MEDIA_PREVIEW_ACCOUNT_DATA_TYPE]: MediaPreviewConfig;\n    }\n}\n\n/**\n * Handles media preview settings provided by MSC4278.\n * This uses both account-level and room-level account data.\n */\nexport default class MediaPreviewConfigController extends MatrixClientBackedController {\n    public static readonly default: AccountDataEvents[typeof MEDIA_PREVIEW_ACCOUNT_DATA_TYPE] = {\n        media_previews: MediaPreviewValue.On,\n        invite_avatars: MediaPreviewValue.On,\n    };\n\n    private static getValidSettingData(content: IContent): Partial<MediaPreviewConfig> {\n        const mediaPreviews: MediaPreviewConfig[\"media_previews\"] = content.media_previews;\n        const inviteAvatars: MediaPreviewConfig[\"invite_avatars\"] = content.invite_avatars;\n        const validMediaPreviews = Object.values(MediaPreviewValue);\n        const validInviteAvatars = [MediaPreviewValue.Off, MediaPreviewValue.On];\n        return {\n            invite_avatars: validInviteAvatars.includes(inviteAvatars) ? inviteAvatars : undefined,\n            media_previews: validMediaPreviews.includes(mediaPreviews) ? mediaPreviews : undefined,\n        };\n    }\n\n    public constructor() {\n        super();\n    }\n\n    private getValue = (roomId?: string): MediaPreviewConfig => {\n        const source = roomId ? this.client?.getRoom(roomId) : this.client;\n        const accountData =\n            source?.getAccountData(MEDIA_PREVIEW_ACCOUNT_DATA_TYPE)?.getContent<MediaPreviewConfig>() ?? {};\n\n        const calculatedConfig = MediaPreviewConfigController.getValidSettingData(accountData);\n\n        // Save an account data fetch if we have all the values.\n        if (calculatedConfig.invite_avatars && calculatedConfig.media_previews) {\n            return calculatedConfig as MediaPreviewConfig;\n        }\n\n        // We're missing some keys.\n        if (roomId) {\n            const globalConfig = this.getValue();\n            return {\n                invite_avatars:\n                    calculatedConfig.invite_avatars ??\n                    globalConfig.invite_avatars ??\n                    MediaPreviewConfigController.default.invite_avatars,\n                media_previews:\n                    calculatedConfig.media_previews ??\n                    globalConfig.media_previews ??\n                    MediaPreviewConfigController.default.media_previews,\n            };\n        }\n        return {\n            invite_avatars: calculatedConfig.invite_avatars ?? MediaPreviewConfigController.default.invite_avatars,\n            media_previews: calculatedConfig.media_previews ?? MediaPreviewConfigController.default.media_previews,\n        };\n    };\n\n    public getValueOverride(_level: SettingLevel, roomId: string | null): MediaPreviewConfig {\n        return this.getValue(roomId ?? undefined);\n    }\n\n    public get settingDisabled(): false {\n        // No homeserver support is required for this MSC.\n        return false;\n    }\n\n    public async beforeChange(\n        _level: SettingLevel,\n        roomId: string | null,\n        newValue: MediaPreviewConfig,\n    ): Promise<boolean> {\n        if (!this.client) {\n            return false;\n        }\n        if (roomId) {\n            await this.client.setRoomAccountData(roomId, MEDIA_PREVIEW_ACCOUNT_DATA_TYPE, newValue);\n            return true;\n        }\n        await this.client.setAccountData(MEDIA_PREVIEW_ACCOUNT_DATA_TYPE, newValue);\n        return true;\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport const INVITE_RULES_ACCOUNT_DATA_TYPE = \"org.matrix.msc4155.invite_permission_config\";\nexport const MSC4380_INVITE_RULES_ACCOUNT_DATA_TYPE = \"org.matrix.msc4380.invite_permission_config\";\n\nexport interface InviteConfigAccountData {\n    allowed_users?: string[];\n    blocked_users?: string[];\n    ignored_users?: string[];\n    allowed_servers?: string[];\n    blocked_servers?: string[];\n    ignored_servers?: string[];\n}\n\n/**\n * Computed values based on MSC4155. Currently Element Web only supports\n * blocking all invites.\n */\nexport interface ComputedInviteConfig extends Record<string, unknown> {\n    /**\n     * Are all invites blocked. This is only about blocking all invites,\n     * but this being false may still block invites through other rules.\n     */\n    allBlocked: boolean;\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient, type IContent } from \"matrix-js-sdk/src/matrix\";\n\nimport { type SettingLevel } from \"../SettingLevel.ts\";\nimport MatrixClientBackedController from \"./MatrixClientBackedController.ts\";\nimport {\n    type ComputedInviteConfig as ComputedInviteRules,\n    INVITE_RULES_ACCOUNT_DATA_TYPE,\n    type InviteConfigAccountData,\n} from \"../../@types/invite-rules.ts\";\nimport { _t } from \"../../languageHandler.tsx\";\n\n/**\n * Handles invite filtering rules provided by MSC4155.\n * This handler does not make use of the roomId parameter.\n */\nexport default class InviteRulesConfigController extends MatrixClientBackedController {\n    public static readonly default: ComputedInviteRules = {\n        allBlocked: false,\n    };\n\n    private static getValidSettingData(content: IContent): ComputedInviteRules {\n        const expectedConfig = content as InviteConfigAccountData;\n        return {\n            allBlocked: !!expectedConfig.blocked_users?.includes(\"*\"),\n        };\n    }\n\n    public initMatrixClient(newClient: MatrixClient): void {\n        newClient.doesServerSupportUnstableFeature(\"org.matrix.msc4155\").then((result) => {\n            this.featureSupported = result;\n        });\n    }\n\n    public featureSupported?: boolean;\n\n    public constructor() {\n        super();\n        this.featureSupported = false;\n    }\n\n    private getValue = (): ComputedInviteRules => {\n        const accountData =\n            this.client?.getAccountData(INVITE_RULES_ACCOUNT_DATA_TYPE)?.getContent<InviteConfigAccountData>() ?? {};\n        return InviteRulesConfigController.getValidSettingData(accountData);\n    };\n\n    public getValueOverride(_level: SettingLevel): ComputedInviteRules {\n        return this.getValue();\n    }\n\n    public get settingDisabled(): true | string {\n        return this.featureSupported ? true : _t(\"settings|not_supported\");\n    }\n\n    public async beforeChange(\n        _level: SettingLevel,\n        _roomId: string | null,\n        newValue: ComputedInviteRules,\n    ): Promise<boolean> {\n        if (!this.client) {\n            return false;\n        }\n        const existingContent = this.client\n            .getAccountData(INVITE_RULES_ACCOUNT_DATA_TYPE)\n            ?.getContent<InviteConfigAccountData>();\n        const newContent: InviteConfigAccountData = {\n            ...existingContent,\n            blocked_users: [...(existingContent?.blocked_users ?? [])],\n        };\n        if (newValue.allBlocked && !newContent.blocked_users!.includes(\"*\")) {\n            newContent.blocked_users!.push(\"*\");\n        } else if (!newValue.allBlocked && newContent.blocked_users?.includes(\"*\")) {\n            newContent.blocked_users = newContent.blocked_users.filter((u) => u !== \"*\");\n        } else {\n            // No changes required.\n            return false;\n        }\n        await this.client.setAccountData(INVITE_RULES_ACCOUNT_DATA_TYPE, newContent);\n        return true;\n    }\n}\n","/*\nCopyright 2024, 2025 New Vector Ltd.\nCopyright 2018-2024 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode } from \"react\";\nimport { STABLE_MSC4133_EXTENDED_PROFILES, UNSTABLE_MSC4133_EXTENDED_PROFILES } from \"matrix-js-sdk/src/matrix\";\n// Import these directly from shared-components to avoid circular deps\nimport { _t, _td } from \"@element-hq/web-shared-components\";\n\nimport { type MediaPreviewConfig } from \"../@types/media_preview.ts\";\nimport DeviceIsolationModeController from \"./controllers/DeviceIsolationModeController.ts\";\nimport {\n    NotificationBodyEnabledController,\n    NotificationsEnabledController,\n} from \"./controllers/NotificationControllers\";\nimport ThemeController from \"./controllers/ThemeController\";\nimport ReloadOnChangeController from \"./controllers/ReloadOnChangeController\";\nimport FontSizeController from \"./controllers/FontSizeController\";\nimport SystemFontController from \"./controllers/SystemFontController\";\nimport { SettingLevel } from \"./SettingLevel\";\nimport type SettingController from \"./controllers/SettingController\";\nimport { IS_MAC } from \"../Keyboard\";\nimport UIFeatureController from \"./controllers/UIFeatureController\";\nimport { UIFeature } from \"./UIFeature\";\nimport { Layout } from \"./enums/Layout\";\nimport ReducedMotionController from \"./controllers/ReducedMotionController\";\nimport IncompatibleController from \"./controllers/IncompatibleController\";\nimport { ImageSize } from \"./enums/ImageSize\";\nimport { MetaSpace } from \"../stores/spaces\";\nimport SdkConfig from \"../SdkConfig\";\nimport SlidingSyncController from \"./controllers/SlidingSyncController\";\nimport { FontWatcher } from \"./watchers/FontWatcher\";\nimport ServerSupportUnstableFeatureController from \"./controllers/ServerSupportUnstableFeatureController\";\nimport { WatchManager } from \"./WatchManager\";\nimport { type CustomTheme } from \"../theme\";\nimport AnalyticsController from \"./controllers/AnalyticsController\";\nimport FallbackIceServerController from \"./controllers/FallbackIceServerController\";\nimport { type IRightPanelForRoomStored } from \"../stores/right-panel/RightPanelStoreIPanelState.ts\";\nimport { type ILayoutSettings } from \"../stores/widgets/WidgetLayoutStore.ts\";\nimport { type ReleaseAnnouncementData } from \"../stores/ReleaseAnnouncementStore.ts\";\nimport { type Json, type JsonValue } from \"../@types/json.ts\";\nimport { type RecentEmojiData } from \"../emojipicker/recent.ts\";\nimport { type Assignable } from \"../@types/common.ts\";\nimport { SortingAlgorithm } from \"../stores/room-list-v3/skip-list/sorters/index.ts\";\nimport MediaPreviewConfigController from \"./controllers/MediaPreviewConfigController.ts\";\nimport InviteRulesConfigController from \"./controllers/InviteRulesConfigController.ts\";\nimport { type ComputedInviteConfig } from \"../@types/invite-rules.ts\";\nimport BlockInvitesConfigController from \"./controllers/BlockInvitesConfigController.ts\";\n\nexport const defaultWatchManager = new WatchManager();\n\n// These are just a bunch of helper arrays to avoid copy/pasting a bunch of times\nconst LEVELS_ROOM_SETTINGS = [\n    SettingLevel.DEVICE,\n    SettingLevel.ROOM_DEVICE,\n    SettingLevel.ROOM_ACCOUNT,\n    SettingLevel.ACCOUNT,\n    SettingLevel.CONFIG,\n];\nconst LEVELS_ROOM_OR_ACCOUNT = [SettingLevel.ROOM_ACCOUNT, SettingLevel.ACCOUNT];\nconst LEVELS_ROOM_SETTINGS_WITH_ROOM = [\n    SettingLevel.DEVICE,\n    SettingLevel.ROOM_DEVICE,\n    SettingLevel.ROOM_ACCOUNT,\n    SettingLevel.ACCOUNT,\n    SettingLevel.CONFIG,\n    SettingLevel.ROOM,\n];\nconst LEVELS_ACCOUNT_SETTINGS = [SettingLevel.DEVICE, SettingLevel.ACCOUNT, SettingLevel.CONFIG];\nconst LEVELS_DEVICE_ONLY_SETTINGS = [SettingLevel.DEVICE];\nconst LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG = [SettingLevel.DEVICE, SettingLevel.CONFIG];\nconst LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED = [SettingLevel.CONFIG, SettingLevel.DEVICE];\nconst LEVELS_UI_FEATURE = [\n    SettingLevel.CONFIG,\n    // in future we might have a .well-known level or something\n];\n\nexport enum LabGroup {\n    Messaging,\n    Profile,\n    Spaces,\n    Widgets,\n    Rooms,\n    Threads,\n    VoiceAndVideo,\n    Moderation,\n    Analytics,\n    Themes,\n    Encryption,\n    Experimental,\n    Developer,\n    Ui,\n}\n\nexport enum Features {\n    NotificationSettings2 = \"feature_notification_settings2\",\n    ReleaseAnnouncement = \"feature_release_announcement\",\n}\n\nexport const labGroupNames: Record<LabGroup, TranslationKey> = {\n    [LabGroup.Messaging]: _td(\"labs|group_messaging\"),\n    [LabGroup.Profile]: _td(\"labs|group_profile\"),\n    [LabGroup.Spaces]: _td(\"labs|group_spaces\"),\n    [LabGroup.Widgets]: _td(\"labs|group_widgets\"),\n    [LabGroup.Rooms]: _td(\"labs|group_rooms\"),\n    [LabGroup.Threads]: _td(\"labs|group_threads\"),\n    [LabGroup.VoiceAndVideo]: _td(\"labs|group_voip\"),\n    [LabGroup.Moderation]: _td(\"labs|group_moderation\"),\n    [LabGroup.Analytics]: _td(\"common|analytics\"),\n    [LabGroup.Themes]: _td(\"labs|group_themes\"),\n    [LabGroup.Encryption]: _td(\"labs|group_encryption\"),\n    [LabGroup.Experimental]: _td(\"labs|group_experimental\"),\n    [LabGroup.Developer]: _td(\"labs|group_developer\"),\n    [LabGroup.Ui]: _td(\"labs|group_ui\"),\n};\n\nexport type SettingValueType = Json | JsonValue | Record<string, unknown> | Record<string, unknown>[];\n\nexport interface IBaseSetting<T extends SettingValueType = SettingValueType> {\n    isFeature?: false | undefined;\n\n    // Display names are strongly recommended for clarity.\n    // Display name can also be an object for different levels.\n    displayName?:\n        | TranslationKey\n        | Partial<{\n              [level in SettingLevel]: TranslationKey;\n          }>;\n\n    // Optional description which will be shown as microCopy under SettingsFlags\n    description?: TranslationKey | (() => ReactNode);\n\n    // The supported levels are required. Preferably, use the preset arrays\n    // at the top of this file to define this rather than a custom array.\n    supportedLevels: SettingLevel[];\n\n    // Required. Can be any data type. The value specified here should match\n    // the data being stored (ie: if a boolean is used, the setting should\n    // represent a boolean).\n    default: T;\n\n    // Optional settings controller. See SettingsController for more information.\n    controller?: SettingController;\n\n    // Optional flag to make supportedLevels be respected as the order to handle\n    // settings. The first element is treated as \"most preferred\". The \"default\"\n    // level is always appended to the end.\n    supportedLevelsAreOrdered?: boolean;\n\n    // Optional value to invert a boolean setting's value. The string given will\n    // be read as the setting's ID instead of the one provided as the key for the\n    // setting definition. By setting this, the returned value will automatically\n    // be inverted, except for when the default value is returned. Inversion will\n    // occur after the controller is asked for an override. This should be used by\n    // historical settings which we don't want existing user's values be wiped. Do\n    // not use this for new settings.\n    invertedSettingName?: string;\n\n    // XXX: Keep this around for re-use in future Betas\n    betaInfo?: {\n        title: TranslationKey;\n        caption: () => ReactNode;\n        faq?: (enabled: boolean) => ReactNode;\n        image?: string; // require(...)\n        feedbackSubheading?: TranslationKey;\n        feedbackLabel?: string;\n        extraSettings?: BooleanSettingKey[];\n        requiresRefresh?: boolean;\n    };\n\n    // Whether the setting should have a warning sign in the microcopy\n    shouldWarn?: boolean;\n\n    /**\n     * Whether the setting should be exported in a rageshake report.\n     */\n    shouldExportToRageshake?: boolean;\n\n    /**\n     * Options array for a setting controlled by a dropdown.\n     */\n    options?: {\n        value: T;\n        label: TranslationKey;\n    }[];\n}\n\nexport interface IFeature extends Omit<IBaseSetting<boolean>, \"isFeature\"> {\n    // Must be set to true for features.\n    isFeature: true;\n    labsGroup: LabGroup;\n}\n\n// Type using I-identifier for backwards compatibility from before it became a discriminated union\nexport type ISetting = IBaseSetting | IFeature;\n\nexport interface Settings {\n    [settingName: `UIFeature.${string}`]: IBaseSetting<boolean>;\n\n    // We can't use the following type because of `feature_sliding_sync_proxy_url` & `feature_hidebold` being in the namespace incorrectly\n    // [settingName: `feature_${string}`]: IFeature;\n    \"feature_video_rooms\": IFeature;\n    [Features.NotificationSettings2]: IFeature;\n    [Features.ReleaseAnnouncement]: IFeature;\n    \"feature_msc3531_hide_messages_pending_moderation\": IFeature;\n    \"feature_report_to_moderators\": IFeature;\n    \"feature_latex_maths\": IFeature;\n    \"feature_wysiwyg_composer\": IFeature;\n    \"feature_mjolnir\": IFeature;\n    \"feature_custom_themes\": IFeature;\n    \"feature_exclude_insecure_devices\": IFeature;\n    \"feature_share_history_on_invite\": IFeature;\n    \"feature_html_topic\": IFeature;\n    \"feature_bridge_state\": IFeature;\n    \"feature_jump_to_date\": IFeature;\n    \"feature_sliding_sync\": IBaseSetting<boolean>;\n    \"feature_simplified_sliding_sync\": IFeature;\n    \"feature_element_call_video_rooms\": IFeature;\n    \"feature_group_calls\": IFeature;\n    \"feature_disable_call_per_sender_encryption\": IFeature;\n    \"feature_location_share_live\": IFeature;\n    \"feature_dynamic_room_predecessors\": IFeature;\n    \"feature_render_reaction_images\": IFeature;\n    \"feature_new_room_list\": IFeature;\n    \"feature_ask_to_join\": IFeature;\n    \"feature_notifications\": IFeature;\n    \"feature_msc4362_encrypted_state_events\": IFeature;\n    // These are in the feature namespace but aren't actually features\n    \"feature_hidebold\": IBaseSetting<boolean>;\n\n    \"useOnlyCurrentProfiles\": IBaseSetting<boolean>;\n    \"mjolnirRooms\": IBaseSetting<string[]>;\n    \"mjolnirPersonalRoom\": IBaseSetting<string | null>;\n    \"RoomList.backgroundImage\": IBaseSetting<string | null>;\n    \"sendReadReceipts\": IBaseSetting<boolean>;\n    \"baseFontSize\": IBaseSetting<\"\" | number>;\n    \"baseFontSizeV2\": IBaseSetting<\"\" | number>;\n    \"fontSizeDelta\": IBaseSetting<number>;\n    \"useCustomFontSize\": IBaseSetting<boolean>;\n    \"MessageComposerInput.suggestEmoji\": IBaseSetting<boolean>;\n    \"MessageComposerInput.showStickersButton\": IBaseSetting<boolean>;\n    \"MessageComposerInput.showPollsButton\": IBaseSetting<boolean>;\n    \"MessageComposerInput.insertTrailingColon\": IBaseSetting<boolean>;\n    \"Notifications.alwaysShowBadgeCounts\": IBaseSetting<boolean>;\n    \"Notifications.showbold\": IBaseSetting<boolean>;\n    \"Notifications.tac_only_notifications\": IBaseSetting<boolean>;\n    \"useCompactLayout\": IBaseSetting<boolean>;\n    \"showRedactions\": IBaseSetting<boolean>;\n    \"showJoinLeaves\": IBaseSetting<boolean>;\n    \"showAvatarChanges\": IBaseSetting<boolean>;\n    \"showDisplaynameChanges\": IBaseSetting<boolean>;\n    \"showReadReceipts\": IBaseSetting<boolean>;\n    \"showTwelveHourTimestamps\": IBaseSetting<boolean>;\n    \"alwaysShowTimestamps\": IBaseSetting<boolean>;\n    \"userTimezone\": IBaseSetting<string>;\n    \"userTimezonePublish\": IBaseSetting<boolean>;\n    \"autoplayGifs\": IBaseSetting<boolean>;\n    \"autoplayVideo\": IBaseSetting<boolean>;\n    \"enableSyntaxHighlightLanguageDetection\": IBaseSetting<boolean>;\n    \"expandCodeByDefault\": IBaseSetting<boolean>;\n    \"showCodeLineNumbers\": IBaseSetting<boolean>;\n    \"scrollToBottomOnMessageSent\": IBaseSetting<boolean>;\n    \"Pill.shouldShowPillAvatar\": IBaseSetting<boolean>;\n    \"TextualBody.enableBigEmoji\": IBaseSetting<boolean>;\n    \"MessageComposerInput.isRichTextEnabled\": IBaseSetting<boolean>;\n    \"MessageComposer.showFormatting\": IBaseSetting<boolean>;\n    \"sendTypingNotifications\": IBaseSetting<boolean>;\n    \"showTypingNotifications\": IBaseSetting<boolean>;\n    \"ctrlFForSearch\": IBaseSetting<boolean>;\n    \"MessageComposerInput.ctrlEnterToSend\": IBaseSetting<boolean>;\n    \"MessageComposerInput.surroundWith\": IBaseSetting<boolean>;\n    \"MessageComposerInput.autoReplaceEmoji\": IBaseSetting<boolean>;\n    \"MessageComposerInput.useMarkdown\": IBaseSetting<boolean>;\n    \"VideoView.flipVideoHorizontally\": IBaseSetting<boolean>;\n    \"theme\": IBaseSetting<string>;\n    \"custom_themes\": IBaseSetting<CustomTheme[]>;\n    \"use_system_theme\": IBaseSetting<boolean>;\n    \"useBundledEmojiFont\": IBaseSetting<boolean>;\n    \"useSystemFont\": IBaseSetting<boolean>;\n    \"systemFont\": IBaseSetting<string>;\n    \"webRtcAllowPeerToPeer\": IBaseSetting<boolean>;\n    \"webrtc_audiooutput\": IBaseSetting<string>;\n    \"webrtc_audioinput\": IBaseSetting<string>;\n    \"webrtc_videoinput\": IBaseSetting<string>;\n    \"webrtc_audio_autoGainControl\": IBaseSetting<boolean>;\n    \"webrtc_audio_echoCancellation\": IBaseSetting<boolean>;\n    \"webrtc_audio_noiseSuppression\": IBaseSetting<boolean>;\n    \"language\": IBaseSetting<string>;\n    \"breadcrumb_rooms\": IBaseSetting<string[]>;\n    \"recent_emoji\": IBaseSetting<RecentEmojiData>;\n    \"showMediaEventIds\": IBaseSetting<{ [eventId: string]: boolean }>;\n    \"SpotlightSearch.recentSearches\": IBaseSetting<string[]>;\n    \"SpotlightSearch.showNsfwPublicRooms\": IBaseSetting<boolean>;\n    \"room_directory_servers\": IBaseSetting<string[]>;\n    \"integrationProvisioning\": IBaseSetting<boolean>;\n    \"allowedWidgets\": IBaseSetting<{ [eventId: string]: boolean }>;\n    \"analyticsOptIn\": IBaseSetting<boolean>;\n    \"pseudonymousAnalyticsOptIn\": IBaseSetting<boolean | null>;\n    \"deviceClientInformationOptIn\": IBaseSetting<boolean>;\n    \"Registration.mobileRegistrationHelper\": IBaseSetting<boolean>;\n    \"autocompleteDelay\": IBaseSetting<number>;\n    \"readMarkerInViewThresholdMs\": IBaseSetting<number>;\n    \"readMarkerOutOfViewThresholdMs\": IBaseSetting<number>;\n    \"blacklistUnverifiedDevices\": IBaseSetting<boolean>;\n    \"urlPreviewsEnabled\": IBaseSetting<boolean>;\n    \"urlPreviewsEnabled_e2ee\": IBaseSetting<boolean>;\n    \"notificationsEnabled\": IBaseSetting<boolean>;\n    \"deviceNotificationsEnabled\": IBaseSetting<boolean>;\n    \"notificationSound\": IBaseSetting<\n        | {\n              name: string;\n              type: string;\n              size: number;\n              url: string;\n          }\n        | false\n    >;\n    \"notificationBodyEnabled\": IBaseSetting<boolean>;\n    \"audioNotificationsEnabled\": IBaseSetting<boolean>;\n    \"enableWidgetScreenshots\": IBaseSetting<boolean>;\n    \"promptBeforeInviteUnknownUsers\": IBaseSetting<boolean>;\n    \"widgetOpenIDPermissions\": IBaseSetting<{\n        allow?: string[];\n        deny?: string[];\n    }>;\n    \"breadcrumbs\": IBaseSetting<boolean>;\n    \"showHiddenEventsInTimeline\": IBaseSetting<boolean>;\n    \"lowBandwidth\": IBaseSetting<boolean>;\n    \"fallbackICEServerAllowed\": IBaseSetting<boolean | null>;\n    \"RoomList.preferredSorting\": IBaseSetting<SortingAlgorithm>;\n    \"RoomList.showMessagePreview\": IBaseSetting<boolean>;\n    \"RightPanel.phasesGlobal\": IBaseSetting<IRightPanelForRoomStored | null>;\n    \"RightPanel.phases\": IBaseSetting<IRightPanelForRoomStored | null>;\n    \"enableEventIndexing\": IBaseSetting<boolean>;\n    \"crawlerSleepTime\": IBaseSetting<number>;\n    \"showCallButtonsInComposer\": IBaseSetting<boolean>;\n    \"ircDisplayNameWidth\": IBaseSetting<number>;\n    \"layout\": IBaseSetting<Layout>;\n    \"Images.size\": IBaseSetting<ImageSize>;\n    \"showChatEffects\": IBaseSetting<boolean>;\n    \"Performance.addSendMessageTimingMetadata\": IBaseSetting<boolean>;\n    \"Widgets.pinned\": IBaseSetting<{ [widgetId: string]: boolean }>;\n    \"Widgets.layout\": IBaseSetting<ILayoutSettings | null>;\n    \"Spaces.allRoomsInHome\": IBaseSetting<boolean>;\n    \"Spaces.enabledMetaSpaces\": IBaseSetting<Partial<Record<MetaSpace, boolean>>>;\n    \"Spaces.showPeopleInSpace\": IBaseSetting<boolean>;\n    \"developerMode\": IBaseSetting<boolean>;\n    \"automaticErrorReporting\": IBaseSetting<boolean>;\n    \"automaticDecryptionErrorReporting\": IBaseSetting<boolean>;\n    \"debug_scroll_panel\": IBaseSetting<boolean>;\n    \"debug_timeline_panel\": IBaseSetting<boolean>;\n    \"debug_registration\": IBaseSetting<boolean>;\n    \"debug_animation\": IBaseSetting<boolean>;\n    \"debug_legacy_call_handler\": IBaseSetting<boolean>;\n    \"audioInputMuted\": IBaseSetting<boolean>;\n    \"videoInputMuted\": IBaseSetting<boolean>;\n    \"activeCallRoomIds\": IBaseSetting<string[]>;\n    \"releaseAnnouncementData\": IBaseSetting<ReleaseAnnouncementData>;\n    \"Electron.autoLaunch\": IBaseSetting<\"enabled\" | \"minimised\" | \"disabled\">;\n    \"Electron.warnBeforeExit\": IBaseSetting<boolean>;\n    \"Electron.alwaysShowMenuBar\": IBaseSetting<boolean>;\n    \"Electron.showTrayIcon\": IBaseSetting<boolean>;\n    \"Electron.enableHardwareAcceleration\": IBaseSetting<boolean>;\n    \"Electron.enableContentProtection\": IBaseSetting<boolean>;\n    \"mediaPreviewConfig\": IBaseSetting<MediaPreviewConfig>;\n    \"inviteRules\": IBaseSetting<ComputedInviteConfig>;\n    \"blockInvites\": IBaseSetting<boolean>;\n    \"Developer.elementCallUrl\": IBaseSetting<string>;\n}\n\nexport type SettingKey = keyof Settings;\nexport type FeatureSettingKey = Assignable<Settings, IFeature>;\nexport type BooleanSettingKey = Assignable<Settings, IBaseSetting<boolean>> | FeatureSettingKey;\nexport type StringSettingKey = Assignable<Settings, IBaseSetting<string>>;\n\nexport const SETTINGS: Settings = {\n    \"feature_video_rooms\": {\n        isFeature: true,\n        labsGroup: LabGroup.VoiceAndVideo,\n        displayName: _td(\"labs|video_rooms\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        default: false,\n        // Reload to ensure that the left panel etc. get remounted\n        controller: new ReloadOnChangeController(),\n        betaInfo: {\n            title: _td(\"labs|video_rooms\"),\n            caption: () => (\n                <>\n                    <p>\n                        {_t(\"labs|video_rooms_a_new_way_to_chat\", {\n                            brand: SdkConfig.get().brand,\n                        })}\n                    </p>\n                    <p>\n                        {_t(\"labs|video_rooms_always_on_voip_channels\", {\n                            brand: SdkConfig.get().brand,\n                        })}\n                    </p>\n                </>\n            ),\n            faq: () => (\n                <>\n                    <h4>{_t(\"labs|video_rooms_faq1_question\")}</h4>\n                    <p>{_t(\"labs|video_rooms_faq1_answer\")}</p>\n                    <h4>{_t(\"labs|video_rooms_faq2_question\")}</h4>\n                    <p>{_t(\"labs|video_rooms_faq2_answer\")}</p>\n                </>\n            ),\n            feedbackLabel: \"video-room-feedback\",\n            feedbackSubheading: _td(\"labs|video_rooms_feedbackSubheading\"),\n            // eslint-disable-next-line @typescript-eslint/no-require-imports\n            image: require(\"../../res/img/betas/video_rooms.png\"),\n            requiresRefresh: true,\n        },\n    },\n    [Features.NotificationSettings2]: {\n        isFeature: true,\n        labsGroup: LabGroup.Experimental,\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        displayName: _td(\"labs|notification_settings\"),\n        default: false,\n        betaInfo: {\n            title: _td(\"labs|notification_settings_beta_title\"),\n            caption: () => (\n                <>\n                    <p>\n                        {_t(\"labs|notification_settings_beta_caption\", {\n                            brand: SdkConfig.get().brand,\n                        })}\n                    </p>\n                </>\n            ),\n        },\n    },\n    \"feature_msc3531_hide_messages_pending_moderation\": {\n        isFeature: true,\n        labsGroup: LabGroup.Moderation,\n        // Requires a reload since this setting is cached in EventUtils\n        controller: new ReloadOnChangeController(),\n        displayName: _td(\"labs|msc3531_hide_messages_pending_moderation\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        default: false,\n    },\n    \"mediaPreviewConfig\": {\n        controller: new MediaPreviewConfigController(),\n        supportedLevels: LEVELS_ROOM_SETTINGS,\n        default: MediaPreviewConfigController.default,\n    },\n    \"inviteRules\": {\n        controller: new InviteRulesConfigController(),\n        supportedLevels: [SettingLevel.ACCOUNT],\n        default: InviteRulesConfigController.default,\n        // Contains server names\n        shouldExportToRageshake: false,\n    },\n    \"blockInvites\": {\n        controller: new BlockInvitesConfigController(\"blockInvites\"),\n        supportedLevels: [SettingLevel.ACCOUNT],\n        default: false,\n    },\n    \"feature_report_to_moderators\": {\n        isFeature: true,\n        labsGroup: LabGroup.Moderation,\n        displayName: _td(\"labs|report_to_moderators\"),\n        description: _td(\"labs|report_to_moderators_description\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        default: false,\n    },\n    \"feature_latex_maths\": {\n        isFeature: true,\n        labsGroup: LabGroup.Messaging,\n        displayName: _td(\"labs|latex_maths\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        default: false,\n    },\n    \"feature_wysiwyg_composer\": {\n        isFeature: true,\n        labsGroup: LabGroup.Messaging,\n        displayName: _td(\"labs|wysiwyg_composer\"),\n        description: _td(\"labs|feature_wysiwyg_composer_description\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        default: false,\n    },\n    \"feature_mjolnir\": {\n        isFeature: true,\n        labsGroup: LabGroup.Moderation,\n        displayName: _td(\"labs|mjolnir\"),\n        description: _td(\"labs|currently_experimental\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        default: false,\n    },\n    \"feature_custom_themes\": {\n        isFeature: true,\n        labsGroup: LabGroup.Themes,\n        displayName: _td(\"labs|custom_themes\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        default: false,\n    },\n    \"feature_exclude_insecure_devices\": {\n        isFeature: true,\n        labsGroup: LabGroup.Encryption,\n        controller: new DeviceIsolationModeController(),\n        displayName: _td(\"labs|exclude_insecure_devices\"),\n        description: _td(\"labs|exclude_insecure_devices_description\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        default: false,\n    },\n    \"feature_share_history_on_invite\": {\n        isFeature: true,\n        labsGroup: LabGroup.Encryption,\n        displayName: _td(\"labs|share_history_on_invite\"),\n        description: () => (\n            <>\n                {_t(\"labs|share_history_on_invite_description\")}\n                <div className=\"mx_SettingsFlag_microcopy\">\n                    {_t(\n                        \"settings|warning\",\n                        {},\n                        {\n                            w: (sub) => <span className=\"mx_SettingsTab_microcopy_warning\">{sub}</span>,\n                            description: _t(\"labs|share_history_on_invite_warning\"),\n                        },\n                    )}\n                </div>\n            </>\n        ),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        default: false,\n    },\n    // Defaulted to true Feb 26, intention is to remove entirely, all being well,\n    // as this fixes bugs where display name / avatar are missing and also makes\n    // Element Web consistent with Element X.\n    \"useOnlyCurrentProfiles\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|disable_historical_profile\"),\n        default: true,\n    },\n    \"mjolnirRooms\": {\n        supportedLevels: [SettingLevel.ACCOUNT],\n        default: [],\n        // Contains room IDs\n        shouldExportToRageshake: false,\n    },\n    \"mjolnirPersonalRoom\": {\n        supportedLevels: [SettingLevel.ACCOUNT],\n        default: null,\n        // Contains room ID\n        shouldExportToRageshake: false,\n    },\n    \"feature_html_topic\": {\n        isFeature: true,\n        labsGroup: LabGroup.Rooms,\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        displayName: _td(\"labs|html_topic\"),\n        default: false,\n    },\n    \"feature_bridge_state\": {\n        isFeature: true,\n        labsGroup: LabGroup.Rooms,\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        displayName: _td(\"labs|bridge_state\"),\n        default: false,\n    },\n    \"feature_jump_to_date\": {\n        isFeature: true,\n        labsGroup: LabGroup.Messaging,\n        displayName: _td(\"labs|jump_to_date\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        default: false,\n        controller: new ServerSupportUnstableFeatureController(\n            \"feature_jump_to_date\",\n            defaultWatchManager,\n            [[\"org.matrix.msc3030\"], [\"org.matrix.msc3030.stable\"]],\n            \"v1.6\",\n            _td(\"labs|jump_to_date_msc_support\"),\n        ),\n    },\n    \"RoomList.backgroundImage\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: null,\n    },\n    \"sendReadReceipts\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|send_read_receipts\"),\n        default: true,\n        controller: new ServerSupportUnstableFeatureController(\n            \"sendReadReceipts\",\n            defaultWatchManager,\n            [[\"org.matrix.msc2285.stable\"]],\n            \"v1.4\",\n            _td(\"settings|send_read_receipts_unsupported\"),\n            true,\n        ),\n    },\n    // legacy sliding sync flag: no longer works, will error for anyone who's still using it\n    \"feature_sliding_sync\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        shouldWarn: true,\n        default: false,\n    },\n    \"feature_simplified_sliding_sync\": {\n        isFeature: true,\n        labsGroup: LabGroup.Developer,\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        displayName: _td(\"labs|sliding_sync\"),\n        description: _td(\"labs|sliding_sync_description\"),\n        shouldWarn: true,\n        default: false,\n        controller: new SlidingSyncController(),\n    },\n    \"feature_element_call_video_rooms\": {\n        isFeature: true,\n        labsGroup: LabGroup.VoiceAndVideo,\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        displayName: _td(\"labs|element_call_video_rooms\"),\n        controller: new ReloadOnChangeController(),\n        default: false,\n    },\n    \"feature_group_calls\": {\n        isFeature: true,\n        labsGroup: LabGroup.VoiceAndVideo,\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        displayName: _td(\"labs|group_calls\"),\n        controller: new ReloadOnChangeController(),\n        default: false,\n    },\n    \"feature_disable_call_per_sender_encryption\": {\n        isFeature: true,\n        labsGroup: LabGroup.VoiceAndVideo,\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        displayName: _td(\"labs|feature_disable_call_per_sender_encryption\"),\n        default: false,\n    },\n    \"feature_location_share_live\": {\n        isFeature: true,\n        labsGroup: LabGroup.Messaging,\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        displayName: _td(\"labs|location_share_live\"),\n        description: _td(\"labs|location_share_live_description\"),\n        shouldWarn: true,\n        default: false,\n    },\n    \"feature_dynamic_room_predecessors\": {\n        isFeature: true,\n        labsGroup: LabGroup.Rooms,\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        displayName: _td(\"labs|dynamic_room_predecessors\"),\n        description: _td(\"labs|dynamic_room_predecessors_description\"),\n        shouldWarn: true,\n        default: false,\n    },\n    /**\n     * @deprecated in favor of {@link fontSizeDelta}\n     */\n    \"baseFontSize\": {\n        displayName: _td(\"settings|appearance|font_size\"),\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: \"\",\n        controller: new FontSizeController(),\n    },\n    \"feature_render_reaction_images\": {\n        isFeature: true,\n        labsGroup: LabGroup.Messaging,\n        displayName: _td(\"labs|render_reaction_images\"),\n        description: _td(\"labs|render_reaction_images_description\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        default: false,\n    },\n    \"feature_new_room_list\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        labsGroup: LabGroup.Ui,\n        displayName: _td(\"labs|new_room_list\"),\n        description: _td(\"labs|under_active_development\"),\n        isFeature: true,\n        default: true,\n        controller: new ReloadOnChangeController(),\n    },\n    /**\n     * With the transition to Compound we are moving to a base font size\n     * of 16px. We're taking the opportunity to move away from the `baseFontSize`\n     * setting that had a 5px offset.\n     * @deprecated in favor {@link fontSizeDelta}\n     */\n    \"baseFontSizeV2\": {\n        displayName: _td(\"settings|appearance|font_size\"),\n        supportedLevels: [SettingLevel.DEVICE],\n        default: \"\",\n        controller: new FontSizeController(),\n    },\n    /**\n     * This delta is added to the browser default font size\n     * Moving from `baseFontSizeV2` to `fontSizeDelta` to replace the default 16px to --cpd-font-size-root (browser default font size) + fontSizeDelta\n     */\n    \"fontSizeDelta\": {\n        displayName: _td(\"settings|appearance|font_size\"),\n        supportedLevels: [SettingLevel.DEVICE],\n        default: FontWatcher.DEFAULT_DELTA,\n        controller: new FontSizeController(),\n    },\n    \"useCustomFontSize\": {\n        displayName: _td(\"settings|appearance|custom_font_size\"),\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: false,\n    },\n    \"MessageComposerInput.suggestEmoji\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|emoji_autocomplete\"),\n        default: true,\n        invertedSettingName: \"MessageComposerInput.dontSuggestEmoji\",\n    },\n    \"MessageComposerInput.showStickersButton\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|show_stickers_button\"),\n        default: true,\n        controller: new UIFeatureController(UIFeature.Widgets, false),\n    },\n    \"MessageComposerInput.showPollsButton\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|preferences|show_polls_button\"),\n        default: true,\n    },\n    \"MessageComposerInput.insertTrailingColon\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|insert_trailing_colon_mentions\"),\n        default: true,\n    },\n    // TODO: Wire up appropriately to UI (FTUE notifications)\n    \"Notifications.alwaysShowBadgeCounts\": {\n        supportedLevels: LEVELS_ROOM_OR_ACCOUNT,\n        default: false,\n    },\n    // Used to be a feature, name kept for backwards compat\n    \"feature_hidebold\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        displayName: _td(\"labs|hidebold\"),\n        default: false,\n    },\n    \"Notifications.showbold\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        displayName: _td(\"settings|showbold\"),\n        default: false,\n        invertedSettingName: \"feature_hidebold\",\n        controller: new AnalyticsController(\"WebSettingsNotificationsShowBoldToggle\"),\n    },\n    \"Notifications.tac_only_notifications\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        displayName: _td(\"settings|tac_only_notifications\"),\n        default: true,\n        controller: new AnalyticsController(\"WebSettingsNotificationsTACOnlyNotificationsToggle\"),\n    },\n    \"feature_ask_to_join\": {\n        isFeature: true,\n        labsGroup: LabGroup.Rooms,\n        default: false,\n        displayName: _td(\"labs|ask_to_join\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n    },\n    \"feature_notifications\": {\n        isFeature: true,\n        labsGroup: LabGroup.Messaging,\n        displayName: _td(\"labs|notifications\"),\n        description: _td(\"labs|unrealiable_e2e\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        default: false,\n    },\n    \"feature_msc4362_encrypted_state_events\": {\n        isFeature: true,\n        labsGroup: LabGroup.Encryption,\n        displayName: _td(\"labs|encrypted_state_events\"),\n        description: _td(\"labs|encrypted_state_events_description\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED,\n        supportedLevelsAreOrdered: true,\n        shouldWarn: true,\n        default: false,\n    },\n    \"useCompactLayout\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        displayName: _td(\"settings|preferences|compact_modern\"),\n        default: false,\n        controller: new IncompatibleController(\"layout\", false, (v: Layout) => v !== Layout.Group),\n    },\n    \"showRedactions\": {\n        supportedLevels: LEVELS_ROOM_SETTINGS_WITH_ROOM,\n        displayName: _td(\"settings|show_redaction_placeholder\"),\n        default: true,\n        invertedSettingName: \"hideRedactions\",\n    },\n    \"showJoinLeaves\": {\n        supportedLevels: LEVELS_ROOM_SETTINGS_WITH_ROOM,\n        displayName: _td(\"settings|show_join_leave\"),\n        default: true,\n        invertedSettingName: \"hideJoinLeaves\",\n    },\n    \"showAvatarChanges\": {\n        supportedLevels: LEVELS_ROOM_SETTINGS_WITH_ROOM,\n        displayName: _td(\"settings|show_avatar_changes\"),\n        default: true,\n        invertedSettingName: \"hideAvatarChanges\",\n    },\n    \"showDisplaynameChanges\": {\n        supportedLevels: LEVELS_ROOM_SETTINGS_WITH_ROOM,\n        displayName: _td(\"settings|show_displayname_changes\"),\n        default: true,\n        invertedSettingName: \"hideDisplaynameChanges\",\n    },\n    \"showReadReceipts\": {\n        supportedLevels: LEVELS_ROOM_SETTINGS,\n        displayName: _td(\"settings|show_read_receipts\"),\n        default: true,\n        invertedSettingName: \"hideReadReceipts\",\n    },\n    \"showTwelveHourTimestamps\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|use_12_hour_format\"),\n        default: false,\n    },\n    \"alwaysShowTimestamps\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|always_show_message_timestamps\"),\n        default: false,\n    },\n    \"userTimezone\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        displayName: _td(\"settings|preferences|user_timezone\"),\n        default: \"\",\n        // Location leak\n        shouldExportToRageshake: false,\n    },\n    \"userTimezonePublish\": {\n        // This is per-device so you can avoid having devices overwrite each other.\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        displayName: _td(\"settings|preferences|publish_timezone\"),\n        default: false,\n        controller: new ServerSupportUnstableFeatureController(\n            \"userTimezonePublish\",\n            defaultWatchManager,\n            [[UNSTABLE_MSC4133_EXTENDED_PROFILES], [STABLE_MSC4133_EXTENDED_PROFILES]],\n            undefined,\n            _td(\"labs|extended_profiles_msc_support\"),\n        ),\n    },\n    \"autoplayGifs\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|autoplay_gifs\"),\n        default: false,\n    },\n    \"autoplayVideo\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|autoplay_videos\"),\n        default: false,\n    },\n    \"enableSyntaxHighlightLanguageDetection\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|automatic_language_detection_syntax_highlight\"),\n        default: false,\n    },\n    \"expandCodeByDefault\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|code_block_expand_default\"),\n        default: false,\n    },\n    \"showCodeLineNumbers\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|code_block_line_numbers\"),\n        default: true,\n    },\n    \"scrollToBottomOnMessageSent\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|jump_to_bottom_on_send\"),\n        default: true,\n    },\n    \"Pill.shouldShowPillAvatar\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|preferences|show_avatars_pills\"),\n        default: true,\n        invertedSettingName: \"Pill.shouldHidePillAvatar\",\n    },\n    \"TextualBody.enableBigEmoji\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|big_emoji\"),\n        default: true,\n        invertedSettingName: \"TextualBody.disableBigEmoji\",\n    },\n    \"MessageComposerInput.isRichTextEnabled\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: false,\n    },\n    \"MessageComposer.showFormatting\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: false,\n    },\n    \"sendTypingNotifications\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|send_typing_notifications\"),\n        default: true,\n        invertedSettingName: \"dontSendTypingNotifications\",\n    },\n    \"showTypingNotifications\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|show_typing_notifications\"),\n        default: true,\n    },\n    \"ctrlFForSearch\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: IS_MAC ? _td(\"settings|use_command_f_search\") : _td(\"settings|use_control_f_search\"),\n        default: false,\n    },\n    \"MessageComposerInput.ctrlEnterToSend\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: IS_MAC\n            ? _td(\"settings|use_command_enter_send_message\")\n            : _td(\"settings|use_control_enter_send_message\"),\n        default: false,\n    },\n    \"MessageComposerInput.surroundWith\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|preferences|surround_text\"),\n        default: false,\n    },\n    \"MessageComposerInput.autoReplaceEmoji\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|replace_plain_emoji\"),\n        default: false,\n    },\n    \"MessageComposerInput.useMarkdown\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|enable_markdown\"),\n        description: () => _t(\"settings|enable_markdown_description\", {}, { code: (sub) => <code>{sub}</code> }),\n        default: true,\n    },\n    \"VideoView.flipVideoHorizontally\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|voip|mirror_local_feed\"),\n        default: true,\n    },\n    \"theme\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: \"light\",\n        controller: new ThemeController(),\n    },\n    \"custom_themes\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: [],\n        // Potential privacy leak via theme origin\n        shouldExportToRageshake: false,\n    },\n    \"use_system_theme\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: true,\n        displayName: _td(\"settings|appearance|match_system_theme\"),\n    },\n    \"useBundledEmojiFont\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: true,\n        displayName: _td(\"settings|appearance|bundled_emoji_font\"),\n        controller: new SystemFontController(),\n    },\n    \"useSystemFont\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: false,\n        displayName: _td(\"settings|appearance|custom_font\"),\n        controller: new SystemFontController(),\n        description: () =>\n            _t(\"settings|appearance|custom_font_description\", {\n                brand: SdkConfig.get().brand,\n            }),\n    },\n    \"systemFont\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: \"\",\n        displayName: _td(\"settings|appearance|custom_font_name\"),\n        controller: new SystemFontController(),\n    },\n    \"webRtcAllowPeerToPeer\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        displayName: _td(\"settings|voip|allow_p2p\"),\n        description: _td(\"settings|voip|allow_p2p_description\"),\n        default: true,\n        invertedSettingName: \"webRtcForceTURN\",\n    },\n    \"webrtc_audiooutput\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: \"default\",\n    },\n    \"webrtc_audioinput\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: \"default\",\n    },\n    \"webrtc_videoinput\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: \"default\",\n    },\n    \"webrtc_audio_autoGainControl\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        displayName: _td(\"settings|voip|auto_gain_control\"),\n        default: true,\n    },\n    \"webrtc_audio_echoCancellation\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        displayName: _td(\"settings|voip|echo_cancellation\"),\n        default: true,\n    },\n    \"webrtc_audio_noiseSuppression\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        displayName: _td(\"settings|voip|noise_suppression\"),\n        default: true,\n    },\n    \"language\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        default: \"en\",\n        // For privacy\n        shouldExportToRageshake: false,\n    },\n    \"breadcrumb_rooms\": {\n        // not really a setting\n        supportedLevels: [SettingLevel.ACCOUNT],\n        default: [],\n        // Contains joined rooms\n        shouldExportToRageshake: false,\n    },\n    \"recent_emoji\": {\n        // not really a setting\n        supportedLevels: [SettingLevel.ACCOUNT],\n        default: [],\n        // For privacy\n        shouldExportToRageshake: false,\n    },\n    \"SpotlightSearch.recentSearches\": {\n        // not really a setting\n        supportedLevels: [SettingLevel.ACCOUNT],\n        default: [], // list of room IDs, most recent first\n        // For privacy\n        shouldExportToRageshake: false,\n    },\n    \"showMediaEventIds\": {\n        // not really a setting\n        supportedLevels: [SettingLevel.DEVICE],\n        default: {}, // List of events => is visible\n        // Exports event IDs\n        shouldExportToRageshake: false,\n    },\n    \"SpotlightSearch.showNsfwPublicRooms\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|show_nsfw_content\"),\n        default: false,\n    },\n    \"room_directory_servers\": {\n        supportedLevels: [SettingLevel.ACCOUNT],\n        default: [],\n        // Contains connected servers for user\n        shouldExportToRageshake: false,\n    },\n    \"integrationProvisioning\": {\n        supportedLevels: [SettingLevel.ACCOUNT],\n        default: true,\n    },\n    \"allowedWidgets\": {\n        supportedLevels: [SettingLevel.ROOM_ACCOUNT, SettingLevel.ROOM_DEVICE],\n        supportedLevelsAreOrdered: true,\n        default: {}, // none allowed\n        shouldExportToRageshake: false,\n    },\n    // Legacy, kept around for transitionary purposes\n    \"analyticsOptIn\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        default: false,\n    },\n    \"pseudonymousAnalyticsOptIn\": {\n        supportedLevels: [SettingLevel.ACCOUNT],\n        displayName: _td(\"settings|security|send_analytics\"),\n        default: null,\n    },\n    \"deviceClientInformationOptIn\": {\n        supportedLevels: [SettingLevel.ACCOUNT],\n        displayName: _td(\"settings|security|record_session_details\"),\n        default: false,\n    },\n    \"Registration.mobileRegistrationHelper\": {\n        supportedLevels: [SettingLevel.CONFIG],\n        default: false,\n    },\n    \"autocompleteDelay\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        default: 200,\n    },\n    \"readMarkerInViewThresholdMs\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        default: 3000,\n    },\n    \"readMarkerOutOfViewThresholdMs\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        default: 30000,\n    },\n    \"blacklistUnverifiedDevices\": {\n        // We specifically want to have room-device > device so that users may set a device default\n        // with a per-room override.\n        supportedLevels: [SettingLevel.ROOM_DEVICE, SettingLevel.DEVICE],\n        supportedLevelsAreOrdered: true,\n        displayName: {\n            \"default\": _td(\"settings|security|strict_encryption\"),\n            \"room-device\": _td(\"room_settings|security|strict_encryption\"),\n        },\n        default: false,\n        controller: new UIFeatureController(UIFeature.AdvancedEncryption),\n    },\n    \"urlPreviewsEnabled\": {\n        supportedLevels: LEVELS_ROOM_SETTINGS_WITH_ROOM,\n        displayName: {\n            \"default\": _td(\"settings|inline_url_previews_default\"),\n            \"room-account\": _td(\"settings|inline_url_previews_room_account\"),\n            \"room\": _td(\"settings|inline_url_previews_room\"),\n        },\n        default: true,\n        controller: new UIFeatureController(UIFeature.URLPreviews),\n    },\n    \"urlPreviewsEnabled_e2ee\": {\n        supportedLevels: [SettingLevel.ROOM_DEVICE],\n        displayName: {\n            \"room-device\": _td(\"settings|inline_url_previews_room_account\"),\n        },\n        default: false,\n        controller: new UIFeatureController(UIFeature.URLPreviews),\n    },\n    \"notificationsEnabled\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: false,\n        controller: new NotificationsEnabledController(),\n        displayName: _td(\"settings|notifications|enable_desktop_notifications_session\"),\n    },\n    \"deviceNotificationsEnabled\": {\n        supportedLevels: [SettingLevel.DEVICE],\n        default: true,\n        displayName: _td(\"settings|notifications|enable_notifications_device\"),\n    },\n    \"notificationSound\": {\n        supportedLevels: LEVELS_ROOM_OR_ACCOUNT,\n        default: false,\n        // Contains personal information in file name\n        shouldExportToRageshake: false,\n    },\n    \"notificationBodyEnabled\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: true,\n        controller: new NotificationBodyEnabledController(),\n        displayName: _td(\"settings|notifications|show_message_desktop_notification\"),\n    },\n    \"audioNotificationsEnabled\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: true,\n        displayName: _td(\"settings|notifications|enable_audible_notifications_session\"),\n    },\n    \"enableWidgetScreenshots\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"devtools|widget_screenshots\"),\n        default: false,\n    },\n    \"promptBeforeInviteUnknownUsers\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|prompt_invite\"),\n        default: true,\n    },\n    \"widgetOpenIDPermissions\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: {\n            allow: [],\n            deny: [],\n        },\n        // Expses widget information\n        shouldExportToRageshake: false,\n    },\n    \"breadcrumbs\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        displayName: _td(\"settings|show_breadcrumbs\"),\n        default: true,\n    },\n    \"showHiddenEventsInTimeline\": {\n        displayName: _td(\"devtools|show_hidden_events\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: false,\n    },\n    \"lowBandwidth\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        displayName: _td(\"devtools|low_bandwidth_mode\"),\n        description: _td(\"devtools|low_bandwidth_mode_description\"),\n        default: false,\n        controller: new ReloadOnChangeController(),\n        shouldWarn: true,\n    },\n    \"fallbackICEServerAllowed\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        description: _td(\"settings|voip|enable_fallback_ice_server_description\"),\n        // This is a tri-state value, where `null` means \"prompt the user\".\n        default: null,\n        controller: new FallbackIceServerController(),\n    },\n    \"RoomList.preferredSorting\": {\n        supportedLevels: [SettingLevel.DEVICE],\n        default: SortingAlgorithm.Recency,\n    },\n    \"RoomList.showMessagePreview\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        default: false,\n        displayName: _td(\"settings|show_message_previews\"),\n    },\n    \"RightPanel.phasesGlobal\": {\n        supportedLevels: [SettingLevel.DEVICE],\n        default: null,\n    },\n    \"RightPanel.phases\": {\n        supportedLevels: [SettingLevel.ROOM_DEVICE],\n        default: null,\n    },\n    \"enableEventIndexing\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        displayName: _td(\"settings|security|enable_message_search\"),\n        default: true,\n    },\n    \"crawlerSleepTime\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        displayName: _td(\"settings|security|message_search_sleep_time\"),\n        default: 3000,\n    },\n    \"showCallButtonsInComposer\": {\n        // Dev note: This is no longer \"in composer\" but is instead \"in room header\".\n        // TODO: Rename with settings v3\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        default: true,\n        controller: new UIFeatureController(UIFeature.Voip),\n    },\n    \"ircDisplayNameWidth\": {\n        // We specifically want to have room-device > device so that users may set a device default\n        // with a per-room override.\n        supportedLevels: [SettingLevel.ROOM_DEVICE, SettingLevel.DEVICE],\n        supportedLevelsAreOrdered: true,\n        default: 80,\n    },\n    \"layout\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: Layout.Group,\n    },\n    \"Images.size\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: ImageSize.Normal,\n    },\n    \"showChatEffects\": {\n        supportedLevels: LEVELS_ROOM_SETTINGS_WITH_ROOM,\n        displayName: _td(\"settings|show_chat_effects\"),\n        default: true,\n        controller: new ReducedMotionController(),\n    },\n    \"Performance.addSendMessageTimingMetadata\": {\n        supportedLevels: [SettingLevel.CONFIG],\n        default: false,\n    },\n    \"Widgets.pinned\": {\n        // deprecated\n        supportedLevels: LEVELS_ROOM_OR_ACCOUNT,\n        default: {},\n        // Sensitive information in widget ID\n        shouldExportToRageshake: false,\n    },\n    \"Widgets.layout\": {\n        supportedLevels: LEVELS_ROOM_OR_ACCOUNT,\n        default: {},\n    },\n    \"Spaces.allRoomsInHome\": {\n        displayName: _td(\"settings|all_rooms_home\"),\n        description: _td(\"settings|all_rooms_home_description\"),\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: false,\n    },\n    \"Spaces.enabledMetaSpaces\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: {\n            [MetaSpace.Home]: true,\n        },\n    },\n    \"Spaces.showPeopleInSpace\": {\n        supportedLevels: [SettingLevel.ROOM_ACCOUNT],\n        default: true,\n    },\n    \"developerMode\": {\n        displayName: _td(\"devtools|developer_mode\"),\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: false,\n    },\n    \"automaticErrorReporting\": {\n        displayName: _td(\"labs|automatic_debug_logs\"),\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: false,\n        controller: new ReloadOnChangeController(),\n    },\n    \"automaticDecryptionErrorReporting\": {\n        displayName: _td(\"labs|automatic_debug_logs_decryption\"),\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: false,\n        controller: new ReloadOnChangeController(),\n    },\n    \"debug_scroll_panel\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: false,\n    },\n    \"debug_timeline_panel\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: false,\n    },\n    \"debug_registration\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: false,\n    },\n    \"debug_animation\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: false,\n    },\n    \"debug_legacy_call_handler\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: false,\n    },\n    \"audioInputMuted\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: false,\n    },\n    \"videoInputMuted\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: false,\n    },\n    \"activeCallRoomIds\": {\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS,\n        default: [],\n        // Contains room IDs\n        shouldExportToRageshake: false,\n    },\n    /**\n     * Enable or disable the release announcement feature\n     */\n    [Features.ReleaseAnnouncement]: {\n        isFeature: true,\n        labsGroup: LabGroup.Ui,\n        supportedLevels: LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG,\n        default: true,\n        displayName: _td(\"labs|release_announcement\"),\n    },\n    /**\n     * Managed by the {@link ReleaseAnnouncementStore}\n     * Store the release announcement data\n     */\n    \"releaseAnnouncementData\": {\n        supportedLevels: LEVELS_ACCOUNT_SETTINGS,\n        default: {},\n    },\n    [UIFeature.RoomHistorySettings]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.AdvancedEncryption]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.URLPreviews]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.Widgets]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.LocationSharing]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.Voip]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.Feedback]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.Registration]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.PasswordReset]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.Deactivate]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.ShareQRCode]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.ShareSocial]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.IdentityServer]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n        // Identity server (discovery) settings make no sense if 3PIDs in general are hidden\n        controller: new UIFeatureController(UIFeature.ThirdPartyID),\n    },\n    [UIFeature.ThirdPartyID]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.AdvancedSettings]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.TimelineEnableRelativeDates]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.AllowCreatingPublicSpaces]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n    [UIFeature.AllowCreatingPublicRooms]: {\n        supportedLevels: LEVELS_UI_FEATURE,\n        default: true,\n    },\n\n    // Electron-specific settings, they are stored by Electron and set/read over an IPC.\n    // We store them over there are they are necessary to know before the renderer process launches.\n    \"Electron.autoLaunch\": {\n        supportedLevels: [SettingLevel.PLATFORM],\n        displayName: _td(\"settings|start_automatically|label\"),\n        options: [\n            { value: \"enabled\", label: _td(\"settings|start_automatically|enabled\") },\n            { value: \"disabled\", label: _td(\"settings|start_automatically|disabled\") },\n            { value: \"minimised\", label: _td(\"settings|start_automatically|minimised\") },\n        ],\n        default: \"disabled\",\n    },\n    \"Electron.warnBeforeExit\": {\n        supportedLevels: [SettingLevel.PLATFORM],\n        displayName: _td(\"settings|warn_quit\"),\n        default: true,\n    },\n    \"Electron.alwaysShowMenuBar\": {\n        supportedLevels: [SettingLevel.PLATFORM],\n        displayName: _td(\"settings|preferences|always_show_menu_bar\"),\n        default: false,\n    },\n    \"Electron.showTrayIcon\": {\n        supportedLevels: [SettingLevel.PLATFORM],\n        displayName: _td(\"settings|preferences|enable_tray_icon\"),\n        default: true,\n    },\n    \"Electron.enableHardwareAcceleration\": {\n        supportedLevels: [SettingLevel.PLATFORM],\n        displayName: _td(\"settings|preferences|enable_hardware_acceleration\"),\n        default: true,\n    },\n    \"Electron.enableContentProtection\": {\n        supportedLevels: [SettingLevel.PLATFORM],\n        displayName: _td(\"settings|preferences|enable_content_protection\"),\n        default: false,\n    },\n    \"Developer.elementCallUrl\": {\n        supportedLevels: [SettingLevel.DEVICE],\n        displayName: _td(\"devtools|settings|elementCallUrl\"),\n        default: \"\",\n    },\n};\n","/*\nCopyright 2019-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type SettingLevel } from \"./SettingLevel\";\n\nexport type CallbackFn = (changedInRoomId: string | null, atLevel: SettingLevel, newValAtLevel: any) => void;\n\nconst IRRELEVANT_ROOM: string | null = null;\n\n/**\n * Generalized management class for dealing with watchers on a per-handler (per-level)\n * basis without duplicating code. Handlers are expected to push updates through this\n * class, which are then proxied outwards to any applicable watchers.\n */\nexport class WatchManager {\n    private watchers = new Map<string, Map<string | null, CallbackFn[]>>(); // settingName -> roomId -> CallbackFn[]\n\n    // Proxy for handlers to delegate changes to this manager\n    public watchSetting(settingName: string, roomId: string | null, cb: CallbackFn): void {\n        if (!this.watchers.has(settingName)) this.watchers.set(settingName, new Map());\n        if (!this.watchers.get(settingName)!.has(roomId)) this.watchers.get(settingName)!.set(roomId, []);\n        this.watchers.get(settingName)!.get(roomId)!.push(cb);\n    }\n\n    // Proxy for handlers to delegate changes to this manager\n    public unwatchSetting(cb: CallbackFn): void {\n        this.watchers.forEach((map) => {\n            map.forEach((callbacks) => {\n                let idx: number;\n                while ((idx = callbacks.indexOf(cb)) !== -1) {\n                    callbacks.splice(idx, 1);\n                }\n            });\n        });\n    }\n\n    public notifyUpdate(\n        settingName: string,\n        inRoomId: string | null,\n        atLevel: SettingLevel,\n        newValueAtLevel: any,\n    ): void {\n        // Dev note: We could avoid raising changes for ultimately inconsequential changes, but\n        // we also don't have a reliable way to get the old value of a setting. Instead, we'll just\n        // let it fall through regardless and let the receiver dedupe if they want to.\n\n        if (!this.watchers.has(settingName)) return;\n\n        const roomWatchers = this.watchers.get(settingName)!;\n        const callbacks: CallbackFn[] = [];\n\n        if (inRoomId !== null && roomWatchers.has(inRoomId)) {\n            callbacks.push(...roomWatchers.get(inRoomId)!);\n        }\n\n        if (!inRoomId) {\n            // Fire updates to all the individual room watchers too, as they probably care about the change higher up.\n            callbacks.push(...Array.from(roomWatchers.values()).flat(1));\n        } else if (roomWatchers.has(IRRELEVANT_ROOM)) {\n            callbacks.push(...roomWatchers.get(IRRELEVANT_ROOM)!);\n        }\n\n        for (const callback of callbacks) {\n            callback(inRoomId, atLevel, newValueAtLevel);\n        }\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type SettingLevel } from \"../SettingLevel.ts\";\nimport { MSC4380_INVITE_RULES_ACCOUNT_DATA_TYPE } from \"../../@types/invite-rules.ts\";\nimport { _td } from \"../../languageHandler.tsx\";\nimport ServerSupportUnstableFeatureController from \"./ServerSupportUnstableFeatureController.ts\";\nimport { defaultWatchManager, type SettingKey } from \"../Settings.tsx\";\n\n/**\n * Handles invite filtering rules provided by MSC4380.\n * This handler does not make use of the roomId parameter.\n */\nexport default class BlockInvitesConfigController extends ServerSupportUnstableFeatureController {\n    public constructor(settingName: SettingKey) {\n        super(settingName, defaultWatchManager, [[\"org.matrix.msc4380\"]], undefined, _td(\"settings|not_supported\"));\n    }\n\n    public getValueOverride(_level: SettingLevel): boolean {\n        const accountData = this.client?.getAccountData(MSC4380_INVITE_RULES_ACCOUNT_DATA_TYPE)?.getContent();\n        return accountData?.default_action == \"block\";\n    }\n\n    public async beforeChange(_level: SettingLevel, _roomId: string | null, newValue: boolean): Promise<boolean> {\n        if (!this.client) {\n            return false;\n        }\n        const newDefault = newValue ? \"block\" : \"allow\";\n        await this.client.setAccountData(MSC4380_INVITE_RULES_ACCOUNT_DATA_TYPE, { default_action: newDefault });\n        return true;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingsHandler from \"./SettingsHandler\";\n\n/**\n * Abstract settings handler wrapping around localStorage making getValue calls cheaper\n * by caching the values and listening for localStorage updates from other tabs.\n */\nexport default abstract class AbstractLocalStorageSettingsHandler extends SettingsHandler {\n    // Shared cache between all subclass instances\n    private static itemCache = new Map<string, string | null>();\n    private static objectCache = new Map<string, object>();\n    private static storageListenerBound = false;\n\n    private static onStorageEvent = (e: StorageEvent): void => {\n        if (e.key === null) {\n            AbstractLocalStorageSettingsHandler.clear();\n        } else {\n            AbstractLocalStorageSettingsHandler.itemCache.delete(e.key);\n            AbstractLocalStorageSettingsHandler.objectCache.delete(e.key);\n        }\n    };\n\n    private static clear(): void {\n        AbstractLocalStorageSettingsHandler.itemCache.clear();\n        AbstractLocalStorageSettingsHandler.objectCache.clear();\n    }\n\n    protected constructor() {\n        super();\n\n        if (!AbstractLocalStorageSettingsHandler.storageListenerBound) {\n            AbstractLocalStorageSettingsHandler.storageListenerBound = true;\n            // Listen for storage changes from other tabs to bust the cache\n            window.addEventListener(\"storage\", AbstractLocalStorageSettingsHandler.onStorageEvent);\n        }\n    }\n\n    protected getItem(key: string): string | null {\n        if (!AbstractLocalStorageSettingsHandler.itemCache.has(key)) {\n            const value = localStorage.getItem(key);\n            AbstractLocalStorageSettingsHandler.itemCache.set(key, value);\n            return value;\n        }\n\n        return AbstractLocalStorageSettingsHandler.itemCache.get(key)!;\n    }\n\n    protected getBoolean(key: string): boolean | null {\n        const item = this.getItem(key);\n        if (item === \"true\") return true;\n        if (item === \"false\") return false;\n        // Fall back to the next config level\n        return null;\n    }\n\n    protected getObject<T extends object>(key: string): T | null {\n        if (!AbstractLocalStorageSettingsHandler.objectCache.has(key)) {\n            try {\n                const value = JSON.parse(localStorage.getItem(key)!);\n                AbstractLocalStorageSettingsHandler.objectCache.set(key, value);\n                return value;\n            } catch (err) {\n                console.error(\"Failed to parse localStorage object\", err);\n                return null;\n            }\n        }\n\n        return AbstractLocalStorageSettingsHandler.objectCache.get(key) as T;\n    }\n\n    protected setItem(key: string, value: string): void {\n        AbstractLocalStorageSettingsHandler.itemCache.set(key, value);\n        localStorage.setItem(key, value);\n    }\n\n    protected setBoolean(key: string, value: boolean | null): void {\n        this.setItem(key, `${value}`);\n    }\n\n    protected setObject(key: string, value: object): void {\n        AbstractLocalStorageSettingsHandler.objectCache.set(key, value);\n        localStorage.setItem(key, JSON.stringify(value));\n    }\n\n    // handles both items and objects\n    protected removeItem(key: string): void {\n        localStorage.removeItem(key);\n        AbstractLocalStorageSettingsHandler.itemCache.delete(key);\n        AbstractLocalStorageSettingsHandler.objectCache.delete(key);\n    }\n\n    public isSupported(): boolean {\n        return localStorage !== undefined && localStorage !== null;\n    }\n\n    public reset(): void {\n        AbstractLocalStorageSettingsHandler.clear();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingsHandler from \"./SettingsHandler\";\n\n/**\n * Gets settings at the \"default\" level. This handler does not support setting values.\n * This handler does not make use of the roomId parameter.\n */\nexport default class DefaultSettingsHandler extends SettingsHandler {\n    /**\n     * Creates a new default settings handler with the given defaults\n     * @param {object} defaults The default setting values, keyed by setting name.\n     * @param {object} invertedDefaults The default inverted setting values, keyed by setting name.\n     */\n    public constructor(\n        private defaults: Record<string, any>,\n        private invertedDefaults: Record<string, any>,\n    ) {\n        super();\n    }\n\n    public getValue(settingName: string, roomId: string): any {\n        let value = this.defaults[settingName];\n        if (value === undefined) {\n            value = this.invertedDefaults[settingName];\n        }\n        return value;\n    }\n\n    public async setValue(settingName: string, roomId: string, newValue: any): Promise<void> {\n        throw new Error(\"Cannot set values on the default level handler\");\n    }\n\n    public canSetValue(settingName: string, roomId: string): boolean {\n        return false;\n    }\n\n    public isSupported(): boolean {\n        return true;\n    }\n}\n","/*\nCopyright 2024, 2025 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type RoomAccountDataEvents,\n    type MatrixClient,\n    type MatrixEvent,\n    type Room,\n    RoomEvent,\n} from \"matrix-js-sdk/src/matrix\";\n\nimport MatrixClientBackedSettingsHandler from \"./MatrixClientBackedSettingsHandler\";\nimport { objectClone, objectKeyChanges } from \"../../utils/objects\";\nimport { SettingLevel } from \"../SettingLevel\";\nimport { type WatchManager } from \"../WatchManager\";\nimport { MEDIA_PREVIEW_ACCOUNT_DATA_TYPE } from \"../../@types/media_preview\";\n\nconst ALLOWED_WIDGETS_EVENT_TYPE = \"im.vector.setting.allowed_widgets\";\nconst DEFAULT_SETTINGS_EVENT_TYPE = \"im.vector.web.settings\";\n\ndeclare module \"matrix-js-sdk/src/types\" {\n    interface RoomAccountDataEvents {\n        [ALLOWED_WIDGETS_EVENT_TYPE]: { [eventId: string]: boolean };\n        [DEFAULT_SETTINGS_EVENT_TYPE]: Record<string, any>;\n        \"org.matrix.room.preview_urls\": { disable: boolean };\n    }\n}\n\n/**\n * Gets and sets settings at the \"room-account\" level for the current user.\n */\nexport default class RoomAccountSettingsHandler extends MatrixClientBackedSettingsHandler {\n    public constructor(public readonly watchers: WatchManager) {\n        super();\n    }\n\n    protected initMatrixClient(oldClient: MatrixClient, newClient: MatrixClient): void {\n        if (oldClient) {\n            oldClient.removeListener(RoomEvent.AccountData, this.onAccountData);\n        }\n\n        newClient.on(RoomEvent.AccountData, this.onAccountData);\n    }\n\n    private onAccountData = (event: MatrixEvent, room: Room, prevEvent?: MatrixEvent): void => {\n        const roomId = room.roomId;\n\n        if (event.getType() === \"org.matrix.room.preview_urls\") {\n            let val = event.getContent()[\"disable\"];\n            if (typeof val !== \"boolean\") {\n                val = null;\n            } else {\n                val = !val;\n            }\n\n            this.watchers.notifyUpdate(\"urlPreviewsEnabled\", roomId, SettingLevel.ROOM_ACCOUNT, val);\n        } else if (event.getType() === DEFAULT_SETTINGS_EVENT_TYPE) {\n            // Figure out what changed and fire those updates\n            const prevContent = prevEvent?.getContent() ?? {};\n            const changedSettings = objectKeyChanges<Record<string, any>>(prevContent, event.getContent());\n            for (const settingName of changedSettings) {\n                const val = event.getContent()[settingName];\n                this.watchers.notifyUpdate(settingName, roomId, SettingLevel.ROOM_ACCOUNT, val);\n            }\n        } else if (event.getType() === ALLOWED_WIDGETS_EVENT_TYPE) {\n            this.watchers.notifyUpdate(\"allowedWidgets\", roomId, SettingLevel.ROOM_ACCOUNT, event.getContent());\n        } else if (event.getType() === MEDIA_PREVIEW_ACCOUNT_DATA_TYPE) {\n            this.watchers.notifyUpdate(\"mediaPreviewConfig\", roomId, SettingLevel.ROOM_ACCOUNT, event.getContent());\n        }\n    };\n\n    public getValue(settingName: string, roomId: string): any {\n        // Special case URL previews\n        if (settingName === \"urlPreviewsEnabled\") {\n            const content = this.getSettings(roomId, \"org.matrix.room.preview_urls\") || {};\n\n            // Check to make sure that we actually got a boolean\n            if (typeof content[\"disable\"] !== \"boolean\") return null;\n            return !content[\"disable\"];\n        }\n\n        // Special case allowed widgets\n        if (settingName === \"allowedWidgets\") {\n            return this.getSettings(roomId, ALLOWED_WIDGETS_EVENT_TYPE);\n        }\n\n        const settings = this.getSettings(roomId) || {};\n        return settings[settingName];\n    }\n\n    // helper function to send room account data then await it being echoed back\n    private async setRoomAccountData<K extends keyof RoomAccountDataEvents, F extends keyof RoomAccountDataEvents[K]>(\n        roomId: string,\n        eventType: K,\n        field: F | null,\n        value: RoomAccountDataEvents[K][F],\n    ): Promise<void> {\n        let content: ReturnType<RoomAccountSettingsHandler[\"getSettings\"]>;\n\n        if (field === null) {\n            content = value;\n        } else {\n            content = this.getSettings(roomId, eventType) || {};\n            content[field] = value;\n        }\n\n        await this.client.setRoomAccountData(roomId, eventType, content);\n\n        const deferred = Promise.withResolvers<void>();\n        const handler = (event: MatrixEvent, room: Room): void => {\n            if (room.roomId !== roomId || event.getType() !== eventType) return;\n            if (field !== null && event.getContent<Record<F, RoomAccountDataEvents[K][F]>>()[field] !== value) return;\n            this.client.off(RoomEvent.AccountData, handler);\n            deferred.resolve();\n        };\n        this.client.on(RoomEvent.AccountData, handler);\n\n        await deferred.promise;\n    }\n\n    public async setValue(settingName: string, roomId: string, newValue: any): Promise<void> {\n        switch (settingName) {\n            // Special case URL previews\n            case \"urlPreviewsEnabled\":\n                return this.setRoomAccountData(roomId, \"org.matrix.room.preview_urls\", \"disable\", !newValue);\n\n            // Special case allowed widgets\n            case \"allowedWidgets\":\n                return this.setRoomAccountData(roomId, ALLOWED_WIDGETS_EVENT_TYPE, null, newValue);\n            case \"mediaPreviewConfig\":\n                // Handled in MediaPreviewConfigController.\n                return;\n            case \"inviteRules\":\n                // Handled in InviteRulesConfigController.\n                return;\n            default:\n                return this.setRoomAccountData(roomId, DEFAULT_SETTINGS_EVENT_TYPE, settingName, newValue);\n        }\n    }\n\n    public canSetValue(settingName: string, roomId: string): boolean {\n        // If they have the room, they can set their own account data\n        return !!this.client.getRoom(roomId);\n    }\n\n    public isSupported(): boolean {\n        return this.client && !this.client.isGuest();\n    }\n\n    private getSettings(roomId: string, eventType = DEFAULT_SETTINGS_EVENT_TYPE): any {\n        // TODO: [TS] Type return\n        const event = this.client.getRoom(roomId)?.getAccountData(eventType);\n        if (!event || !event.getContent()) return null;\n        return objectClone(event.getContent()); // clone to prevent mutation\n    }\n}\n","/*\nCopyright 2024, 2025 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type AccountDataEvents, ClientEvent, type MatrixClient, type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { isEqual } from \"lodash\";\n\nimport MatrixClientBackedSettingsHandler from \"./MatrixClientBackedSettingsHandler\";\nimport { objectClone, objectKeyChanges } from \"../../utils/objects\";\nimport { SettingLevel } from \"../SettingLevel\";\nimport { type WatchManager } from \"../WatchManager\";\nimport { MEDIA_PREVIEW_ACCOUNT_DATA_TYPE } from \"../../@types/media_preview\";\n\nconst BREADCRUMBS_LEGACY_EVENT_TYPE = \"im.vector.riot.breadcrumb_rooms\";\nconst BREADCRUMBS_EVENT_TYPE = \"im.vector.setting.breadcrumbs\";\nconst BREADCRUMBS_EVENT_TYPES = [BREADCRUMBS_LEGACY_EVENT_TYPE, BREADCRUMBS_EVENT_TYPE];\nconst RECENT_EMOJI_EVENT_TYPE = \"io.element.recent_emoji\";\nconst INTEG_PROVISIONING_EVENT_TYPE = \"im.vector.setting.integration_provisioning\";\nconst ANALYTICS_EVENT_TYPE = \"im.vector.analytics\";\nconst DEFAULT_SETTINGS_EVENT_TYPE = \"im.vector.web.settings\";\n\n/**\n * Gets and sets settings at the \"account\" level for the current user.\n * This handler does not make use of the roomId parameter.\n */\nexport default class AccountSettingsHandler extends MatrixClientBackedSettingsHandler {\n    public constructor(public readonly watchers: WatchManager) {\n        super();\n    }\n\n    public get level(): SettingLevel {\n        return SettingLevel.ACCOUNT;\n    }\n\n    public initMatrixClient(oldClient: MatrixClient, newClient: MatrixClient): void {\n        oldClient?.removeListener(ClientEvent.AccountData, this.onAccountData);\n        newClient.on(ClientEvent.AccountData, this.onAccountData);\n    }\n\n    private onAccountData = (event: MatrixEvent, prevEvent?: MatrixEvent): void => {\n        if (event.getType() === \"org.matrix.preview_urls\") {\n            let val = event.getContent()[\"disable\"];\n            if (typeof val !== \"boolean\") {\n                val = null;\n            } else {\n                val = !val;\n            }\n\n            this.watchers.notifyUpdate(\"urlPreviewsEnabled\", null, SettingLevel.ACCOUNT, val);\n        } else if (event.getType() === DEFAULT_SETTINGS_EVENT_TYPE || event.getType() === ANALYTICS_EVENT_TYPE) {\n            // Figure out what changed and fire those updates\n            const prevContent = prevEvent?.getContent() ?? {};\n            const changedSettings = objectKeyChanges<Record<string, any>>(prevContent, event.getContent());\n            for (const settingName of changedSettings) {\n                const val = event.getContent()[settingName];\n                this.watchers.notifyUpdate(settingName, null, SettingLevel.ACCOUNT, val);\n            }\n        } else if (BREADCRUMBS_EVENT_TYPES.includes(event.getType())) {\n            this.notifyBreadcrumbsUpdate(event);\n        } else if (event.getType() === INTEG_PROVISIONING_EVENT_TYPE) {\n            const val = event.getContent()[\"enabled\"];\n            this.watchers.notifyUpdate(\"integrationProvisioning\", null, SettingLevel.ACCOUNT, val);\n        } else if (event.getType() === RECENT_EMOJI_EVENT_TYPE) {\n            const val = event.getContent()[\"enabled\"];\n            this.watchers.notifyUpdate(\"recent_emoji\", null, SettingLevel.ACCOUNT, val);\n        } else if (event.getType() === MEDIA_PREVIEW_ACCOUNT_DATA_TYPE) {\n            this.watchers.notifyUpdate(\"mediaPreviewConfig\", null, SettingLevel.ROOM_ACCOUNT, event.getContent());\n        }\n    };\n\n    public getValue(settingName: string, roomId: string): any {\n        // Special case URL previews\n        if (settingName === \"urlPreviewsEnabled\") {\n            const content = this.getSettings(\"org.matrix.preview_urls\") || {};\n\n            // Check to make sure that we actually got a boolean\n            if (typeof content[\"disable\"] !== \"boolean\") return null;\n            return !content[\"disable\"];\n        }\n\n        // Special case for breadcrumbs\n        if (settingName === \"breadcrumb_rooms\") {\n            let content = this.getSettings(BREADCRUMBS_EVENT_TYPE);\n            if (!content || !content[\"recent_rooms\"]) {\n                content = this.getSettings(BREADCRUMBS_LEGACY_EVENT_TYPE);\n\n                // This is a bit of a hack, but it makes things slightly easier\n                if (content) content[\"recent_rooms\"] = content[\"rooms\"];\n            }\n\n            return content && content[\"recent_rooms\"] ? content[\"recent_rooms\"] : [];\n        }\n\n        // Special case recent emoji\n        if (settingName === \"recent_emoji\") {\n            const content = this.getSettings(RECENT_EMOJI_EVENT_TYPE);\n            return content ? content[\"recent_emoji\"] : null;\n        }\n\n        // Special case integration manager provisioning\n        if (settingName === \"integrationProvisioning\") {\n            const content = this.getSettings(INTEG_PROVISIONING_EVENT_TYPE);\n            return content ? content[\"enabled\"] : null;\n        }\n\n        if (settingName === \"pseudonymousAnalyticsOptIn\") {\n            const content = this.getSettings(ANALYTICS_EVENT_TYPE) || {};\n            // Check to make sure that we actually got a boolean\n            if (typeof content[settingName] !== \"boolean\") return null;\n            return content[settingName];\n        }\n\n        if (settingName === \"MessageComposerInput.insertTrailingColon\") {\n            const content = this.getSettings() || {};\n            const value = content[settingName];\n            if (value === null || value === undefined) {\n                // Write true as it is the default. This will give us the option\n                // of making this opt-in in the future, without affecting old\n                // users\n                this.setValue(settingName, roomId, true);\n                return true;\n            }\n            return value;\n        }\n\n        const settings = this.getSettings() || {};\n        let preferredValue = settings[settingName];\n\n        if (preferredValue === null || preferredValue === undefined) {\n            // Honour the old setting on read only\n            if (settingName === \"hideAvatarChanges\" || settingName === \"hideDisplaynameChanges\") {\n                preferredValue = settings[\"hideAvatarDisplaynameChanges\"];\n            }\n        }\n\n        return preferredValue;\n    }\n\n    // helper function to set account data then await it being echoed back\n    private async setAccountData<K extends keyof AccountDataEvents, F extends keyof AccountDataEvents[K]>(\n        eventType: K,\n        field: F,\n        value: AccountDataEvents[K][F],\n        legacyEventType?: keyof AccountDataEvents,\n    ): Promise<void> {\n        let content = this.getSettings(eventType);\n        if (legacyEventType && !content?.[field]) {\n            content = this.getSettings(legacyEventType);\n        }\n\n        if (!content) {\n            content = {};\n        }\n\n        content[field] = value;\n\n        // Attach a deferred *before* setting the account data to ensure we catch any requests\n        // which race between different lines.\n        const deferred = Promise.withResolvers<void>();\n        const handler = (event: MatrixEvent): void => {\n            if (event.getType() !== eventType || !isEqual(event.getContent<AccountDataEvents[K]>()[field], value))\n                return;\n            this.client.off(ClientEvent.AccountData, handler);\n            deferred.resolve();\n        };\n        this.client.on(ClientEvent.AccountData, handler);\n\n        await this.client.setAccountData(eventType, content);\n\n        await deferred.promise;\n    }\n\n    public async setValue(settingName: string, roomId: string, newValue: any): Promise<void> {\n        switch (settingName) {\n            // Special case URL previews\n            case \"urlPreviewsEnabled\":\n                return this.setAccountData(\"org.matrix.preview_urls\", \"disable\", !newValue);\n\n            // Special case for breadcrumbs\n            case \"breadcrumb_rooms\":\n                return this.setAccountData(\n                    BREADCRUMBS_EVENT_TYPE,\n                    \"recent_rooms\",\n                    newValue,\n                    BREADCRUMBS_LEGACY_EVENT_TYPE,\n                );\n\n            // Special case recent emoji\n            case \"recent_emoji\":\n                return this.setAccountData(RECENT_EMOJI_EVENT_TYPE, \"recent_emoji\", newValue);\n\n            // Special case integration manager provisioning\n            case \"integrationProvisioning\":\n                return this.setAccountData(INTEG_PROVISIONING_EVENT_TYPE, \"enabled\", newValue);\n\n            // Special case analytics\n            case \"pseudonymousAnalyticsOptIn\":\n                return this.setAccountData(ANALYTICS_EVENT_TYPE, \"pseudonymousAnalyticsOptIn\", newValue);\n            case \"mediaPreviewConfig\":\n                // Handled in MediaPreviewConfigController.\n                return;\n            case \"inviteRules\":\n                // Handled in InviteRulesConfigController.\n                return;\n            default:\n                return this.setAccountData(DEFAULT_SETTINGS_EVENT_TYPE, settingName, newValue);\n        }\n    }\n\n    public canSetValue(settingName: string, roomId: string): boolean {\n        return true; // It's their account, so they should be able to\n    }\n\n    public isSupported(): boolean {\n        return this.client && !this.client.isGuest();\n    }\n\n    private getSettings(eventType: keyof AccountDataEvents = \"im.vector.web.settings\"): any {\n        // TODO: [TS] Types on return\n        if (!this.client) return null;\n\n        const event = this.client.getAccountData(eventType);\n        if (!event || !event.getContent()) return null;\n        return objectClone(event.getContent()); // clone to prevent mutation\n    }\n\n    private notifyBreadcrumbsUpdate(event: MatrixEvent): void {\n        let val = [];\n        if (event.getType() === BREADCRUMBS_LEGACY_EVENT_TYPE) {\n            // This seems fishy - try and get the event for the new rooms\n            const newType = this.getSettings(BREADCRUMBS_EVENT_TYPE);\n            if (newType) val = newType[\"recent_rooms\"];\n            else val = event.getContent()[\"rooms\"];\n        } else if (event.getType() === BREADCRUMBS_EVENT_TYPE) {\n            val = event.getContent()[\"recent_rooms\"];\n        } else {\n            return; // for sanity, not because we expect to be here.\n        }\n        this.watchers.notifyUpdate(\"breadcrumb_rooms\", null, SettingLevel.ACCOUNT, val || []);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type MatrixClient,\n    type MatrixEvent,\n    type RoomState,\n    RoomStateEvent,\n    type StateEvents,\n} from \"matrix-js-sdk/src/matrix\";\n\nimport MatrixClientBackedSettingsHandler from \"./MatrixClientBackedSettingsHandler\";\nimport { objectClone, objectKeyChanges } from \"../../utils/objects\";\nimport { SettingLevel } from \"../SettingLevel\";\nimport { type WatchManager } from \"../WatchManager\";\n\nconst DEFAULT_SETTINGS_EVENT_TYPE = \"im.vector.web.settings\";\ntype RoomSettingsEventType = typeof DEFAULT_SETTINGS_EVENT_TYPE | \"org.matrix.room.preview_urls\";\n\n/**\n * Gets and sets settings at the \"room\" level.\n */\nexport default class RoomSettingsHandler extends MatrixClientBackedSettingsHandler {\n    public constructor(public readonly watchers: WatchManager) {\n        super();\n    }\n\n    protected initMatrixClient(oldClient: MatrixClient, newClient: MatrixClient): void {\n        if (oldClient) {\n            oldClient.removeListener(RoomStateEvent.Events, this.onEvent);\n        }\n\n        newClient.on(RoomStateEvent.Events, this.onEvent);\n    }\n\n    private onEvent = (event: MatrixEvent, state: RoomState, prevEvent: MatrixEvent | null): void => {\n        const roomId = event.getRoomId()!;\n        const room = this.client.getRoom(roomId);\n\n        // Note: in tests and during the encryption setup on initial load we might not have\n        // rooms in the store, so we just quietly ignore the problem. If we log it then we'll\n        // just end up spamming the logs a few thousand times. It is perfectly fine for us\n        // to ignore the problem as the app will not have loaded enough to care yet.\n        if (!room) return;\n\n        // ignore state updates which are not current\n        if (room && state !== room.currentState) return;\n\n        if (event.getType() === \"org.matrix.room.preview_urls\") {\n            let val = event.getContent()[\"disable\"];\n            if (typeof val !== \"boolean\") {\n                val = null;\n            } else {\n                val = !val;\n            }\n\n            this.watchers.notifyUpdate(\"urlPreviewsEnabled\", roomId, SettingLevel.ROOM, val);\n        } else if (event.getType() === DEFAULT_SETTINGS_EVENT_TYPE) {\n            // Figure out what changed and fire those updates\n            const prevContent = prevEvent?.getContent() ?? {};\n            const changedSettings = objectKeyChanges<Record<string, any>>(prevContent, event.getContent());\n            for (const settingName of changedSettings) {\n                this.watchers.notifyUpdate(settingName, roomId, SettingLevel.ROOM, event.getContent()[settingName]);\n            }\n        }\n    };\n\n    public getValue(settingName: string, roomId: string): any {\n        // Special case URL previews\n        if (settingName === \"urlPreviewsEnabled\") {\n            const content = this.getSettings(roomId, \"org.matrix.room.preview_urls\") || {};\n\n            // Check to make sure that we actually got a boolean\n            if (typeof content[\"disable\"] !== \"boolean\") return null;\n            return !content[\"disable\"];\n        }\n\n        const settings = this.getSettings(roomId) || {};\n        return settings[settingName];\n    }\n\n    // helper function to send state event then await it being echoed back\n    private async sendStateEvent<K extends RoomSettingsEventType, F extends keyof StateEvents[K]>(\n        roomId: string,\n        eventType: K,\n        field: F,\n        value: StateEvents[K][F],\n    ): Promise<void> {\n        const content = this.getSettings(roomId, eventType) || {};\n        content[field] = value;\n\n        const { event_id: eventId } = await this.client.sendStateEvent(roomId, eventType, content);\n\n        const deferred = Promise.withResolvers<void>();\n        const handler = (event: MatrixEvent): void => {\n            if (event.getId() !== eventId) return;\n            this.client.off(RoomStateEvent.Events, handler);\n            deferred.resolve();\n        };\n        this.client.on(RoomStateEvent.Events, handler);\n\n        await deferred.promise;\n    }\n\n    public setValue(settingName: string, roomId: string, newValue: any): Promise<void> {\n        switch (settingName) {\n            // Special case URL previews\n            case \"urlPreviewsEnabled\":\n                return this.sendStateEvent(roomId, \"org.matrix.room.preview_urls\", \"disable\", !newValue);\n\n            default:\n                return this.sendStateEvent(roomId, DEFAULT_SETTINGS_EVENT_TYPE, settingName, newValue);\n        }\n    }\n\n    public canSetValue(settingName: string, roomId: string): boolean {\n        const room = this.client.getRoom(roomId);\n\n        let eventType = DEFAULT_SETTINGS_EVENT_TYPE;\n        if (settingName === \"urlPreviewsEnabled\") eventType = \"org.matrix.room.preview_urls\";\n\n        return room?.currentState.maySendStateEvent(eventType, this.client.getUserId()!) ?? false;\n    }\n\n    public isSupported(): boolean {\n        return !!this.client;\n    }\n\n    private getSettings(roomId: string, eventType = DEFAULT_SETTINGS_EVENT_TYPE): any {\n        const event = this.client.getRoom(roomId)?.currentState.getStateEvents(eventType, \"\");\n        if (!event?.getContent()) return null;\n        return objectClone(event.getContent()); // clone to prevent mutation\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { isNullOrUndefined } from \"matrix-js-sdk/src/utils\";\n\nimport SettingsHandler from \"./SettingsHandler\";\nimport SdkConfig from \"../../SdkConfig\";\nimport { SnakedObject } from \"../../utils/SnakedObject\";\nimport { type IConfigOptions } from \"../../IConfigOptions\";\n\n/**\n * Gets and sets settings at the \"config\" level. This handler does not make use of the\n * roomId parameter.\n */\nexport default class ConfigSettingsHandler extends SettingsHandler {\n    public constructor(private featureNames: string[]) {\n        super();\n    }\n\n    public getValue(settingName: string, roomId: string): any {\n        const config = new SnakedObject<IConfigOptions>(SdkConfig.get());\n\n        if (this.featureNames.includes(settingName)) {\n            const labsConfig = config.get(\"features\") || {};\n            const val = labsConfig[settingName];\n            if (isNullOrUndefined(val)) return null; // no definition at this level\n            if (val === true || val === false) return val; // new style: mapped as a boolean\n            if (val === \"enable\") return true; // backwards compat\n            if (val === \"disable\") return false; // backwards compat\n            if (val === \"labs\") return null; // backwards compat, no override\n            return null; // fallback in the case of invalid input\n        }\n\n        // Special case themes\n        if (settingName === \"theme\") {\n            return config.get(\"default_theme\");\n        }\n\n        const settingsConfig = config.get(\"setting_defaults\");\n        if (!settingsConfig || isNullOrUndefined(settingsConfig[settingName])) return null;\n        return settingsConfig[settingName];\n    }\n\n    public async setValue(settingName: string, roomId: string, newValue: any): Promise<void> {\n        throw new Error(\"Cannot change settings at the config level\");\n    }\n\n    public canSetValue(settingName: string, roomId: string): boolean {\n        return false;\n    }\n\n    public isSupported(): boolean {\n        return true; // SdkConfig is always there\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingsHandler from \"./SettingsHandler\";\nimport { type SettingLevel } from \"../SettingLevel\";\n\n/**\n * A wrapper for a SettingsHandler that performs local echo on\n * changes to settings. This wrapper will use the underlying\n * handler as much as possible to ensure values are not stale.\n */\nexport default class LocalEchoWrapper extends SettingsHandler {\n    private cache: {\n        [settingName: string]: {\n            [roomId: string]: any;\n        };\n    } = {};\n\n    /**\n     * Creates a new local echo wrapper\n     * @param {SettingsHandler} handler The handler to wrap\n     * @param {SettingLevel} level The level to notify updates at\n     */\n    public constructor(\n        private readonly handler: SettingsHandler,\n        private readonly level: SettingLevel,\n    ) {\n        super();\n    }\n\n    public getValue(settingName: string, roomId: string): any {\n        const cacheRoomId = roomId ?? \"UNDEFINED\"; // avoid weird keys\n        const bySetting = this.cache[settingName];\n        if (bySetting?.hasOwnProperty(cacheRoomId)) {\n            return bySetting[cacheRoomId];\n        }\n\n        return this.handler.getValue(settingName, roomId);\n    }\n\n    public async setValue(settingName: string, roomId: string, newValue: any): Promise<void> {\n        if (!this.cache[settingName]) this.cache[settingName] = {};\n        const bySetting = this.cache[settingName];\n\n        const cacheRoomId = roomId ?? \"UNDEFINED\"; // avoid weird keys\n        bySetting[cacheRoomId] = newValue;\n\n        const currentValue = this.handler.getValue(settingName, roomId);\n        const handlerPromise = this.handler.setValue(settingName, roomId, newValue);\n        this.handler.watchers?.notifyUpdate(settingName, roomId, this.level, newValue);\n\n        try {\n            await handlerPromise;\n        } catch {\n            // notify of a rollback\n            this.handler.watchers?.notifyUpdate(settingName, roomId, this.level, currentValue);\n        } finally {\n            // only expire the cache if our value hasn't been overwritten yet\n            if (bySetting[cacheRoomId] === newValue) {\n                delete bySetting[cacheRoomId];\n            }\n        }\n    }\n\n    public canSetValue(settingName: string, roomId: string): boolean {\n        return this.handler.canSetValue(settingName, roomId);\n    }\n\n    public isSupported(): boolean {\n        return this.handler.isSupported();\n    }\n\n    public reset(): void {\n        this.cache = {};\n        this.handler.reset();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingsHandler from \"./SettingsHandler\";\nimport PlatformPeg from \"../../PlatformPeg\";\nimport { SETTINGS } from \"../Settings\";\nimport { SettingLevel } from \"../SettingLevel\";\n\n/**\n * Gets and sets settings at the \"platform\" level for the current device.\n * This handler does not make use of the roomId parameter.\n */\nexport default class PlatformSettingsHandler extends SettingsHandler {\n    private store: { [settingName: string]: any } = {};\n\n    public constructor() {\n        super();\n\n        void this.setup();\n    }\n\n    private async setup(): Promise<void> {\n        const platform = await PlatformPeg.platformPromise;\n        await platform.initialised;\n\n        // Load setting values as they are async and `getValue` must be synchronous\n        Object.entries(SETTINGS).forEach(([key, setting]) => {\n            if (setting.supportedLevels?.includes(SettingLevel.PLATFORM) && platform.supportsSetting(key)) {\n                platform.getSettingValue(key).then((value: any) => {\n                    this.store[key] = value;\n                });\n            }\n        });\n    }\n\n    public canSetValue(settingName: string, roomId: string): boolean {\n        return PlatformPeg.get()?.supportsSetting(settingName) ?? false;\n    }\n\n    public getValue(settingName: string, roomId: string): any {\n        return this.store[settingName];\n    }\n\n    public async setValue(settingName: string, roomId: string, newValue: any): Promise<void> {\n        this.store[settingName] = newValue; // keep cache up to date for synchronous access\n        await PlatformPeg.get()?.setSettingValue(settingName, newValue);\n    }\n\n    public isSupported(): boolean {\n        return PlatformPeg.get()?.supportsSetting() ?? false;\n    }\n}\n","/*\nCopyright 2024, 2025 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type ReactNode } from \"react\";\nimport { ClientEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport DeviceSettingsHandler from \"./handlers/DeviceSettingsHandler\";\nimport RoomDeviceSettingsHandler from \"./handlers/RoomDeviceSettingsHandler\";\nimport DefaultSettingsHandler from \"./handlers/DefaultSettingsHandler\";\nimport RoomAccountSettingsHandler from \"./handlers/RoomAccountSettingsHandler\";\nimport AccountSettingsHandler from \"./handlers/AccountSettingsHandler\";\nimport RoomSettingsHandler from \"./handlers/RoomSettingsHandler\";\nimport ConfigSettingsHandler from \"./handlers/ConfigSettingsHandler\";\nimport { _t } from \"../languageHandler\";\nimport dis from \"../dispatcher/dispatcher\";\nimport {\n    type IFeature,\n    type ISetting,\n    type LabGroup,\n    SETTINGS,\n    defaultWatchManager,\n    type SettingKey,\n    type Settings,\n} from \"./Settings\";\nimport LocalEchoWrapper from \"./handlers/LocalEchoWrapper\";\nimport { type CallbackFn as WatchCallbackFn } from \"./WatchManager\";\nimport { SettingLevel } from \"./SettingLevel\";\nimport type SettingsHandler from \"./handlers/SettingsHandler\";\nimport { type SettingUpdatedPayload } from \"../dispatcher/payloads/SettingUpdatedPayload\";\nimport { Action } from \"../dispatcher/actions\";\nimport PlatformSettingsHandler from \"./handlers/PlatformSettingsHandler\";\nimport ReloadOnChangeController from \"./controllers/ReloadOnChangeController\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { MediaPreviewValue } from \"../@types/media_preview\";\n\n// Convert the settings to easier to manage objects for the handlers\nconst defaultSettings: Record<string, any> = {};\nconst invertedDefaultSettings: Record<string, boolean> = {};\nconst featureNames: SettingKey[] = [];\nfor (const key in SETTINGS) {\n    const setting = SETTINGS[key as SettingKey];\n    defaultSettings[key] = setting.default;\n    if (setting.isFeature) featureNames.push(key as SettingKey);\n    if (setting.invertedSettingName) {\n        // Invert now so that the rest of the system will invert it back to what was intended.\n        invertedDefaultSettings[setting.invertedSettingName] = !setting.default;\n    }\n}\n\n// Only wrap the handlers with async setters in a local echo wrapper\nconst LEVEL_HANDLERS: Record<SettingLevel, SettingsHandler> = {\n    [SettingLevel.DEVICE]: new DeviceSettingsHandler(featureNames, defaultWatchManager),\n    [SettingLevel.ROOM_DEVICE]: new RoomDeviceSettingsHandler(defaultWatchManager),\n    [SettingLevel.ROOM_ACCOUNT]: new LocalEchoWrapper(\n        new RoomAccountSettingsHandler(defaultWatchManager),\n        SettingLevel.ROOM_ACCOUNT,\n    ),\n    [SettingLevel.ACCOUNT]: new LocalEchoWrapper(new AccountSettingsHandler(defaultWatchManager), SettingLevel.ACCOUNT),\n    [SettingLevel.ROOM]: new LocalEchoWrapper(new RoomSettingsHandler(defaultWatchManager), SettingLevel.ROOM),\n    [SettingLevel.PLATFORM]: new LocalEchoWrapper(new PlatformSettingsHandler(), SettingLevel.PLATFORM),\n    [SettingLevel.CONFIG]: new ConfigSettingsHandler(featureNames),\n    [SettingLevel.DEFAULT]: new DefaultSettingsHandler(defaultSettings, invertedDefaultSettings),\n};\n\nexport const LEVEL_ORDER = [\n    SettingLevel.DEVICE,\n    SettingLevel.ROOM_DEVICE,\n    SettingLevel.ROOM_ACCOUNT,\n    SettingLevel.ACCOUNT,\n    SettingLevel.ROOM,\n    SettingLevel.CONFIG,\n    SettingLevel.DEFAULT,\n];\n\nfunction getLevelOrder(setting: ISetting): SettingLevel[] {\n    // Settings which support only a single setting level are inherently ordered\n    if (setting.supportedLevelsAreOrdered || setting.supportedLevels.length === 1) {\n        // return a copy to prevent callers from modifying the array\n        return [...setting.supportedLevels];\n    }\n    return LEVEL_ORDER;\n}\n\nexport type CallbackFn = (\n    settingName: SettingKey,\n    roomId: string | null,\n    atLevel: SettingLevel,\n    newValAtLevel: any,\n    newVal: any,\n) => void;\n\ntype HandlerMap = Partial<{\n    [level in SettingLevel]: SettingsHandler;\n}>;\n\n/**\n * Controls and manages application settings by providing varying levels at which the\n * setting value may be specified. The levels are then used to determine what the setting\n * value should be given a set of circumstances. The levels, in priority order, are:\n * - SettingLevel.DEVICE         - Values are determined by the current device\n * - SettingLevel.ROOM_DEVICE    - Values are determined by the current device for a particular room\n * - SettingLevel.ROOM_ACCOUNT   - Values are determined by the current account for a particular room\n * - SettingLevel.ACCOUNT        - Values are determined by the current account\n * - SettingLevel.ROOM           - Values are determined by a particular room (by the room admins)\n * - SettingLevel.CONFIG         - Values are determined by the config.json\n * - SettingLevel.DEFAULT        - Values are determined by the hardcoded defaults\n *\n * Each level has a different method to storing the setting value. For implementation\n * specific details, please see the handlers. The \"config\" and \"default\" levels are\n * both always supported on all platforms. All other settings should be guarded by\n * isLevelSupported() prior to attempting to set the value.\n *\n * Settings can also represent features. Features are significant portions of the\n * application that warrant a dedicated setting to toggle them on or off. Features are\n * special-cased to ensure that their values respect the configuration (for example, a\n * feature may be reported as disabled even though a user has specifically requested it\n * be enabled).\n */\nexport default class SettingsStore {\n    // We support watching settings for changes, and do this by tracking which callbacks have\n    // been given to us. We end up returning the callbackRef to the caller so they can unsubscribe\n    // at a later point.\n    //\n    // We also maintain a list of monitors which are special watchers: they cause dispatches\n    // when the setting changes. We track which rooms we're monitoring though to ensure we\n    // don't duplicate updates on the bus.\n    private static watchers = new Map<string, WatchCallbackFn>();\n    private static monitors = new Map<string, Map<string | null, string>>(); // { settingName => { roomId => callbackRef } }\n\n    // Counter used for generation of watcher IDs\n    private static watcherCount = 1;\n\n    public static reset(): void {\n        for (const handler of Object.values(LEVEL_HANDLERS)) {\n            handler.reset();\n        }\n    }\n\n    /**\n     * Gets all the feature-style setting names.\n     * @returns {string[]} The names of the feature settings.\n     */\n    public static getFeatureSettingNames(): SettingKey[] {\n        return (Object.keys(SETTINGS) as SettingKey[]).filter((n) => SettingsStore.isFeature(n));\n    }\n\n    /**\n     * Watches for changes in a particular setting. This is done without any local echo\n     * wrapping and fires whenever a change is detected in a setting's value, at any level.\n     * Watching is intended to be used in scenarios where the app needs to react to changes\n     * made by other devices. It is otherwise expected that callers will be able to use the\n     * Controller system or track their own changes to settings. Callers should retain the\n     * returned reference to later unsubscribe from updates.\n     * @param {string} settingName The setting name to watch\n     * @param {String} roomId The room ID to watch for changes in. May be null for 'all'.\n     * @param {function} callbackFn A function to be called when a setting change is\n     * detected. Five arguments can be expected: the setting name, the room ID (may be null),\n     * the level the change happened at, the new value at the given level, and finally the new\n     * value for the setting regardless of level. The callback is responsible for determining\n     * if the change in value is worthwhile enough to react upon.\n     * @returns {string} A reference to the watcher that was employed.\n     */\n    public static watchSetting(settingName: SettingKey, roomId: string | null, callbackFn: CallbackFn): string {\n        const setting = SETTINGS[settingName];\n        if (!setting) throw new Error(`${settingName} is not a setting`);\n\n        const finalSettingName: string = setting.invertedSettingName ?? settingName;\n\n        const watcherId = `${new Date().getTime()}_${SettingsStore.watcherCount++}_${finalSettingName}_${roomId}`;\n\n        const localizedCallback = (changedInRoomId: string | null, atLevel: SettingLevel, newValAtLevel: any): void => {\n            if (!SettingsStore.doesSettingSupportLevel(settingName, atLevel)) {\n                logger.warn(\n                    `Setting handler notified for an update of an invalid setting level: ` +\n                        `${settingName}@${atLevel} - this likely means a weird setting value ` +\n                        `made it into the level's storage. The notification will be ignored.`,\n                );\n                return;\n            }\n            const newValue = SettingsStore.getValue(settingName);\n            const newValueAtLevel = SettingsStore.getValueAt(atLevel, settingName) ?? newValAtLevel;\n            callbackFn(settingName, changedInRoomId, atLevel, newValueAtLevel, newValue);\n        };\n\n        SettingsStore.watchers.set(watcherId, localizedCallback);\n        defaultWatchManager.watchSetting(finalSettingName, roomId, localizedCallback);\n\n        return watcherId;\n    }\n\n    /**\n     * Stops the SettingsStore from watching a setting. This is a no-op if the watcher\n     * provided is not found.\n     * @param watcherReference The watcher reference (received from #watchSetting) to cancel.\n     * Can be undefined to avoid needing an if around every caller.\n     */\n    public static unwatchSetting(watcherReference: string | undefined): void {\n        if (!watcherReference) return;\n        if (!SettingsStore.watchers.has(watcherReference)) {\n            logger.warn(`Ending non-existent watcher ID ${watcherReference}`);\n            return;\n        }\n\n        defaultWatchManager.unwatchSetting(SettingsStore.watchers.get(watcherReference)!);\n        SettingsStore.watchers.delete(watcherReference);\n    }\n\n    /**\n     * Sets up a monitor for a setting. This behaves similar to #watchSetting except instead\n     * of making a call to a callback, it forwards all changes to the dispatcher. Callers can\n     * expect to listen for the 'setting_updated' action with an object containing settingName,\n     * roomId, level, newValueAtLevel, and newValue.\n     * @param {string} settingName The setting name to monitor.\n     * @param {String} roomId The room ID to monitor for changes in. Use null for all rooms.\n     */\n    public static monitorSetting(settingName: SettingKey, roomId: string | null): void {\n        roomId = roomId || null; // the thing wants null specifically to work, so appease it.\n\n        if (!this.monitors.has(settingName)) this.monitors.set(settingName, new Map());\n\n        const registerWatcher = (): void => {\n            this.monitors.get(settingName)!.set(\n                roomId,\n                SettingsStore.watchSetting(\n                    settingName,\n                    roomId,\n                    (settingName, inRoomId, level, newValueAtLevel, newValue) => {\n                        dis.dispatch<SettingUpdatedPayload>({\n                            action: Action.SettingUpdated,\n                            settingName,\n                            roomId: inRoomId,\n                            level,\n                            newValueAtLevel,\n                            newValue,\n                        });\n                    },\n                ),\n            );\n        };\n\n        const rooms = Array.from(this.monitors.get(settingName)!.keys());\n        const hasRoom = rooms.find((r) => r === roomId || r === null);\n        if (!hasRoom) {\n            registerWatcher();\n        } else {\n            if (roomId === null) {\n                // Unregister all existing watchers and register the new one\n                rooms.forEach((roomId) => {\n                    SettingsStore.unwatchSetting(this.monitors.get(settingName)!.get(roomId)!);\n                });\n                this.monitors.get(settingName)!.clear();\n                registerWatcher();\n            } // else a watcher is already registered for the room, so don't bother registering it again\n        }\n    }\n\n    /**\n     * Gets the translated display name for a given setting\n     * @param {string} settingName The setting to look up.\n     * @param {SettingLevel} atLevel\n     * The level to get the display name for; Defaults to 'default'.\n     * @return {String} The display name for the setting, or null if not found.\n     */\n    public static getDisplayName(settingName: SettingKey, atLevel = SettingLevel.DEFAULT): string | null {\n        if (!SETTINGS[settingName] || !SETTINGS[settingName].displayName) return null;\n\n        const displayName = SETTINGS[settingName].displayName;\n\n        if (typeof displayName === \"string\") {\n            return _t(displayName);\n        }\n        if (displayName?.[atLevel]) {\n            return _t(displayName[atLevel]);\n        }\n        if (displayName?.[\"default\"]) {\n            return _t(displayName[\"default\"]);\n        }\n\n        return null;\n    }\n\n    /**\n     * Gets the translated description for a given setting\n     * @param {string} settingName The setting to look up.\n     * @return {String} The description for the setting, or null if not found.\n     */\n    public static getDescription(settingName: SettingKey): string | ReactNode {\n        const description = SETTINGS[settingName]?.description;\n        if (!description) return null;\n        if (typeof description !== \"string\") return description();\n        return _t(description);\n    }\n\n    /**\n     * Determines if a setting is also a feature.\n     * @param {string} settingName The setting to look up.\n     * @return {boolean} True if the setting is a feature.\n     */\n    public static isFeature(settingName: SettingKey): boolean {\n        if (!SETTINGS[settingName]) return false;\n        return !!SETTINGS[settingName].isFeature;\n    }\n\n    /**\n     * Determines if a setting should have a warning sign in the microcopy\n     * @param {string} settingName The setting to look up.\n     * @return {boolean} True if the setting should have a warning sign.\n     */\n    public static shouldHaveWarning(settingName: SettingKey): boolean {\n        if (!SETTINGS[settingName]) return false;\n        return SETTINGS[settingName].shouldWarn ?? false;\n    }\n\n    public static getBetaInfo(settingName: SettingKey): ISetting[\"betaInfo\"] {\n        // consider a beta disabled if the config is explicitly set to false, in which case treat as normal Labs flag\n        if (\n            SettingsStore.isFeature(settingName) &&\n            SettingsStore.getValueAt(SettingLevel.CONFIG, settingName, null, true, true) !== false\n        ) {\n            const betaInfo = SETTINGS[settingName]!.betaInfo;\n            if (betaInfo) {\n                betaInfo.requiresRefresh =\n                    betaInfo.requiresRefresh ?? SETTINGS[settingName]!.controller instanceof ReloadOnChangeController;\n            }\n            return betaInfo;\n        }\n    }\n\n    public static getLabGroup(settingName: SettingKey): LabGroup | undefined {\n        if (SettingsStore.isFeature(settingName)) {\n            return (<IFeature>SETTINGS[settingName]).labsGroup;\n        }\n    }\n\n    /**\n     * Retrieves the internationalised reason a setting is disabled if one is assigned.\n     * If a setting is not disabled, or no reason is given by the `SettingController`,\n     * this will return undefined.\n     * @param {string} settingName The setting to look up.\n     * @return {string} The reason the setting is disabled.\n     */\n    public static disabledMessage(settingName: SettingKey): string | undefined {\n        const disabled = SETTINGS[settingName].controller?.settingDisabled;\n        return typeof disabled === \"string\" ? disabled : undefined;\n    }\n\n    /**\n     * Gets the value of a setting. The room ID is optional if the setting is not to\n     * be applied to any particular room, otherwise it should be supplied.\n     * @param {string} settingName The name of the setting to read the value of.\n     * @param {String} roomId The room ID to read the setting value in, may be null.\n     * @param {boolean} excludeDefault True to disable using the default value.\n     * @return {*} The value, or null if not found\n     */\n    public static getValue<S extends SettingKey>(\n        settingName: S,\n        roomId: string | null,\n        excludeDefault: true,\n    ): Settings[S][\"default\"] | undefined;\n    public static getValue<S extends SettingKey>(\n        settingName: S,\n        roomId?: string | null,\n        excludeDefault?: false,\n    ): Settings[S][\"default\"];\n    public static getValue<S extends SettingKey>(\n        settingName: S,\n        roomId: string | null = null,\n        excludeDefault = false,\n    ): Settings[S][\"default\"] | undefined {\n        // Verify that the setting is actually a setting\n        if (!SETTINGS[settingName]) {\n            throw new Error(\"Setting '\" + settingName + \"' does not appear to be a setting.\");\n        }\n\n        const setting = SETTINGS[settingName];\n        const levelOrder = getLevelOrder(setting);\n\n        return SettingsStore.getValueAt(levelOrder[0], settingName, roomId, false, excludeDefault);\n    }\n\n    /**\n     * Gets a setting's value at a particular level, ignoring all levels that are more specific.\n     * @param {SettingLevel|\"config\"|\"default\"} level The\n     * level to look at.\n     * @param {string} settingName The name of the setting to read.\n     * @param {String} roomId The room ID to read the setting value in, may be null.\n     * @param {boolean} explicit If true, this method will not consider other levels, just the one\n     * provided. Defaults to false.\n     * @param {boolean} excludeDefault True to disable using the default value.\n     * @return {*} The value, or null if not found.\n     */\n    public static getValueAt<S extends SettingKey>(\n        level: SettingLevel,\n        settingName: S,\n        roomId: string | null = null,\n        explicit = false,\n        excludeDefault = false,\n    ): Settings[S][\"default\"] {\n        // Verify that the setting is actually a setting\n        const setting = SETTINGS[settingName];\n        if (!setting) {\n            throw new Error(\"Setting '\" + settingName + \"' does not appear to be a setting.\");\n        }\n\n        const levelOrder = getLevelOrder(setting);\n        if (!levelOrder.includes(SettingLevel.DEFAULT)) levelOrder.push(SettingLevel.DEFAULT); // always include default\n\n        const minIndex = levelOrder.indexOf(level);\n        if (minIndex === -1) throw new Error(`Level \"${level}\" for setting \"${settingName}\" is not prioritized`);\n\n        const handlers = SettingsStore.getHandlers(settingName);\n\n        // Check if we need to invert the setting at all. Do this after we get the setting\n        // handlers though, otherwise we'll fail to read the value.\n        let finalSettingName: string = settingName;\n        if (setting.invertedSettingName) {\n            //console.warn(`Inverting ${settingName} to be ${setting.invertedSettingName} - legacy setting`);\n            finalSettingName = setting.invertedSettingName;\n        }\n\n        if (explicit) {\n            const handler = handlers[level];\n            if (!handler) {\n                return SettingsStore.getFinalValue(setting, level, roomId, null, null);\n            }\n            const value = handler.getValue(finalSettingName, roomId);\n            return SettingsStore.getFinalValue(setting, level, roomId, value, level);\n        }\n\n        for (let i = minIndex; i < levelOrder.length; i++) {\n            const handler = handlers[levelOrder[i]];\n            if (!handler) continue;\n            if (excludeDefault && levelOrder[i] === \"default\") continue;\n\n            const value = handler.getValue(finalSettingName, roomId);\n            if (value === null || value === undefined) continue;\n            return SettingsStore.getFinalValue(setting, level, roomId, value, levelOrder[i]);\n        }\n\n        return SettingsStore.getFinalValue(setting, level, roomId, null, null);\n    }\n\n    /**\n     * Gets the default value of a setting.\n     * @param {string} settingName The name of the setting to read the value of.\n     * @param {String} roomId The room ID to read the setting value in, may be null.\n     * @return {*} The default value\n     */\n    public static getDefaultValue(settingName: SettingKey): any {\n        // Verify that the setting is actually a setting\n        if (!SETTINGS[settingName]) {\n            throw new Error(\"Setting '\" + settingName + \"' does not appear to be a setting.\");\n        }\n\n        return SETTINGS[settingName].default;\n    }\n\n    private static getFinalValue(\n        setting: ISetting,\n        level: SettingLevel,\n        roomId: string | null,\n        calculatedValue: any,\n        calculatedAtLevel: SettingLevel | null,\n    ): any {\n        let resultingValue = calculatedValue;\n\n        if (setting.controller) {\n            const actualValue = setting.controller.getValueOverride(level, roomId, calculatedValue, calculatedAtLevel);\n            if (actualValue !== undefined && actualValue !== null) resultingValue = actualValue;\n        }\n\n        if (setting.invertedSettingName) resultingValue = !resultingValue;\n        return resultingValue;\n    }\n\n    /* eslint-disable valid-jsdoc */ //https://github.com/eslint/eslint/issues/7307\n    /**\n     * Sets the value for a setting. The room ID is optional if the setting is not being\n     * set for a particular room, otherwise it should be supplied. The value may be null\n     * to indicate that the level should no longer have an override.\n     * @param {string} settingName The name of the setting to change.\n     * @param {String} roomId The room ID to change the value in, may be null.\n     * @param {SettingLevel} level The level\n     * to change the value at.\n     * @param {*} value The new value of the setting, may be null.\n     * @return {Promise} Resolves when the setting has been changed.\n     */\n\n    /* eslint-enable valid-jsdoc */\n    public static async setValue(\n        settingName: SettingKey,\n        roomId: string | null,\n        level: SettingLevel,\n        value: any,\n    ): Promise<void> {\n        // Verify that the setting is actually a setting\n        const setting = SETTINGS[settingName];\n        if (!setting) {\n            throw new Error(\"Setting '\" + settingName + \"' does not appear to be a setting.\");\n        }\n\n        const handler = SettingsStore.getHandler(settingName, level);\n        if (!handler) {\n            throw new Error(\"Setting \" + settingName + \" does not have a handler for \" + level);\n        }\n\n        let finalSettingName: string = settingName;\n        if (setting.invertedSettingName) {\n            // Note: We can't do this when the `level` is \"default\", however we also\n            // know that the user can't possible change the default value through this\n            // function so we don't bother checking it.\n            //console.warn(`Inverting ${settingName} to be ${setting.invertedSettingName} - legacy setting`);\n            finalSettingName = setting.invertedSettingName;\n            value = !value;\n        }\n\n        if (!handler.canSetValue(finalSettingName, roomId)) {\n            throw new Error(\"User cannot set \" + finalSettingName + \" at \" + level + \" in \" + roomId);\n        }\n\n        if (setting.controller && !(await setting.controller.beforeChange(level, roomId, value))) {\n            return; // controller says no\n        }\n\n        await handler.setValue(finalSettingName, roomId, value);\n\n        setting.controller?.onChange(level, roomId, value);\n    }\n\n    /**\n     * Determines if the current user is permitted to set the given setting at the given\n     * level for a particular room. The room ID is optional if the setting is not being\n     * set for a particular room, otherwise it should be supplied.\n     *\n     * This takes into account both the value of {@link SettingController#settingDisabled} of the\n     * `SettingController`, if any; and, for settings where {@link IBaseSetting#supportedLevelsAreOrdered} is true,\n     * checks whether a level of higher precedence is set.\n     *\n     * Typically, if the user cannot set the setting, it should be hidden, to declutter the UI;\n     * however some settings (typically, the labs flags) are exposed but greyed out, to unveil\n     * what features are available with the right server support.\n     *\n     * @param {string} settingName The name of the setting to check.\n     * @param {String} roomId The room ID to check in, may be null.\n     * @param {SettingLevel} level The level to check at.\n     * @return {boolean} True if the user may set the setting, false otherwise.\n     */\n    public static canSetValue(settingName: SettingKey, roomId: string | null, level: SettingLevel): boolean {\n        const setting = SETTINGS[settingName];\n        // Verify that the setting is actually a setting\n        if (!setting) {\n            throw new Error(\"Setting '\" + settingName + \"' does not appear to be a setting.\");\n        }\n\n        if (setting.controller?.settingDisabled) {\n            return false;\n        }\n\n        // For some config settings (mostly: non-beta features), a value in config.json overrides the local setting\n        // (ie: we force them as enabled or disabled). In this case we should not let the user change the setting.\n        if (\n            setting?.supportedLevelsAreOrdered &&\n            SettingsStore.settingIsOveriddenAtConfigLevel(settingName, roomId, level)\n        ) {\n            return false;\n        }\n\n        const handler = SettingsStore.getHandler(settingName, level);\n        if (!handler) return false;\n        return handler.canSetValue(settingName, roomId);\n    }\n\n    /**\n     * Determines if the setting at the specified level is overidden by one at a config level.\n     * @param settingName The name of the setting to check.\n     * @param roomId The room ID to check in, may be null.\n     * @param level The level to check at.\n     * @returns\n     */\n    public static settingIsOveriddenAtConfigLevel(\n        settingName: SettingKey,\n        roomId: string | null,\n        level: SettingLevel,\n    ): boolean {\n        const setting = SETTINGS[settingName];\n        const levelOrders = getLevelOrder(setting);\n        const configIndex = levelOrders.indexOf(SettingLevel.CONFIG);\n        const levelIndex = levelOrders.indexOf(level);\n        if (configIndex === -1 || levelIndex === -1 || configIndex >= levelIndex) {\n            return false;\n        }\n        const configVal = SettingsStore.getValueAt(SettingLevel.CONFIG, settingName, roomId, true, true);\n        return configVal === true || configVal === false;\n    }\n\n    /**\n     * Determines if the given level is supported on this device.\n     * @param {SettingLevel} level The level\n     * to check the feasibility of.\n     * @return {boolean} True if the level is supported, false otherwise.\n     */\n    public static isLevelSupported(level: SettingLevel): boolean {\n        if (!LEVEL_HANDLERS[level]) return false;\n        return LEVEL_HANDLERS[level].isSupported();\n    }\n\n    /**\n     * Determines if a setting supports a particular level.\n     * @param settingName The setting name.\n     * @param level The level.\n     * @returns True if supported, false otherwise. Note that this will not check to see if\n     * the level itself can be supported by the runtime (ie: you will need to call #isLevelSupported()\n     * on your own).\n     */\n    public static doesSettingSupportLevel(settingName: SettingKey, level: SettingLevel): boolean {\n        const setting = SETTINGS[settingName];\n        if (!setting) {\n            throw new Error(\"Setting '\" + settingName + \"' does not appear to be a setting.\");\n        }\n\n        return level === SettingLevel.DEFAULT || !!setting.supportedLevels?.includes(level);\n    }\n\n    /**\n     * Determines the first supported level out of all the levels that can be used for a\n     * specific setting.\n     * @param {string} settingName The setting name.\n     * @return {SettingLevel}\n     */\n    public static firstSupportedLevel(settingName: SettingKey): SettingLevel | null {\n        // Verify that the setting is actually a setting\n        const setting = SETTINGS[settingName];\n        if (!setting) {\n            throw new Error(\"Setting '\" + settingName + \"' does not appear to be a setting.\");\n        }\n\n        const levelOrder = getLevelOrder(setting);\n        if (!levelOrder.includes(SettingLevel.DEFAULT)) levelOrder.push(SettingLevel.DEFAULT); // always include default\n\n        const handlers = SettingsStore.getHandlers(settingName);\n\n        for (const level of levelOrder) {\n            const handler = handlers[level];\n            if (!handler) continue;\n            return level;\n        }\n        return null;\n    }\n\n    /**\n     * Migrate the setting for URL previews in e2e rooms from room account\n     * data to the room device level.\n     *\n     * @param isFreshLogin True if the user has just logged in, false if a previous session is being restored.\n     */\n    private static async migrateURLPreviewsE2EE(isFreshLogin: boolean): Promise<void> {\n        const MIGRATION_DONE_FLAG = \"url_previews_e2ee_migration_done\";\n        if (localStorage.getItem(MIGRATION_DONE_FLAG)) return;\n        if (isFreshLogin) return;\n\n        const client = MatrixClientPeg.safeGet();\n\n        while (!client.isInitialSyncComplete()) {\n            await new Promise((r) => client.once(ClientEvent.Sync, r));\n        }\n\n        logger.info(\"Performing one-time settings migration of URL previews in E2EE rooms\");\n\n        const roomAccounthandler = LEVEL_HANDLERS[SettingLevel.ROOM_ACCOUNT];\n\n        for (const room of client.getRooms()) {\n            // We need to use the handler directly because this setting is no longer supported\n            // at this level at all\n            const val = roomAccounthandler.getValue(\"urlPreviewsEnabled_e2ee\", room.roomId);\n\n            if (val !== undefined) {\n                await SettingsStore.setValue(\"urlPreviewsEnabled_e2ee\", room.roomId, SettingLevel.ROOM_DEVICE, val);\n            }\n        }\n\n        localStorage.setItem(MIGRATION_DONE_FLAG, \"true\");\n    }\n\n    /**\n     * Migrate the setting for visible images to a setting.\n     */\n    private static migrateShowImagesToSettings(): void {\n        const MIGRATION_DONE_FLAG = \"mx_show_images_migration_done\";\n        if (localStorage.getItem(MIGRATION_DONE_FLAG)) return;\n\n        logger.info(\"Performing one-time settings migration of shown images to settings store\");\n        const newValue = Object.fromEntries(\n            Object.keys(localStorage)\n                .filter((k) => k.startsWith(\"mx_ShowImage_\"))\n                .map((k) => [k.slice(\"mx_ShowImage_\".length), true]),\n        );\n        this.setValue(\"showMediaEventIds\", null, SettingLevel.DEVICE, newValue);\n\n        localStorage.setItem(MIGRATION_DONE_FLAG, \"true\");\n    }\n\n    /**\n     * Migrate the setting for visible images to a setting.\n     *\n     * @param isFreshLogin True if the user has just logged in, false if a previous session is being restored.\n     */\n    private static async migrateMediaControlsToSetting(isFreshLogin: boolean): Promise<void> {\n        if (isFreshLogin) return;\n        const client = MatrixClientPeg.safeGet();\n\n        while (!client.isInitialSyncComplete()) {\n            await new Promise((r) => client.once(ClientEvent.Sync, r));\n        }\n        // Never migrate if the config already exists.\n        if (client.getAccountData(\"io.element.msc4278.media_preview_config\")) {\n            return;\n        }\n        logger.info(\"Performing one-time settings migration of show images and invite avatars to account data\");\n        const handler = LEVEL_HANDLERS[SettingLevel.ACCOUNT];\n        const showImages = handler.getValue(\"showImages\", null);\n        const showAvatarsOnInvites = handler.getValue(\"showAvatarsOnInvites\", null);\n\n        if (typeof showImages === \"boolean\" || typeof showAvatarsOnInvites === \"boolean\") {\n            this.setValue(\"mediaPreviewConfig\", null, SettingLevel.ACCOUNT, {\n                invite_avatars: showAvatarsOnInvites === false ? MediaPreviewValue.Off : MediaPreviewValue.On,\n                media_previews: showImages === false ? MediaPreviewValue.Off : MediaPreviewValue.On,\n            });\n        } // else, we don't set anything and use the server value\n    }\n\n    /**\n     * Runs or queues any setting migrations needed.\n     */\n    public static runMigrations(isFreshLogin: boolean): void {\n        // This can be removed once enough users have run a version of Element with\n        // this migration. A couple of months after its release should be sufficient\n        // (so around October 2024).\n        // The consequences of missing the migration are only that URL previews will\n        // be disabled in E2EE rooms.\n        SettingsStore.migrateURLPreviewsE2EE(isFreshLogin).catch((e) => {\n            logger.error(\"Failed to migrate URL previews in E2EE rooms:\", e);\n        });\n\n        // This can be removed once enough users have run a version of Element with\n        // this migration.\n        // The consequences of missing the migration are that previously shown images\n        // will now be hidden again, so this fails safely.\n        SettingsStore.migrateShowImagesToSettings();\n\n        // This can be removed once enough users have run a version of Element with\n        // this migration.\n        // The consequences of missing the migration are that the previously set\n        // media controls for this user will be missing\n        SettingsStore.migrateMediaControlsToSetting(isFreshLogin).catch((e) => {\n            logger.error(\"Failed to migrate media config settings\", e);\n        });\n        // Dev notes: to add your migration, just add a new `migrateMyFeature` function, call it, and\n        // add a comment to note when it can be removed.\n        return;\n    }\n\n    /**\n     * Debugging function for reading explicit setting values without going through the\n     * complicated/biased functions in the SettingsStore. This will print information to\n     * the console for analysis. Not intended to be used within the application.\n     * @param {string} realSettingName The setting name to try and read.\n     * @param {string} roomId Optional room ID to test the setting in.\n     */\n    public static debugSetting(realSettingName: SettingKey, roomId: string): void {\n        logger.log(`--- DEBUG ${realSettingName}`);\n\n        // Note: we intentionally use JSON.stringify here to avoid the console masking the\n        // problem if there's a type representation issue. Also, this way it is guaranteed\n        // to show up in a rageshake if required.\n\n        const def = SETTINGS[realSettingName];\n        logger.log(`--- definition: ${def ? JSON.stringify(def) : \"<NOT_FOUND>\"}`);\n        logger.log(`--- default level order: ${JSON.stringify(LEVEL_ORDER)}`);\n        logger.log(`--- registered handlers: ${JSON.stringify(Object.keys(LEVEL_HANDLERS))}`);\n\n        const doChecks = (settingName: SettingKey): void => {\n            for (const handlerName of Object.keys(LEVEL_HANDLERS)) {\n                const handler = LEVEL_HANDLERS[handlerName as SettingLevel];\n\n                try {\n                    const value = handler.getValue(settingName, roomId);\n                    logger.log(`---     ${handlerName}@${roomId || \"<no_room>\"} = ${JSON.stringify(value)}`);\n                } catch (e) {\n                    logger.log(\n                        `---     ${handler.constructor.name}@${roomId || \"<no_room>\"} THREW ERROR: ${\n                            e instanceof Error ? e.message : e\n                        }`,\n                    );\n                    logger.error(e);\n                }\n\n                if (roomId) {\n                    try {\n                        const value = handler.getValue(settingName, null);\n                        logger.log(`---     ${handlerName}@<no_room> = ${JSON.stringify(value)}`);\n                    } catch (e) {\n                        logger.log(\n                            `---     ${handler.constructor.name}@<no_room> THREW ERROR: ${\n                                e instanceof Error ? e.message : e\n                            }`,\n                        );\n                        logger.error(e);\n                    }\n                }\n            }\n\n            logger.log(`--- calculating as returned by SettingsStore`);\n            logger.log(`--- these might not match if the setting uses a controller - be warned!`);\n\n            try {\n                const value = SettingsStore.getValue(settingName, roomId);\n                logger.log(`---     SettingsStore#generic@${roomId || \"<no_room>\"}  = ${JSON.stringify(value)}`);\n            } catch (e) {\n                logger.log(\n                    `---     SettingsStore#generic@${roomId || \"<no_room>\"} THREW ERROR: ${\n                        e instanceof Error ? e.message : e\n                    }`,\n                );\n                logger.error(e);\n            }\n\n            if (roomId) {\n                try {\n                    const value = SettingsStore.getValue(settingName, null);\n                    logger.log(`---     SettingsStore#generic@<no_room>  = ${JSON.stringify(value)}`);\n                } catch (e) {\n                    logger.log(\n                        `---     SettingsStore#generic@$<no_room> THREW ERROR: ${e instanceof Error ? e.message : e}`,\n                    );\n                    logger.error(e);\n                }\n            }\n\n            for (const level of LEVEL_ORDER) {\n                try {\n                    const value = SettingsStore.getValueAt(level, settingName, roomId);\n                    logger.log(`---     SettingsStore#${level}@${roomId || \"<no_room>\"} = ${JSON.stringify(value)}`);\n                } catch (e) {\n                    logger.log(\n                        `---     SettingsStore#${level}@${roomId || \"<no_room>\"} THREW ERROR: ${\n                            e instanceof Error ? e.message : e\n                        }`,\n                    );\n                    logger.error(e);\n                }\n\n                if (roomId) {\n                    try {\n                        const value = SettingsStore.getValueAt(level, settingName, null);\n                        logger.log(`---     SettingsStore#${level}@<no_room> = ${JSON.stringify(value)}`);\n                    } catch (e) {\n                        logger.log(\n                            `---     SettingsStore#${level}@$<no_room> THREW ERROR: ${\n                                e instanceof Error ? e.message : e\n                            }`,\n                        );\n                        logger.error(e);\n                    }\n                }\n            }\n        };\n\n        doChecks(realSettingName);\n\n        if (def.invertedSettingName) {\n            logger.log(`--- TESTING INVERTED SETTING NAME`);\n            logger.log(`--- inverted: ${def.invertedSettingName}`);\n            doChecks(def.invertedSettingName as SettingKey);\n        }\n\n        logger.log(`--- END DEBUG`);\n    }\n\n    /**\n     * Export all settings as a JSON object, except for settings\n     * blocked from being exported by `shouldExportToRageshake`.\n     * @returns Settings as a JSON object string.\n     */\n    public static exportForRageshake(): string {\n        const settingMap: Record<string, unknown> = {};\n        for (const settingKey of (Object.keys(SETTINGS) as SettingKey[]).filter(\n            (s) => SETTINGS[s].shouldExportToRageshake !== false,\n        )) {\n            try {\n                settingMap[settingKey] = SettingsStore.getValue(settingKey);\n            } catch (e) {\n                logger.warn(\"Failed to read setting\", settingKey, e);\n                settingMap[settingKey] = \"Failed to read setting!\";\n            }\n        }\n        return JSON.stringify(settingMap);\n    }\n\n    private static getHandler(settingName: SettingKey, level: SettingLevel): SettingsHandler | null {\n        const handlers = SettingsStore.getHandlers(settingName);\n        if (!handlers[level]) return null;\n        return handlers[level]!;\n    }\n\n    private static getHandlers(settingName: SettingKey): HandlerMap {\n        if (!SETTINGS[settingName]) return {};\n\n        const handlers: Partial<Record<SettingLevel, SettingsHandler>> = {};\n        for (const level of SETTINGS[settingName].supportedLevels) {\n            if (!LEVEL_HANDLERS[level]) throw new Error(\"Unexpected level \" + level);\n            if (SettingsStore.isLevelSupported(level)) handlers[level] = LEVEL_HANDLERS[level];\n        }\n\n        // Always support 'default'\n        if (!handlers[\"default\"]) handlers[\"default\"] = LEVEL_HANDLERS[\"default\"];\n\n        return handlers;\n    }\n}\n\n// For debugging purposes\nwindow.mxSettingsStore = SettingsStore;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2022 The Matrix.org Foundation C.I.C.\nCopyright 2019 New Vector Ltd.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { SettingLevel } from \"../SettingLevel\";\nimport { type CallbackFn, type WatchManager } from \"../WatchManager\";\nimport AbstractLocalStorageSettingsHandler from \"./AbstractLocalStorageSettingsHandler\";\n\n/**\n * Gets and sets settings at the \"device\" level for the current device.\n * This handler does not make use of the roomId parameter. This handler\n * will special-case features to support legacy settings.\n */\nexport default class DeviceSettingsHandler extends AbstractLocalStorageSettingsHandler {\n    /**\n     * Creates a new device settings handler\n     * @param {string[]} featureNames The names of known features.\n     * @param {WatchManager} watchers The watch manager to notify updates to\n     */\n    public constructor(\n        private featureNames: string[],\n        public readonly watchers: WatchManager,\n    ) {\n        super();\n    }\n\n    public getValue(settingName: string, roomId: string): any {\n        if (this.featureNames.includes(settingName)) {\n            return this.readFeature(settingName);\n        }\n\n        // Special case notifications\n        if (settingName === \"notificationsEnabled\") {\n            return this.getBoolean(\"notifications_enabled\");\n        } else if (settingName === \"notificationBodyEnabled\") {\n            return this.getBoolean(\"notifications_body_enabled\");\n        } else if (settingName === \"audioNotificationsEnabled\") {\n            return this.getBoolean(\"audio_notifications_enabled\");\n        }\n\n        const settings = this.getSettings() || {};\n        return settings[settingName];\n    }\n\n    public setValue(settingName: string, roomId: string, newValue: any): Promise<void> {\n        if (this.featureNames.includes(settingName)) {\n            this.writeFeature(settingName, newValue);\n            return Promise.resolve();\n        }\n\n        // Special case notifications\n        if (settingName === \"notificationsEnabled\") {\n            this.setBoolean(\"notifications_enabled\", newValue);\n            this.watchers.notifyUpdate(settingName, null, SettingLevel.DEVICE, newValue);\n            return Promise.resolve();\n        } else if (settingName === \"notificationBodyEnabled\") {\n            this.setBoolean(\"notifications_body_enabled\", newValue);\n            this.watchers.notifyUpdate(settingName, null, SettingLevel.DEVICE, newValue);\n            return Promise.resolve();\n        } else if (settingName === \"audioNotificationsEnabled\") {\n            this.setBoolean(\"audio_notifications_enabled\", newValue);\n            this.watchers.notifyUpdate(settingName, null, SettingLevel.DEVICE, newValue);\n            return Promise.resolve();\n        }\n\n        // Special case for old useIRCLayout setting\n        if (settingName === \"layout\") {\n            const settings = this.getSettings() || {};\n\n            delete settings[\"useIRCLayout\"];\n            settings[\"layout\"] = newValue;\n            this.setObject(\"mx_local_settings\", settings);\n\n            this.watchers.notifyUpdate(settingName, null, SettingLevel.DEVICE, newValue);\n            return Promise.resolve();\n        }\n\n        const settings = this.getSettings() || {};\n        settings[settingName] = newValue;\n        this.setObject(\"mx_local_settings\", settings);\n        this.watchers.notifyUpdate(settingName, null, SettingLevel.DEVICE, newValue);\n\n        return Promise.resolve();\n    }\n\n    public canSetValue(settingName: string, roomId: string): boolean {\n        return true; // It's their device, so they should be able to\n    }\n\n    public watchSetting(settingName: string, roomId: string, cb: CallbackFn): void {\n        this.watchers.watchSetting(settingName, roomId, cb);\n    }\n\n    public unwatchSetting(cb: CallbackFn): void {\n        this.watchers.unwatchSetting(cb);\n    }\n\n    private getSettings(): any {\n        // TODO: [TS] Type return\n        return this.getObject(\"mx_local_settings\");\n    }\n\n    // Note: features intentionally don't use the same key as settings to avoid conflicts\n    // and to be backwards compatible.\n\n    // public for access to migrations - not exposed from the SettingsHandler interface\n    public readFeature(featureName: string): boolean | null {\n        // Previously, we disabled all features for guests, but since different\n        // installations can have site-specific config files which might set up\n        // different behaviour that is relevant to guests, we removed that\n        // special behaviour. See\n        // https://github.com/vector-im/element-web/issues/24513 for the\n        // discussion.\n\n        // XXX: This turns they key names into `mx_labs_feature_feature_x` (double feature).\n        // This is because all feature names start with `feature_` as a matter of policy.\n        // Oh well.\n        return this.getBoolean(\"mx_labs_feature_\" + featureName);\n    }\n\n    private writeFeature(featureName: string, enabled: boolean | null): void {\n        this.setBoolean(\"mx_labs_feature_\" + featureName, enabled);\n        this.watchers.notifyUpdate(featureName, null, SettingLevel.DEVICE, enabled);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 - 2022 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { safeSet } from \"matrix-js-sdk/src/utils\";\n\nimport { SettingLevel } from \"../SettingLevel\";\nimport { type WatchManager } from \"../WatchManager\";\nimport AbstractLocalStorageSettingsHandler from \"./AbstractLocalStorageSettingsHandler\";\n\n/**\n * Gets and sets settings at the \"room-device\" level for the current device in a particular\n * room.\n */\nexport default class RoomDeviceSettingsHandler extends AbstractLocalStorageSettingsHandler {\n    public constructor(public readonly watchers: WatchManager) {\n        super();\n    }\n\n    public getValue(settingName: string, roomId: string): any {\n        // Special case blacklist setting to use legacy values\n        if (settingName === \"blacklistUnverifiedDevices\") {\n            const value = this.read(\"mx_local_settings\");\n            if (value?.[\"blacklistUnverifiedDevicesPerRoom\"]) {\n                return value[\"blacklistUnverifiedDevicesPerRoom\"][roomId];\n            }\n        }\n\n        const value = this.read(this.getKey(settingName, roomId));\n        if (value) return value.value;\n        return null;\n    }\n\n    public setValue(settingName: string, roomId: string, newValue: any): Promise<void> {\n        // Special case blacklist setting for legacy structure\n        if (settingName === \"blacklistUnverifiedDevices\") {\n            let value = this.read(\"mx_local_settings\");\n            if (!value) value = {};\n            if (!value[\"blacklistUnverifiedDevicesPerRoom\"]) value[\"blacklistUnverifiedDevicesPerRoom\"] = {};\n            safeSet(value[\"blacklistUnverifiedDevicesPerRoom\"], roomId, newValue);\n            this.setObject(\"mx_local_settings\", value);\n            this.watchers.notifyUpdate(settingName, roomId, SettingLevel.ROOM_DEVICE, newValue);\n            return Promise.resolve();\n        }\n\n        if (newValue === null) {\n            this.removeItem(this.getKey(settingName, roomId));\n        } else {\n            this.setObject(this.getKey(settingName, roomId), { value: newValue });\n        }\n\n        this.watchers.notifyUpdate(settingName, roomId, SettingLevel.ROOM_DEVICE, newValue);\n        return Promise.resolve();\n    }\n\n    public canSetValue(settingName: string, roomId: string): boolean {\n        return true; // It's their device, so they should be able to\n    }\n\n    private read(key: string): any {\n        return this.getObject(key);\n    }\n\n    private getKey(settingName: string, roomId: string): string {\n        return \"mx_setting_\" + settingName + \"_\" + roomId;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// see settings.md for documentation on conventions\nexport const enum UIFeature {\n    AdvancedEncryption = \"UIFeature.advancedEncryption\",\n    URLPreviews = \"UIFeature.urlPreviews\",\n    Widgets = \"UIFeature.widgets\",\n    LocationSharing = \"UIFeature.locationSharing\",\n    Voip = \"UIFeature.voip\",\n    Feedback = \"UIFeature.feedback\",\n    Registration = \"UIFeature.registration\",\n    PasswordReset = \"UIFeature.passwordReset\",\n    Deactivate = \"UIFeature.deactivate\",\n    ShareQRCode = \"UIFeature.shareQrCode\",\n    ShareSocial = \"UIFeature.shareSocial\",\n    IdentityServer = \"UIFeature.identityServer\",\n    ThirdPartyID = \"UIFeature.thirdPartyId\",\n    AdvancedSettings = \"UIFeature.advancedSettings\",\n    RoomHistorySettings = \"UIFeature.roomHistorySettings\",\n    TimelineEnableRelativeDates = \"UIFeature.timelineEnableRelativeDates\",\n    AllowCreatingPublicRooms = \"UIFeature.allowCreatingPublicRooms\",\n    AllowCreatingPublicSpaces = \"UIFeature.allowCreatingPublicSpaces\",\n}\n\nexport enum UIComponent {\n    /**\n     * Components that lead to a user being invited.\n     */\n    InviteUsers = \"UIComponent.sendInvites\",\n\n    /**\n     * Components that lead to a room being created that aren't already\n     * guarded by some other condition (ie: \"only if you can edit this\n     * space\" is *not* guarded by this component, but \"start DM\" is).\n     */\n    CreateRooms = \"UIComponent.roomCreation\",\n\n    /**\n     * Components that lead to a Space being created that aren't already\n     * guarded by some other condition (ie: \"only if you can add subspaces\"\n     * is *not* guarded by this component, but \"create new space\" is).\n     */\n    CreateSpaces = \"UIComponent.spaceCreation\",\n\n    /**\n     * Components that lead to the public room directory.\n     */\n    ExploreRooms = \"UIComponent.exploreRooms\",\n\n    /**\n     * Components that lead to the user being able to easily add widgets\n     * and integrations to the room, such as from the room information card.\n     */\n    AddIntegrations = \"UIComponent.addIntegrations\",\n\n    /**\n     * Component that lead to the user being able to search, dial, explore rooms\n     */\n    FilterContainer = \"UIComponent.filterContainer\",\n\n    /**\n     * Components that lead the user to room options menu.\n     */\n    RoomOptionsMenu = \"UIComponent.roomOptionsMenu\",\n}\n","/*\nCopyright 2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { AllDevicesIsolationMode, OnlySignedDevicesIsolationMode } from \"matrix-js-sdk/src/crypto-api\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport SettingController from \"./SettingController\";\nimport { MatrixClientPeg } from \"../../MatrixClientPeg\";\nimport { type SettingLevel } from \"../SettingLevel\";\n\n/**\n * A controller for the \"exclude_insecure_devices\" setting, which will\n * update the crypto stack's device isolation mode on change.\n */\nexport default class DeviceIsolationModeController extends SettingController {\n    public onChange(level: SettingLevel, roomId: string, newValue: any): void {\n        setDeviceIsolationMode(MatrixClientPeg.safeGet(), newValue);\n    }\n}\n\n/**\n * Set the crypto stack's device isolation mode based on the current value of the\n * \"exclude_insecure_devices\" setting.\n *\n * @param client - MatrixClient to update to the new setting.\n * @param settingValue - value of the \"exclude_insecure_devices\" setting.\n */\nexport function setDeviceIsolationMode(client: MatrixClient, settingValue: boolean): void {\n    client.getCrypto()?.setDeviceIsolationMode(\n        settingValue\n            ? new OnlySignedDevicesIsolationMode()\n            : // TODO: As part of https://github.com/element-hq/element-meta/issues/2492, we will change\n              //   `errorOnVerifiedUserProblems` to `true`, but we need to have better UI in place before we can do so.\n              new AllDevicesIsolationMode(false),\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport SettingController from \"./SettingController\";\n\n// Dev note: This whole class exists in the event someone logs out and back in - we want\n// to make sure the right MatrixClient is listening for changes.\n\n/**\n * Represents the base class for settings controllers which need access to a MatrixClient.\n * This class performs no logic and should be overridden.\n */\nexport default abstract class MatrixClientBackedController extends SettingController {\n    private static _matrixClient?: MatrixClient;\n    private static instances: MatrixClientBackedController[] = [];\n\n    public static set matrixClient(client: MatrixClient) {\n        const oldClient = MatrixClientBackedController._matrixClient;\n        MatrixClientBackedController._matrixClient = client;\n\n        for (const instance of MatrixClientBackedController.instances) {\n            instance.initMatrixClient?.(client, oldClient);\n        }\n    }\n\n    protected constructor() {\n        super();\n\n        MatrixClientBackedController.instances.push(this);\n    }\n\n    public get client(): MatrixClient | undefined {\n        return MatrixClientBackedController._matrixClient;\n    }\n\n    protected initMatrixClient?(newClient: MatrixClient, oldClient?: MatrixClient): void;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { PushRuleActionName } from \"matrix-js-sdk/src/matrix\";\n\nimport SettingController from \"./SettingController\";\nimport { MatrixClientPeg } from \"../../MatrixClientPeg\";\nimport { type SettingLevel } from \"../SettingLevel\";\n\n// .m.rule.master being enabled means all events match that push rule\n// default action on this rule is dont_notify, but it could be something else\nexport function isPushNotifyDisabled(): boolean {\n    // Return the value of the master push rule as a default\n    const masterRule = MatrixClientPeg.get()?.pushProcessor.getPushRuleById(\".m.rule.master\");\n\n    if (!masterRule) {\n        logger.warn(\"No master push rule! Notifications are disabled for this user.\");\n        return true;\n    }\n\n    // If the rule is enabled then check it does not notify on everything\n    return masterRule.enabled && !masterRule.actions.includes(PushRuleActionName.Notify);\n}\n\nfunction getNotifier(): any {\n    // TODO: [TS] Formal type that doesn't cause a cyclical reference.\n    // eslint-disable-next-line @typescript-eslint/no-require-imports\n    let Notifier = require(\"../../Notifier\"); // avoids cyclical references\n    if (Notifier.default) Notifier = Notifier.default; // correct for webpack require() weirdness\n    return Notifier;\n}\n\nexport class NotificationsEnabledController extends SettingController {\n    public getValueOverride(\n        level: SettingLevel,\n        roomId: string,\n        calculatedValue: any,\n        calculatedAtLevel: SettingLevel | null,\n    ): any {\n        if (!getNotifier().isPossible()) return false;\n\n        if (calculatedValue === null || calculatedAtLevel === \"default\") {\n            return !isPushNotifyDisabled();\n        }\n\n        return calculatedValue;\n    }\n\n    public onChange(level: SettingLevel, roomId: string, newValue: any): void {\n        if (getNotifier().supportsDesktopNotifications()) {\n            getNotifier().setEnabled(newValue);\n        }\n    }\n}\n\nexport class NotificationBodyEnabledController extends SettingController {\n    public getValueOverride(level: SettingLevel, roomId: string, calculatedValue: any): any {\n        if (!getNotifier().isPossible()) return false;\n\n        if (calculatedValue === null) {\n            return !isPushNotifyDisabled();\n        }\n\n        return calculatedValue;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport SettingController from \"./SettingController\";\nimport PlatformPeg from \"../../PlatformPeg\";\nimport { type SettingLevel } from \"../SettingLevel\";\n\nexport default class ReloadOnChangeController extends SettingController {\n    public onChange(level: SettingLevel, roomId: string, newValue: any): void {\n        PlatformPeg.get()?.reload();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type SettingLevel } from \"../SettingLevel\";\n\n/**\n * Represents a controller for individual settings to alter the reading behaviour\n * based upon environmental conditions, or to react to changes and therefore update\n * the working environment.\n *\n * This is not intended to replace the functionality of a SettingsHandler, it is only\n * intended to handle environmental factors for specific settings.\n */\nexport default abstract class SettingController {\n    /**\n     * Gets the overridden value for the setting, if any. This must return null if the\n     * value is not to be overridden, otherwise it must return the new value.\n     * @param {string} level The level at which the value was requested at.\n     * @param {String} roomId The room ID, may be null.\n     * @param {*} calculatedValue The value that the handlers think the setting should be,\n     * may be null.\n     * @param {SettingLevel} calculatedAtLevel The level for which the calculated value was\n     * calculated at. May be null.\n     * @return {*} The value that should be used, or null if no override is applicable.\n     */\n    public getValueOverride(\n        level: SettingLevel,\n        roomId: string | null,\n        calculatedValue: any,\n        calculatedAtLevel: SettingLevel | null,\n    ): any {\n        return null; // no override\n    }\n\n    /**\n     * Called before the setting value has been changed, can abort the change.\n     * @param {string} level The level at which the setting has been modified.\n     * @param {String} roomId The room ID, may be null.\n     * @param {*} newValue The new value for the setting, may be null.\n     * @return {boolean} Whether the settings change should be accepted.\n     */\n    public async beforeChange(level: SettingLevel, roomId: string | null, newValue: any): Promise<boolean> {\n        return true;\n    }\n\n    /**\n     * Called when the setting value has been changed.\n     * @param {string} level The level at which the setting has been modified.\n     * @param {String} roomId The room ID, may be null.\n     * @param {*} newValue The new value for the setting, may be null.\n     */\n    public onChange(level: SettingLevel, roomId: string | null, newValue: any): void {\n        // do nothing by default\n    }\n\n    /**\n     * Gets whether the setting has been disabled due to this controller.\n     * Can also return a string with the reason the setting is disabled.\n     */\n    public get settingDisabled(): boolean | string {\n        return false;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// For Large the image gets drawn as big as possible.\n// constraint by: timeline width, manual height overrides, SIZE_LARGE.h\nconst SIZE_LARGE = { w: 800, h: 600 };\n// For Normal the image gets drawn to never exceed SIZE_NORMAL.w, SIZE_NORMAL.h\n// constraint by: timeline width, manual height overrides\nconst SIZE_NORMAL_LANDSCAPE = { w: 324, h: 324 }; // for w > h\nconst SIZE_NORMAL_PORTRAIT = { w: Math.ceil(324 * (9 / 16)), h: 324 }; // for h > w\n\ntype Dimensions = { w?: number; h?: number };\n\nexport enum ImageSize {\n    Normal = \"normal\",\n    Large = \"large\",\n}\n\n/**\n * @param {ImageSize} size The user's image size preference\n * @param {Dimensions} contentSize The natural dimensions of the content\n * @param {number} maxHeight Overrides the default height limit\n * @returns {Dimensions} The suggested maximum dimensions for the image\n */\nexport function suggestedSize(size: ImageSize, contentSize: Dimensions, maxHeight?: number): Required<Dimensions> {\n    const aspectRatio = contentSize.w! / contentSize.h!;\n    const portrait = aspectRatio < 1;\n\n    const maxSize = size === ImageSize.Large ? SIZE_LARGE : portrait ? SIZE_NORMAL_PORTRAIT : SIZE_NORMAL_LANDSCAPE;\n    if (!contentSize.w || !contentSize.h) {\n        return maxSize;\n    }\n\n    const constrainedSize = {\n        w: Math.min(maxSize.w, contentSize.w),\n        h: maxHeight ? Math.min(maxSize.h, contentSize.h, maxHeight) : Math.min(maxSize.h, contentSize.h),\n    };\n\n    if (constrainedSize.h * aspectRatio < constrainedSize.w) {\n        // Height dictates width\n        return { w: Math.floor(constrainedSize.h * aspectRatio), h: constrainedSize.h };\n    } else {\n        // Width dictates height\n        return { w: constrainedSize.w, h: Math.floor(constrainedSize.w / aspectRatio) };\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2021 Quirin Götz <codeworks@supercable.onl>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/* TODO: This should be later reworked into something more generic */\nexport enum Layout {\n    IRC = \"irc\",\n    Group = \"group\",\n    Bubble = \"bubble\",\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport SettingsHandler from \"./SettingsHandler\";\n\n// Dev note: This whole class exists in the event someone logs out and back in - we want\n// to make sure the right MatrixClient is listening for changes.\n\n/**\n * Represents the base class for settings handlers which need access to a MatrixClient.\n * This class performs no logic and should be overridden.\n */\nexport default abstract class MatrixClientBackedSettingsHandler extends SettingsHandler {\n    private static _matrixClient: MatrixClient;\n    private static instances: MatrixClientBackedSettingsHandler[] = [];\n\n    public static set matrixClient(client: MatrixClient) {\n        const oldClient = MatrixClientBackedSettingsHandler._matrixClient;\n        MatrixClientBackedSettingsHandler._matrixClient = client;\n\n        for (const instance of MatrixClientBackedSettingsHandler.instances) {\n            instance.initMatrixClient(oldClient, client);\n        }\n    }\n\n    protected constructor() {\n        super();\n\n        MatrixClientBackedSettingsHandler.instances.push(this);\n    }\n\n    public get client(): MatrixClient {\n        return MatrixClientBackedSettingsHandler._matrixClient;\n    }\n\n    protected abstract initMatrixClient(oldClient: MatrixClient, newClient: MatrixClient): void;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type WatchManager } from \"../WatchManager\";\n\n/**\n * Represents the base class for all level handlers. This class performs no logic\n * and should be overridden.\n */\nexport default abstract class SettingsHandler {\n    public readonly watchers?: WatchManager;\n\n    /**\n     * Gets the value for a particular setting at this level for a particular room.\n     * If no room is applicable, the roomId may be null. The roomId may not be\n     * applicable to this level and may be ignored by the handler.\n     * @param {string} settingName The name of the setting.\n     * @param {String} roomId The room ID to read from, may be null.\n     * @returns {*} The setting value, or null if not found.\n     */\n    public abstract getValue(settingName: string, roomId: string | null): any;\n\n    /**\n     * Sets the value for a particular setting at this level for a particular room.\n     * If no room is applicable, the roomId may be null. The roomId may not be\n     * applicable to this level and may be ignored by the handler. Setting a value\n     * to null will cause the level to remove the value. The current user should be\n     * able to set the value prior to calling this.\n     * @param {string} settingName The name of the setting to change.\n     * @param {String} roomId The room ID to set the value in, may be null.\n     * @param {*} newValue The new value for the setting, may be null.\n     * @returns {Promise} Resolves when the setting has been saved.\n     */\n    public abstract setValue(settingName: string, roomId: string | null, newValue: any): Promise<void>;\n\n    /**\n     * Determines if the current user is able to set the value of the given setting\n     * in the given room at this level.\n     * @param {string} settingName The name of the setting to check.\n     * @param {String} roomId The room ID to check in, may be null\n     * @returns {boolean} True if the setting can be set by the user, false otherwise.\n     */\n    public abstract canSetValue(settingName: string, roomId: string | null): boolean;\n\n    /**\n     * Determines if this level is supported on this device.\n     * @returns {boolean} True if this level is supported on the current device.\n     */\n    public abstract isSupported(): boolean;\n\n    /**\n     * Resets the handler, clearing any caches or other stored data. Called on user logout.\n     */\n    public reset(): void {}\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport dis from \"../../dispatcher/dispatcher\";\nimport SettingsStore from \"../SettingsStore\";\nimport type IWatcher from \"./Watcher\";\nimport { toPx } from \"../../utils/units\";\nimport { Action } from \"../../dispatcher/actions\";\nimport { SettingLevel } from \"../SettingLevel\";\nimport { type UpdateSystemFontPayload } from \"../../dispatcher/payloads/UpdateSystemFontPayload\";\nimport { type ActionPayload } from \"../../dispatcher/payloads\";\n\nexport class FontWatcher implements IWatcher {\n    /**\n     * This Compound value is using `100%` of the default browser font size.\n     * It allows EW to use the browser's default font size instead of a fixed value.\n     * All the Compound font size are using `rem`, they are relative to the root font size\n     * and therefore of the browser font size.\n     */\n    private static readonly DEFAULT_SIZE = \"var(--cpd-font-size-root)\";\n    /**\n     * Default delta added to the ${@link DEFAULT_SIZE}\n     */\n    public static readonly DEFAULT_DELTA = 0;\n\n    private dispatcherRef?: string;\n\n    public async start(): Promise<void> {\n        this.updateFont();\n        this.dispatcherRef = dis.register(this.onAction);\n        /**\n         * baseFontSize is an account level setting which is loaded after the initial\n         * sync. Hence why we can't do that in the `constructor`\n         */\n        await this.migrateBaseFontSize();\n    }\n\n    /**\n     * Migrate the base font size from the V1 and V2 version to the V3 version\n     * @private\n     */\n    private async migrateBaseFontSize(): Promise<void> {\n        await this.migrateBaseFontV1toFontSizeDelta();\n        await this.migrateBaseFontV2toFontSizeDelta();\n    }\n\n    /**\n     * Migrating from the V1 version of the base font size to the new delta system.\n     * The delta system is using the default browser font size as a base\n     * Everything will become slightly larger, and getting rid of the `SIZE_DIFF`\n     * weirdness for locally persisted values\n     * @private\n     */\n    private async migrateBaseFontV1toFontSizeDelta(): Promise<void> {\n        const legacyBaseFontSize = SettingsStore.getValue(\"baseFontSize\");\n        // No baseFontV1 found, nothing to migrate\n        if (!legacyBaseFontSize) return;\n\n        console.log(\n            \"Migrating base font size -> base font size V2 -> font size delta for Compound, current value\",\n            legacyBaseFontSize,\n        );\n\n        // Compute the V1 to V2 version before migrating to fontSizeDelta\n        const baseFontSizeV2 = this.computeBaseFontSizeV1toV2(legacyBaseFontSize);\n\n        // Compute the difference between the V2 and the fontSizeDelta\n        const delta = this.computeFontSizeDeltaFromV2BaseFontSize(baseFontSizeV2);\n\n        await SettingsStore.setValue(\"fontSizeDelta\", null, SettingLevel.DEVICE, delta);\n        await SettingsStore.setValue(\"baseFontSize\", null, SettingLevel.DEVICE, 0);\n        console.log(\"Migration complete, deleting legacy `baseFontSize`\");\n    }\n\n    /**\n     * Migrating from the V2 version of the base font size to the new delta system\n     * @private\n     */\n    private async migrateBaseFontV2toFontSizeDelta(): Promise<void> {\n        const legacyBaseFontV2Size = SettingsStore.getValue(\"baseFontSizeV2\");\n        // No baseFontV2 found, nothing to migrate\n        if (!legacyBaseFontV2Size) return;\n\n        console.log(\"Migrating base font size V2 for Compound, current value\", legacyBaseFontV2Size);\n\n        // Compute the difference between the V2 and the fontSizeDelta\n        const delta = this.computeFontSizeDeltaFromV2BaseFontSize(legacyBaseFontV2Size);\n\n        await SettingsStore.setValue(\"fontSizeDelta\", null, SettingLevel.DEVICE, delta);\n        await SettingsStore.setValue(\"baseFontSizeV2\", null, SettingLevel.DEVICE, 0);\n        console.log(\"Migration complete, deleting legacy `baseFontSizeV2`\");\n    }\n\n    /**\n     * Compute the V2 font size from the V1 font size\n     * @param legacyBaseFontSize\n     * @private\n     */\n    private computeBaseFontSizeV1toV2(legacyBaseFontSize: number): number {\n        // For some odd reason, the persisted value in user storage has an offset\n        // of 5 pixels for all values stored under `baseFontSize`\n        const LEGACY_SIZE_DIFF = 5;\n\n        // Compound uses a base font size of `16px`, whereas the old Element\n        // styles based their calculations off a `15px` root font size.\n        const ROOT_FONT_SIZE_INCREASE = 1;\n\n        // Compute the font size of the V2 version before migrating to V3\n        return legacyBaseFontSize + ROOT_FONT_SIZE_INCREASE + LEGACY_SIZE_DIFF;\n    }\n\n    /**\n     * Compute the difference between the V2 font size and the default browser font size\n     * @param legacyBaseFontV2Size\n     * @private\n     */\n    private computeFontSizeDeltaFromV2BaseFontSize(legacyBaseFontV2Size: number): number {\n        const browserDefaultFontSize = FontWatcher.getRootFontSize();\n\n        // Compute the difference between the V2 font size and the default browser font size\n        return legacyBaseFontV2Size - browserDefaultFontSize;\n    }\n\n    /**\n     * Get the root font size of the document\n     * Fallback to 16px if the value is not found\n     * @returns {number}\n     */\n    public static getRootFontSize(): number {\n        return parseInt(window.getComputedStyle(document.documentElement).getPropertyValue(\"font-size\"), 10) || 16;\n    }\n\n    /**\n     * Get the browser default font size\n     * @returns {number} the default font size of the browser\n     */\n    public static getBrowserDefaultFontSize(): number {\n        return this.getRootFontSize() - SettingsStore.getValue(\"fontSizeDelta\");\n    }\n\n    public stop(): void {\n        dis.unregister(this.dispatcherRef);\n    }\n\n    private updateFont(): void {\n        this.setRootFontSize(SettingsStore.getValue(\"fontSizeDelta\"));\n        this.setSystemFont({\n            useBundledEmojiFont: SettingsStore.getValue(\"useBundledEmojiFont\"),\n            useSystemFont: SettingsStore.getValue(\"useSystemFont\"),\n            font: SettingsStore.getValue(\"systemFont\"),\n        });\n    }\n\n    private onAction = (payload: ActionPayload): void => {\n        if (payload.action === Action.MigrateBaseFontSize) {\n            this.migrateBaseFontSize();\n        } else if (payload.action === Action.UpdateFontSizeDelta) {\n            this.setRootFontSize(payload.delta);\n        } else if (payload.action === Action.UpdateSystemFont) {\n            this.setSystemFont(payload as UpdateSystemFontPayload);\n        } else if (payload.action === Action.OnLoggedOut) {\n            // Clear font overrides when logging out\n            this.setRootFontSize(FontWatcher.DEFAULT_DELTA);\n            this.setSystemFont({\n                useBundledEmojiFont: false,\n                useSystemFont: false,\n                font: \"\",\n            });\n        } else if (payload.action === Action.OnLoggedIn) {\n            // Font size can be saved on the account, so grab value when logging in\n            this.updateFont();\n        }\n    };\n\n    /**\n     * Set the root font size of the document\n     * @param delta {number} the delta to add to the default font size\n     */\n    private setRootFontSize = async (delta: number): Promise<void> => {\n        // Add the delta to the browser default font size\n        document.querySelector<HTMLElement>(\":root\")!.style.fontSize =\n            `calc(${FontWatcher.DEFAULT_SIZE} + ${toPx(delta)})`;\n    };\n\n    public static readonly FONT_FAMILY_CUSTOM_PROPERTY = \"--cpd-font-family-sans\";\n    public static readonly EMOJI_FONT_FAMILY_CUSTOM_PROPERTY = \"--emoji-font-family\";\n    public static readonly BUNDLED_EMOJI_FONT = \"Twemoji\";\n\n    private setSystemFont = ({\n        useBundledEmojiFont,\n        useSystemFont,\n        font,\n    }: Pick<UpdateSystemFontPayload, \"useBundledEmojiFont\" | \"useSystemFont\" | \"font\">): void => {\n        if (useSystemFont) {\n            let fontString = font\n                .split(\",\")\n                .map((font) => {\n                    font = font.trim();\n                    if (!font.startsWith('\"') && !font.endsWith('\"')) {\n                        font = `\"${font}\"`;\n                    }\n                    return font;\n                })\n                .join(\",\");\n\n            if (useBundledEmojiFont) {\n                fontString += \", \" + FontWatcher.BUNDLED_EMOJI_FONT;\n            }\n\n            /**\n             * Overrides the default font family from Compound\n             * Make sure that fonts with spaces in their names get interpreted properly\n             */\n            document.body.style.setProperty(FontWatcher.FONT_FAMILY_CUSTOM_PROPERTY, fontString);\n        } else {\n            document.body.style.removeProperty(FontWatcher.FONT_FAMILY_CUSTOM_PROPERTY);\n\n            if (useBundledEmojiFont) {\n                document.body.style.setProperty(\n                    FontWatcher.EMOJI_FONT_FAMILY_CUSTOM_PROPERTY,\n                    FontWatcher.BUNDLED_EMOJI_FONT,\n                );\n            } else {\n                document.body.style.removeProperty(FontWatcher.EMOJI_FONT_FAMILY_CUSTOM_PROPERTY);\n            }\n        }\n    };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { TypedEventEmitter } from \"matrix-js-sdk/src/matrix\";\n\nimport SettingsStore from \"../SettingsStore\";\nimport dis from \"../../dispatcher/dispatcher\";\nimport { Action } from \"../../dispatcher/actions\";\nimport { findHighContrastTheme } from \"../../theme\";\nimport { type ActionPayload } from \"../../dispatcher/payloads\";\nimport { SettingLevel } from \"../SettingLevel\";\n\nexport enum ThemeWatcherEvent {\n    Change = \"change\",\n}\n\ninterface ThemeWatcherEventHandlerMap {\n    [ThemeWatcherEvent.Change]: (theme: string) => void;\n}\n\nexport default class ThemeWatcher extends TypedEventEmitter<ThemeWatcherEvent, ThemeWatcherEventHandlerMap> {\n    private themeWatchRef?: string;\n    private systemThemeWatchRef?: string;\n    private dispatcherRef?: string;\n\n    private preferDark: MediaQueryList;\n    private preferLight: MediaQueryList;\n    private preferHighContrast: MediaQueryList;\n\n    private currentTheme: string;\n\n    public constructor() {\n        super();\n        // we have both here as each may either match or not match, so by having both\n        // we can get the tristate of dark/light/unsupported\n        this.preferDark = (<any>global).matchMedia(\"(prefers-color-scheme: dark)\");\n        this.preferLight = (<any>global).matchMedia(\"(prefers-color-scheme: light)\");\n        this.preferHighContrast = (<any>global).matchMedia(\"(prefers-contrast: more)\");\n\n        this.currentTheme = this.getEffectiveTheme();\n    }\n\n    public start(): void {\n        this.themeWatchRef = SettingsStore.watchSetting(\"theme\", null, this.onChange);\n        this.systemThemeWatchRef = SettingsStore.watchSetting(\"use_system_theme\", null, this.onChange);\n        this.preferDark.addEventListener(\"change\", this.onChange);\n        this.preferLight.addEventListener(\"change\", this.onChange);\n        this.preferHighContrast.addEventListener(\"change\", this.onChange);\n        this.dispatcherRef = dis.register(this.onAction);\n    }\n\n    public stop(): void {\n        this.preferDark.removeEventListener(\"change\", this.onChange);\n        this.preferLight.removeEventListener(\"change\", this.onChange);\n        this.preferHighContrast.removeEventListener(\"change\", this.onChange);\n        SettingsStore.unwatchSetting(this.systemThemeWatchRef);\n        SettingsStore.unwatchSetting(this.themeWatchRef);\n        dis.unregister(this.dispatcherRef);\n    }\n\n    private onChange = (): void => {\n        this.recheck();\n    };\n\n    private onAction = (payload: ActionPayload): void => {\n        if (payload.action === Action.RecheckTheme) {\n            // XXX forceTheme\n            this.recheck(payload.forceTheme);\n        }\n    };\n\n    // XXX: forceTheme param added here as local echo appears to be unreliable\n    // https://github.com/vector-im/element-web/issues/11443\n    public recheck(forceTheme?: string): void {\n        const oldTheme = this.currentTheme;\n        this.currentTheme = forceTheme === undefined ? this.getEffectiveTheme() : forceTheme;\n        if (oldTheme !== this.currentTheme) this.emit(ThemeWatcherEvent.Change, this.currentTheme);\n    }\n\n    public getEffectiveTheme(): string {\n        // Dev note: Much of this logic is replicated in the AppearanceUserSettingsTab\n\n        // If the user has specifically enabled the system matching option (excluding default),\n        // then use that over anything else. We pick the lowest possible level for the setting\n        // to ensure the ordering otherwise works.\n        const systemThemeExplicit = SettingsStore.getValueAt(\n            SettingLevel.DEVICE,\n            \"use_system_theme\",\n            null,\n            false,\n            true,\n        );\n        if (systemThemeExplicit) {\n            logger.log(\"returning explicit system theme\");\n            const theme = this.themeBasedOnSystem();\n            if (theme) {\n                return theme;\n            }\n        }\n\n        // If the user has specifically enabled the theme (without the system matching option being\n        // enabled specifically and excluding the default), use that theme. We pick the lowest possible\n        // level for the setting to ensure the ordering otherwise works.\n        const themeExplicit = SettingsStore.getValueAt(SettingLevel.DEVICE, \"theme\", null, false, true);\n        if (themeExplicit) {\n            logger.log(\"returning explicit theme: \" + themeExplicit);\n            return themeExplicit;\n        }\n\n        // If the user hasn't really made a preference in either direction, assume the defaults of the\n        // settings and use those.\n        if (SettingsStore.getValue(\"use_system_theme\")) {\n            const theme = this.themeBasedOnSystem();\n            if (theme) {\n                return theme;\n            }\n        }\n        return SettingsStore.getValue(\"theme\");\n    }\n\n    private themeBasedOnSystem(): string | undefined {\n        let newTheme: string | undefined;\n        if (this.preferDark.matches) {\n            newTheme = \"dark\";\n        } else if (this.preferLight.matches) {\n            newTheme = \"light\";\n        }\n        if (newTheme && this.preferHighContrast.matches) {\n            const hcTheme = findHighContrastTheme(newTheme);\n            if (hcTheme) {\n                newTheme = hcTheme;\n            }\n        }\n        return newTheme;\n    }\n\n    public isSystemThemeSupported(): boolean {\n        return this.preferDark.matches || this.preferLight.matches;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n */\n\nimport { type MatrixEvent, EventType, RelationType, M_POLL_END } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport SettingsStore from \"./settings/SettingsStore\";\nimport { type IRoomState } from \"./components/structures/RoomView\";\nimport { type SettingKey } from \"./settings/Settings.tsx\";\n\ninterface IDiff {\n    isMemberEvent: boolean;\n    isJoin?: boolean;\n    isPart?: boolean;\n    isDisplaynameChange?: boolean;\n    isAvatarChange?: boolean;\n}\n\nfunction memberEventDiff(ev: MatrixEvent): IDiff {\n    const diff: IDiff = {\n        isMemberEvent: ev.getType() === EventType.RoomMember,\n    };\n\n    // If is not a Member Event then the other checks do not apply, so bail early.\n    if (!diff.isMemberEvent) return diff;\n\n    const content = ev.getContent();\n    const prevContent = ev.getPrevContent();\n\n    const isMembershipChanged = content.membership !== prevContent.membership;\n    diff.isJoin = isMembershipChanged && content.membership === KnownMembership.Join;\n    diff.isPart =\n        isMembershipChanged && content.membership === KnownMembership.Leave && ev.getStateKey() === ev.getSender();\n\n    const isJoinToJoin = !isMembershipChanged && content.membership === KnownMembership.Join;\n    diff.isDisplaynameChange = isJoinToJoin && content.displayname !== prevContent.displayname;\n    diff.isAvatarChange = isJoinToJoin && content.avatar_url !== prevContent.avatar_url;\n    return diff;\n}\n\n/**\n * Determines whether the given event should be hidden from timelines.\n * @param ev The event\n * @param ctx An optional RoomContext to pull cached settings values from to avoid\n *     hitting the settings store\n */\nexport default function shouldHideEvent(ev: MatrixEvent, ctx?: IRoomState): boolean {\n    // Hide all poll end events\n    if (M_POLL_END.matches(ev.getType())) return true;\n\n    // Accessing the settings store directly can be expensive if done frequently,\n    // so we should prefer using cached values if a RoomContext is available\n    const isEnabled = ctx\n        ? (name: keyof IRoomState) => ctx[name]\n        : (name: SettingKey) => SettingsStore.getValue(name, ev.getRoomId());\n\n    // Hide redacted events\n    // Deleted events with a thread are always shown regardless of user preference\n    // to make sure that a thread can be accessible even if the root message is deleted\n    if (ev.isRedacted() && !isEnabled(\"showRedactions\") && !ev.getThread()) return true;\n\n    // Hide replacement events since they update the original tile (if enabled)\n    if (ev.isRelation(RelationType.Replace)) return true;\n\n    const eventDiff = memberEventDiff(ev);\n\n    if (eventDiff.isMemberEvent) {\n        if ((eventDiff.isJoin || eventDiff.isPart) && !isEnabled(\"showJoinLeaves\")) return true;\n        if (eventDiff.isAvatarChange && !isEnabled(\"showAvatarChanges\")) return true;\n        if (eventDiff.isDisplaynameChange && !isEnabled(\"showDisplaynameChanges\")) return true;\n    }\n\n    return false;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { type Command, CommandCategories, Commands } from \"../../../slash-commands/SlashCommands\";\nimport InfoDialog from \"./InfoDialog\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\n\n/**\n * Props for {@link SlashCommandHelpDialog}\n * @param roomId - The room ID to check whether commands are enabled\n * @param onFinished - Callback called when the dialog is closed\n */\ninterface IProps {\n    roomId: string;\n    onFinished(): void;\n}\n\nconst SlashCommandHelpDialog: React.FC<IProps> = ({ roomId, onFinished }) => {\n    const categories: Record<string, Command[]> = {};\n    Commands.forEach((cmd) => {\n        if (!cmd.isEnabled(MatrixClientPeg.get(), roomId)) return;\n        if (!categories[cmd.category]) {\n            categories[cmd.category] = [];\n        }\n        categories[cmd.category].push(cmd);\n    });\n\n    const body = Object.values(CommandCategories)\n        .filter((c) => categories[c])\n        .map((category) => {\n            const rows = [\n                <tr key={\"_category_\" + category} className=\"mx_SlashCommandHelpDialog_headerRow\">\n                    <td colSpan={3}>\n                        <h2>{_t(category)}</h2>\n                    </td>\n                </tr>,\n            ];\n\n            categories[category].forEach((cmd) => {\n                rows.push(\n                    <tr key={cmd.command}>\n                        <td>\n                            <strong>{cmd.getCommand()}</strong>\n                        </td>\n                        <td>{cmd.args}</td>\n                        <td>{_t(cmd.description)}</td>\n                    </tr>,\n                );\n            });\n\n            return rows;\n        });\n\n    return (\n        <InfoDialog\n            className=\"mx_SlashCommandHelpDialog\"\n            title={_t(\"slash_command|help_dialog_title\")}\n            description={\n                <table>\n                    <tbody>{body}</tbody>\n                </table>\n            }\n            hasCloseButton={true}\n            onFinished={onFinished}\n        />\n    );\n};\n\nexport default SlashCommandHelpDialog;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2023 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EventType, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { SdkContextClass } from \"../contexts/SDKContext\";\nimport { isLocalRoom } from \"../utils/localRoom/isLocalRoom\";\nimport Modal from \"../Modal\";\nimport UploadConfirmDialog from \"../components/views/dialogs/UploadConfirmDialog\";\nimport { type RunResult } from \"./interface\";\n\nexport function reject(error?: any): RunResult {\n    return { error };\n}\n\nexport function success(promise: Promise<any> = Promise.resolve()): RunResult {\n    return { promise };\n}\n\nexport function successSync(value: any): RunResult {\n    return success(Promise.resolve(value));\n}\n\n/**\n * Check whether the user can affect power levels in the given room\n * @param cli - The Matrix client\n * @param roomId - The room ID\n * @returns True if the user can affect power levels, false otherwise\n */\nexport const canAffectPowerlevels = (cli: MatrixClient | null, roomId: string | null): boolean => {\n    if (!cli || !roomId) return false;\n    const room = cli?.getRoom(roomId);\n    return !!room?.currentState.maySendStateEvent(EventType.RoomPowerLevels, cli.getSafeUserId()) && !isLocalRoom(room);\n};\n\n// XXX: workaround for https://github.com/microsoft/TypeScript/issues/31816\ninterface HTMLInputEvent extends Event {\n    target: HTMLInputElement & EventTarget;\n}\n\nexport const singleMxcUpload = async (cli: MatrixClient): Promise<string | null> => {\n    return new Promise((resolve) => {\n        const fileSelector = document.createElement(\"input\");\n        fileSelector.setAttribute(\"type\", \"file\");\n        fileSelector.onchange = (ev: Event) => {\n            const file = (ev as HTMLInputEvent).target.files?.[0];\n            if (!file) return;\n\n            const { finished } = Modal.createDialog(UploadConfirmDialog, { file });\n            finished.then(async ([shouldContinue]) => {\n                if (shouldContinue) {\n                    const { content_uri: uri } = await cli.uploadContent(file);\n                    resolve(uri);\n                } else {\n                    resolve(null);\n                }\n            });\n        };\n\n        fileSelector.click();\n    });\n};\n\nexport const isCurrentLocalRoom = (cli: MatrixClient | null): boolean => {\n    const roomId = SdkContextClass.instance.roomViewStore.getRoomId();\n    if (!roomId) return false;\n    const room = cli?.getRoom(roomId);\n    if (!room) return false;\n    return isLocalRoom(room);\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2023 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type RoomMessageEventContent } from \"matrix-js-sdk/src/types\";\n\nimport { _td } from \"../languageHandler\";\nimport { type XOR } from \"../@types/common\";\n\nexport const CommandCategories = {\n    messages: _td(\"slash_command|category_messages\"),\n    actions: _td(\"slash_command|category_actions\"),\n    admin: _td(\"slash_command|category_admin\"),\n    advanced: _td(\"slash_command|category_advanced\"),\n    effects: _td(\"slash_command|category_effects\"),\n    other: _td(\"slash_command|category_other\"),\n};\n\nexport type RunResult = XOR<{ error: Error }, { promise: Promise<RoomMessageEventContent | undefined> }>;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2023 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { type SlashCommand as SlashCommandEvent } from \"@matrix-org/analytics-events/types/typescript/SlashCommand\";\n\nimport { TimelineRenderingType } from \"../contexts/RoomContext\";\nimport { reject } from \"./utils\";\nimport { _t, UserFriendlyError } from \"../languageHandler\";\nimport { PosthogAnalytics } from \"../PosthogAnalytics\";\nimport { CommandCategories, type RunResult } from \"./interface\";\n\n/**\n * The function signature for the run function of a {@link Command}\n * @param matrixClient - The Matrix client\n * @param roomId - The room ID where the command is run\n * @param threadId - The thread ID where the command is run, or null for room timeline\n * @param args - The arguments passed to the command\n * @returns The result of running the command\n */\ntype RunFn = (\n    this: Command,\n    matrixClient: MatrixClient,\n    roomId: string,\n    threadId: string | null,\n    args?: string,\n) => RunResult;\n\n/**\n * Options for {@link Command}\n * @param command - The command name, e.g. \"me\" for the /me command\n * @param aliases - Alternative names for the command\n * @param args - The arguments for the command, e.g. \"<message>\" for the /me command\n * @param description - A translation key describing the command\n * @param analyticsName - The name to use for analytics tracking\n * @param runFn - The function to execute when the command is run\n * @param category - The category of the command, e.g. CommandCategories.emoji\n * @param hideCompletionAfterSpace - Whether to hide autocomplete after a space is typed\n * @param isEnabled - A function to determine if the command is enabled in a given context\n * @param renderingTypes - The rendering types (room/thread) where this command is valid\n */\ninterface ICommandOpts {\n    command: string;\n    aliases?: string[];\n    args?: string;\n    description: TranslationKey;\n    analyticsName?: SlashCommandEvent[\"command\"];\n    runFn?: RunFn;\n    category: string;\n    hideCompletionAfterSpace?: boolean;\n    isEnabled?(matrixClient: MatrixClient | null, roomId: string | null): boolean;\n    renderingTypes?: TimelineRenderingType[];\n}\n\nexport class Command {\n    public readonly command: string;\n    public readonly aliases: string[];\n    public readonly args?: string;\n    public readonly description: TranslationKey;\n    public readonly runFn?: RunFn;\n    public readonly category: string;\n    public readonly hideCompletionAfterSpace: boolean;\n    public readonly renderingTypes?: TimelineRenderingType[];\n    public readonly analyticsName?: SlashCommandEvent[\"command\"];\n    private readonly _isEnabled?: (matrixClient: MatrixClient | null, roomId: string | null) => boolean;\n\n    public constructor(opts: ICommandOpts) {\n        this.command = opts.command;\n        this.aliases = opts.aliases || [];\n        this.args = opts.args || \"\";\n        this.description = opts.description;\n        this.runFn = opts.runFn?.bind(this);\n        this.category = opts.category || CommandCategories.other;\n        this.hideCompletionAfterSpace = opts.hideCompletionAfterSpace || false;\n        this._isEnabled = opts.isEnabled;\n        this.renderingTypes = opts.renderingTypes;\n        this.analyticsName = opts.analyticsName;\n    }\n\n    public getCommand(): string {\n        return `/${this.command}`;\n    }\n\n    public getCommandWithArgs(): string {\n        return this.getCommand() + \" \" + this.args;\n    }\n\n    public run(matrixClient: MatrixClient, roomId: string, threadId: string | null, args?: string): RunResult {\n        // if it has no runFn then its an ignored/nop command (autocomplete only) e.g `/me`\n        if (!this.runFn) {\n            return reject(new UserFriendlyError(\"slash_command|error_invalid_runfn\"));\n        }\n\n        const renderingType = threadId ? TimelineRenderingType.Thread : TimelineRenderingType.Room;\n        if (this.renderingTypes && !this.renderingTypes?.includes(renderingType)) {\n            return reject(\n                new UserFriendlyError(\"slash_command|error_invalid_rendering_type\", {\n                    renderingType,\n                    cause: undefined,\n                }),\n            );\n        }\n\n        if (this.analyticsName) {\n            PosthogAnalytics.instance.trackEvent<SlashCommandEvent>({\n                eventName: \"SlashCommand\",\n                command: this.analyticsName,\n            });\n        }\n\n        return this.runFn(matrixClient, roomId, threadId, args);\n    }\n\n    public getUsage(): string {\n        return _t(\"slash_command|usage\") + \": \" + this.getCommandWithArgs();\n    }\n\n    public isEnabled(cli: MatrixClient | null, roomId: string | null): boolean {\n        return this._isEnabled?.(cli, roomId) ?? true;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2023 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient, type Room, type RoomMember } from \"matrix-js-sdk/src/matrix\";\n\nimport { _td, UserFriendlyError } from \"../languageHandler\";\nimport { EffectiveMembership, getEffectiveMembership } from \"../utils/membership\";\nimport { warnSelfDemote } from \"../components/views/right_panel/UserInfo\";\nimport { TimelineRenderingType } from \"../contexts/RoomContext\";\nimport { canAffectPowerlevels, success, reject } from \"./utils\";\nimport { CommandCategories, type RunResult } from \"./interface\";\nimport { Command } from \"./command\";\n\nconst updatePowerLevel = async (room: Room, member: RoomMember, powerLevel: number | undefined): Promise<unknown> => {\n    // Only warn if the target is ourselves and the power level is decreasing or being unset\n    if (member.userId === room.client.getUserId() && (powerLevel === undefined || member.powerLevel > powerLevel)) {\n        const ok = await warnSelfDemote(room.isSpaceRoom());\n        if (!ok) return; // Nothing to do\n    }\n    return room.client.setPowerLevel(room.roomId, member.userId, powerLevel);\n};\n\nconst updatePowerLevelHelper = (\n    client: MatrixClient,\n    roomId: string,\n    userId: string,\n    powerLevel: number | undefined,\n): RunResult => {\n    const room = client.getRoom(roomId);\n    if (!room) {\n        return reject(\n            new UserFriendlyError(\"slash_command|error_invalid_room\", {\n                roomId,\n                cause: undefined,\n            }),\n        );\n    }\n    const member = room.getMember(userId);\n    if (!member?.membership || getEffectiveMembership(member.membership) === EffectiveMembership.Leave) {\n        return reject(new UserFriendlyError(\"slash_command|error_invalid_user_in_room\"));\n    }\n\n    return success(updatePowerLevel(room, member, powerLevel));\n};\n\nexport const op = new Command({\n    command: \"op\",\n    args: \"<user-id> [<power-level>]\",\n    description: _td(\"slash_command|op\"),\n    isEnabled: canAffectPowerlevels,\n    runFn: function (cli, roomId, threadId, args) {\n        if (args) {\n            const matches = args.match(/^(\\S+?)( +(-?\\d+))?$/);\n            let powerLevel = 50; // default power level for op\n            if (matches) {\n                const userId = matches[1];\n                if (matches.length === 4 && undefined !== matches[3]) {\n                    powerLevel = parseInt(matches[3], 10);\n                }\n                return updatePowerLevelHelper(cli, roomId, userId, powerLevel);\n            }\n        }\n        return reject(this.getUsage());\n    },\n    category: CommandCategories.admin,\n    renderingTypes: [TimelineRenderingType.Room],\n});\n\nexport const deop = new Command({\n    command: \"deop\",\n    args: \"<user-id>\",\n    description: _td(\"slash_command|deop\"),\n    isEnabled: canAffectPowerlevels,\n    runFn: function (cli, roomId, threadId, args) {\n        if (args) {\n            const matches = args.match(/^(\\S+)$/);\n            if (matches) {\n                return updatePowerLevelHelper(cli, roomId, args, undefined);\n            }\n        }\n        return reject(this.getUsage());\n    },\n    category: CommandCategories.admin,\n    renderingTypes: [TimelineRenderingType.Room],\n});\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { _td } from \"../languageHandler\";\nimport { reject, success } from \"./utils\";\nimport { isPermalinkHost, parsePermalink } from \"../utils/permalinks/Permalinks\";\nimport dis from \"../dispatcher/dispatcher\";\nimport { type ViewRoomPayload } from \"../dispatcher/payloads/ViewRoomPayload\";\nimport { Action } from \"../dispatcher/actions\";\nimport { TimelineRenderingType } from \"../contexts/RoomContext\";\nimport { Command } from \"./command\";\nimport { CommandCategories, type RunResult } from \"./interface\";\n\n// A return of undefined here signals a usage error, where the command should return `reject(this.getUsage());`\nfunction openRoom(cli: MatrixClient, args: string | undefined, autoJoin: boolean): RunResult | undefined {\n    if (!args) return;\n    const params = args.split(\" \");\n    if (params.length < 1) return;\n\n    let isPermalink = false;\n    if (params[0].startsWith(\"http:\") || params[0].startsWith(\"https:\")) {\n        // It's at least a URL - try and pull out a hostname to check against the\n        // permalink handler\n        const parsedUrl = new URL(params[0]);\n        const hostname = parsedUrl.host || parsedUrl.hostname; // takes first non-falsey value\n\n        // if we're using a Element permalink handler, this will catch it before we get much further.\n        // see below where we make assumptions about parsing the URL.\n        if (isPermalinkHost(hostname)) {\n            isPermalink = true;\n        }\n    }\n\n    if (params[0][0] === \"#\") {\n        let roomAlias = params[0];\n        if (!roomAlias.includes(\":\")) {\n            roomAlias += \":\" + cli.getDomain();\n        }\n\n        dis.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            room_alias: roomAlias,\n            auto_join: autoJoin,\n            metricsTrigger: \"SlashCommand\",\n            metricsViaKeyboard: true,\n        });\n        return success();\n    }\n\n    if (params[0][0] === \"!\") {\n        const [roomId, ...viaServers] = params;\n\n        dis.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            room_id: roomId,\n            via_servers: viaServers, // for the rejoin button\n            auto_join: autoJoin,\n            metricsTrigger: \"SlashCommand\",\n            metricsViaKeyboard: true,\n        });\n        return success();\n    }\n\n    if (isPermalink) {\n        const permalinkParts = parsePermalink(params[0]);\n\n        // This check technically isn't needed because we already did our\n        // safety checks up above. However, for good measure, let's be sure.\n        if (!permalinkParts) {\n            return;\n        }\n\n        // If for some reason someone wanted to join a user, we should\n        // stop them now.\n        if (!permalinkParts.roomIdOrAlias) {\n            return;\n        }\n\n        const entity = permalinkParts.roomIdOrAlias;\n        const viaServers = permalinkParts.viaServers;\n        const eventId = permalinkParts.eventId;\n\n        const dispatch: ViewRoomPayload = {\n            action: Action.ViewRoom,\n            auto_join: autoJoin,\n            metricsTrigger: \"SlashCommand\",\n            metricsViaKeyboard: true,\n        };\n\n        if (entity[0] === \"!\") dispatch[\"room_id\"] = entity;\n        else dispatch[\"room_alias\"] = entity;\n\n        if (eventId) {\n            dispatch[\"event_id\"] = eventId;\n            dispatch[\"highlighted\"] = true;\n        }\n\n        if (viaServers) {\n            // For the join, these are passed down to the js-sdk's /join call\n            dispatch[\"opts\"] = { viaServers };\n\n            // For if the join fails (rejoin button)\n            dispatch[\"via_servers\"] = viaServers;\n        }\n\n        dis.dispatch(dispatch);\n        return success();\n    }\n\n    // Otherwise, it's a usage error. Return `undefined`.\n}\n\n// Note: we support 2 versions of this command. The first is\n// the public-facing one for most users and the other is a\n// power-user edition where someone may join via permalink or\n// room ID with optional servers. Practically, this results\n// in the following variations:\n//   /join #example:example.org\n//   /join !example:example.org\n//   /join !example:example.org altserver.com elsewhere.ca\n//   /join https://matrix.to/#/!example:example.org?via=altserver.com\n// The command also supports event permalinks transparently:\n//   /join https://matrix.to/#/!example:example.org/$something:example.org\n//   /join https://matrix.to/#/!example:example.org/$something:example.org?via=altserver.com\nexport const join = new Command({\n    command: \"join\",\n    aliases: [\"j\"],\n    args: \"<room-address>\",\n    description: _td(\"slash_command|join\"),\n    runFn: function (cli, roomId, threadId, args) {\n        return openRoom(cli, args, true) ?? reject(this.getUsage());\n    },\n    category: CommandCategories.actions,\n    renderingTypes: [TimelineRenderingType.Room],\n});\n\n// Similar to join but doesn't auto join the room if you aren't already joined to it\nexport const goto = new Command({\n    command: \"goto\",\n    aliases: [\"view\"],\n    args: \"<room-address>\",\n    description: _td(\"slash_command|view\"),\n    runFn: function (cli, roomId, threadId, args) {\n        return openRoom(cli, args, false) ?? reject(this.getUsage());\n    },\n    category: CommandCategories.actions,\n    renderingTypes: [TimelineRenderingType.Room],\n});\n","/*\n * Copyright 2026 Element Creations Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { _td } from \"../../languageHandler\";\nimport { isCurrentLocalRoom } from \"../utils\";\nimport { runUpgradeRoomCommand } from \"./runUpgradeRoomCommand\";\nimport { Command } from \"../command\";\nimport { CommandCategories, type RunResult } from \"../interface\";\nimport { TimelineRenderingType } from \"../../contexts/RoomContext\";\n\nconst upgraderoom = new Command({\n    command: \"upgraderoom\",\n    args: \"<new_version> [<additional-creator-user-id> ...]\",\n    description: _td(\"slash_command|upgraderoom\"),\n    isEnabled: (cli: MatrixClient) => !isCurrentLocalRoom(cli),\n    runFn: function (cli: MatrixClient, roomId: string, threadId: string | null, args?: string): RunResult {\n        return runUpgradeRoomCommand(this, cli, roomId, threadId, args);\n    },\n    category: CommandCategories.admin,\n    renderingTypes: [TimelineRenderingType.Room],\n});\n\nexport default upgraderoom;\n","/*\n * Copyright 2026 Element Creations Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { EventTimeline, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport Modal from \"../../Modal\";\nimport RoomUpgradeWarningDialog from \"../../components/views/dialogs/RoomUpgradeWarningDialog\";\nimport { type Command } from \"../command\";\nimport { UserFriendlyError } from \"../../languageHandler\";\nimport { parseUpgradeRoomArgs } from \"./parseUpgradeRoomArgs\";\nimport { reject, success } from \"../utils\";\nimport { type RunResult } from \"../interface\";\nimport { upgradeRoom } from \"../../utils/RoomUpgrade\";\n\nexport function runUpgradeRoomCommand(\n    command: Command,\n    cli: MatrixClient,\n    roomId: string,\n    _threadId: string | null,\n    args?: string,\n): RunResult {\n    if (!args) {\n        return reject(command.getUsage());\n    }\n    const parsedArgs = parseUpgradeRoomArgs(args);\n    if (parsedArgs) {\n        const room = cli.getRoom(roomId);\n        if (\n            !room?.getLiveTimeline().getState(EventTimeline.FORWARDS)?.mayClientSendStateEvent(\"m.room.tombstone\", cli)\n        ) {\n            return reject(new UserFriendlyError(\"slash_command|upgraderoom_permission_error\"));\n        }\n\n        const { finished } = Modal.createDialog(\n            RoomUpgradeWarningDialog,\n            { roomId: roomId, targetVersion: parsedArgs.targetVersion },\n            /*className=*/ undefined,\n            /*isPriority=*/ false,\n            /*isStatic=*/ true,\n        );\n\n        return success(\n            finished.then(async ([resp]): Promise<void> => {\n                if (!resp?.continue) return;\n                await upgradeRoom(\n                    room,\n                    parsedArgs.targetVersion,\n                    resp.invite,\n                    true,\n                    true,\n                    false,\n                    undefined,\n                    false,\n                    parsedArgs.additionalCreators,\n                );\n            }),\n        );\n    }\n    return reject(command.getUsage());\n}\n","/*\n * Copyright 2026 Element Creations Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nexport type UpgradeRoomParsedArgs = {\n    targetVersion: string;\n    additionalCreators?: string[];\n};\n\n/**\n * Parse the supplied arguments for a room upgrade, or return null if the\n * arguments are not valid. The arguments must be a room version followed by\n * zero or more valid user IDs.\n */\nexport function parseUpgradeRoomArgs(args: string): UpgradeRoomParsedArgs | null {\n    const parts = args.split(/\\s+/);\n    if (parts.length === 0 || parts[0] === \"\") {\n        return null;\n    } else {\n        const targetVersion = parts[0];\n        let additionalCreators: string[] | undefined;\n        for (let i = 1; i < parts.length; ++i) {\n            if (additionalCreators === undefined) {\n                additionalCreators = [];\n            }\n            additionalCreators.push(parts[i]);\n        }\n        return { targetVersion, additionalCreators };\n    }\n}\n","/*\n * Copyright 2026 Element Creations Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { ContentHelpers } from \"matrix-js-sdk/src/matrix\";\n\nimport { Command } from \"./command\";\nimport { successSync } from \"./utils\";\nimport { CommandCategories } from \"./interface\";\n\nexport function emoticon(command: string, description: TranslationKey, message: string): Command {\n    return new Command({\n        command,\n        args: \"<message>\",\n        description,\n        runFn: function (_cli, _roomId, _threadId, args) {\n            if (args) {\n                message = message + \" \" + args;\n            }\n            return successSync(ContentHelpers.makeTextMessage(message));\n        },\n        category: CommandCategories.messages,\n    });\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2018 New Vector Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport {\n    ContentHelpers,\n    Direction,\n    EventType,\n    type IContent,\n    type MRoomTopicEventContent,\n    type User,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { KnownMembership, type RoomMemberEventContent } from \"matrix-js-sdk/src/types\";\n\nimport dis from \"../dispatcher/dispatcher\";\nimport { _t, _td, UserFriendlyError } from \"../languageHandler\";\nimport Modal from \"../Modal\";\nimport MultiInviter from \"../utils/MultiInviter\";\nimport { Linkify, topicToHtml } from \"../HtmlUtils\";\nimport QuestionDialog from \"../components/views/dialogs/QuestionDialog\";\nimport WidgetUtils from \"../utils/WidgetUtils\";\nimport { textToHtmlRainbow } from \"../utils/colour\";\nimport { AddressType, getAddressType } from \"../UserAddress\";\nimport { abbreviateUrl } from \"../utils/UrlUtils\";\nimport { getDefaultIdentityServerUrl, setToDefaultIdentityServer } from \"../utils/IdentityServerUtils\";\nimport { WidgetType } from \"../widgets/WidgetType\";\nimport { Jitsi } from \"../widgets/Jitsi\";\nimport BugReportDialog from \"../components/views/dialogs/BugReportDialog\";\nimport { ensureDMExists } from \"../createRoom\";\nimport { type ViewUserPayload } from \"../dispatcher/payloads/ViewUserPayload\";\nimport { Action } from \"../dispatcher/actions\";\nimport SdkConfig from \"../SdkConfig\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { UIComponent, UIFeature } from \"../settings/UIFeature\";\nimport { CHAT_EFFECTS } from \"../effects\";\nimport LegacyCallHandler from \"../LegacyCallHandler\";\nimport { guessAndSetDMRoom } from \"../Rooms\";\nimport DevtoolsDialog from \"../components/views/dialogs/DevtoolsDialog\";\nimport InfoDialog from \"../components/views/dialogs/InfoDialog\";\nimport SlashCommandHelpDialog from \"../components/views/dialogs/SlashCommandHelpDialog\";\nimport { shouldShowComponent } from \"../customisations/helpers/UIComponents\";\nimport { TimelineRenderingType } from \"../contexts/RoomContext\";\nimport { type ViewRoomPayload } from \"../dispatcher/payloads/ViewRoomPayload\";\nimport { htmlSerializeFromMdIfNeeded } from \"../editor/serialize\";\nimport { leaveRoomBehaviour } from \"../utils/leave-behaviour\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { isCurrentLocalRoom, reject, singleMxcUpload, success, successSync } from \"./utils\";\nimport { deop, op } from \"./op\";\nimport { CommandCategories } from \"./interface\";\nimport { Command } from \"./command\";\nimport { goto, join } from \"./join\";\nimport { manuallyVerifyDevice } from \"../components/views/dialogs/ManualDeviceKeyVerificationDialog\";\nimport upgraderoom from \"./upgraderoom/upgraderoom\";\nimport { emoticon } from \"./emoticon\";\n\nexport { CommandCategories, Command };\n\nexport const Commands = [\n    new Command({\n        command: \"spoiler\",\n        args: \"<message>\",\n        description: _td(\"slash_command|spoiler\"),\n        runFn: function (cli, roomId, threadId, message = \"\") {\n            return successSync(ContentHelpers.makeHtmlMessage(message, `<span data-mx-spoiler>${message}</span>`));\n        },\n        category: CommandCategories.messages,\n    }),\n    emoticon(\"shrug\", _td(\"slash_command|shrug\"), \"¯\\\\_(ツ)_/¯\"),\n    emoticon(\"tableflip\", _td(\"slash_command|tableflip\"), \"(╯°□°)╯︵ ┻━┻\"),\n    emoticon(\"unflip\", _td(\"slash_command|unflip\"), \"┬──┬ ノ( ゜-゜ノ)\"),\n    emoticon(\"lenny\", _td(\"slash_command|lenny\"), \"( ͡° ͜ʖ ͡°)\"),\n    new Command({\n        command: \"plain\",\n        args: \"<message>\",\n        description: _td(\"slash_command|plain\"),\n        runFn: function (cli, roomId, threadId, messages = \"\") {\n            return successSync(ContentHelpers.makeTextMessage(messages));\n        },\n        category: CommandCategories.messages,\n    }),\n    new Command({\n        command: \"html\",\n        args: \"<message>\",\n        description: _td(\"slash_command|html\"),\n        runFn: function (cli, roomId, threadId, messages = \"\") {\n            return successSync(ContentHelpers.makeHtmlMessage(messages, messages));\n        },\n        category: CommandCategories.messages,\n    }),\n    upgraderoom,\n    new Command({\n        command: \"jumptodate\",\n        args: \"<YYYY-MM-DD>\",\n        description: _td(\"slash_command|jumptodate\"),\n        isEnabled: () => SettingsStore.getValue(\"feature_jump_to_date\"),\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                return success(\n                    (async (): Promise<void> => {\n                        const unixTimestamp = Date.parse(args);\n                        if (!unixTimestamp) {\n                            throw new UserFriendlyError(\"slash_command|jumptodate_invalid_input\", {\n                                inputDate: args,\n                                cause: undefined,\n                            });\n                        }\n\n                        const { event_id: eventId, origin_server_ts: originServerTs } = await cli.timestampToEvent(\n                            roomId,\n                            unixTimestamp,\n                            Direction.Forward,\n                        );\n                        logger.log(\n                            `/timestamp_to_event: found ${eventId} (${originServerTs}) for timestamp=${unixTimestamp}`,\n                        );\n                        dis.dispatch<ViewRoomPayload>({\n                            action: Action.ViewRoom,\n                            event_id: eventId,\n                            highlighted: true,\n                            room_id: roomId,\n                            metricsTrigger: \"SlashCommand\",\n                            metricsViaKeyboard: true,\n                        });\n                    })(),\n                );\n            }\n\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.actions,\n    }),\n    new Command({\n        command: \"nick\",\n        args: \"<display_name>\",\n        description: _td(\"slash_command|nick\"),\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                return success(cli.setDisplayName(args));\n            }\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.actions,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"myroomnick\",\n        aliases: [\"roomnick\"],\n        args: \"<display_name>\",\n        description: _td(\"slash_command|myroomnick\"),\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                const ev = cli.getRoom(roomId)?.currentState.getStateEvents(EventType.RoomMember, cli.getSafeUserId());\n                const content: RoomMemberEventContent = {\n                    ...(ev ? ev.getContent() : { membership: KnownMembership.Join }),\n                    displayname: args,\n                };\n                return success(cli.sendStateEvent(roomId, EventType.RoomMember, content, cli.getSafeUserId()));\n            }\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.actions,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"roomavatar\",\n        args: \"[<mxc_url>]\",\n        description: _td(\"slash_command|roomavatar\"),\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            let promise = Promise.resolve(args ?? null);\n            if (!args) {\n                promise = singleMxcUpload(cli);\n            }\n\n            return success(\n                promise.then((url) => {\n                    if (!url) return;\n                    return cli.sendStateEvent(roomId, EventType.RoomAvatar, { url }, \"\");\n                }),\n            );\n        },\n        category: CommandCategories.actions,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"myroomavatar\",\n        args: \"[<mxc_url>]\",\n        description: _td(\"slash_command|myroomavatar\"),\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            const room = cli.getRoom(roomId);\n            const userId = cli.getSafeUserId();\n\n            let promise = Promise.resolve(args ?? null);\n            if (!args) {\n                promise = singleMxcUpload(cli);\n            }\n\n            return success(\n                promise.then((url) => {\n                    if (!url) return;\n                    const ev = room?.currentState.getStateEvents(EventType.RoomMember, userId);\n                    const content: RoomMemberEventContent = {\n                        ...(ev ? ev.getContent() : { membership: KnownMembership.Join }),\n                        avatar_url: url,\n                    };\n                    return cli.sendStateEvent(roomId, EventType.RoomMember, content, userId);\n                }),\n            );\n        },\n        category: CommandCategories.actions,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"myavatar\",\n        args: \"[<mxc_url>]\",\n        description: _td(\"slash_command|myavatar\"),\n        runFn: function (cli, roomId, threadId, args) {\n            let promise = Promise.resolve(args ?? null);\n            if (!args) {\n                promise = singleMxcUpload(cli);\n            }\n\n            return success(\n                promise.then((url) => {\n                    if (!url) return;\n                    return cli.setAvatarUrl(url);\n                }),\n            );\n        },\n        category: CommandCategories.actions,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"topic\",\n        args: \"[<topic>]\",\n        description: _td(\"slash_command|topic\"),\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                const html = htmlSerializeFromMdIfNeeded(args, { forceHTML: false });\n                return success(cli.setRoomTopic(roomId, args, html));\n            }\n            const room = cli.getRoom(roomId);\n            if (!room) {\n                return reject(\n                    new UserFriendlyError(\"slash_command|topic_room_error\", {\n                        roomId,\n                        cause: undefined,\n                    }),\n                );\n            }\n\n            const content = room.currentState.getStateEvents(\"m.room.topic\", \"\")?.getContent<MRoomTopicEventContent>();\n            const topic = !!content\n                ? ContentHelpers.parseTopicContent(content)\n                : { text: _t(\"slash_command|topic_none\") };\n\n            const body = topicToHtml(topic.text, topic.html, undefined, true);\n\n            Modal.createDialog(InfoDialog, {\n                title: room.name,\n                description: <Linkify>{body}</Linkify>,\n                hasCloseButton: true,\n                className: \"markdown-body\",\n            });\n            return success();\n        },\n        category: CommandCategories.admin,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"roomname\",\n        args: \"<name>\",\n        description: _td(\"slash_command|roomname\"),\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                return success(cli.setRoomName(roomId, args));\n            }\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.admin,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"invite\",\n        args: \"<user-id> [<reason>]\",\n        description: _td(\"slash_command|invite\"),\n        analyticsName: \"Invite\",\n        isEnabled: (cli) => !isCurrentLocalRoom(cli) && shouldShowComponent(UIComponent.InviteUsers),\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                const [address, reason] = splitAtFirstSpace(args);\n                if (address) {\n                    // We use a MultiInviter to re-use the invite logic, even though\n                    // we're only inviting one user.\n                    // If we need an identity server but don't have one, things\n                    // get a bit more complex here, but we try to show something\n                    // meaningful.\n                    let prom = Promise.resolve();\n                    if (getAddressType(address) === AddressType.Email && !cli.getIdentityServerUrl()) {\n                        const defaultIdentityServerUrl = getDefaultIdentityServerUrl();\n                        if (defaultIdentityServerUrl) {\n                            const { finished } = Modal.createDialog(QuestionDialog, {\n                                title: _t(\"slash_command|invite_3pid_use_default_is_title\"),\n                                description: (\n                                    <p>\n                                        {_t(\"slash_command|invite_3pid_use_default_is_title_description\", {\n                                            defaultIdentityServerName: abbreviateUrl(defaultIdentityServerUrl),\n                                        })}\n                                    </p>\n                                ),\n                                button: _t(\"action|continue\"),\n                            });\n\n                            prom = finished.then(([useDefault]) => {\n                                if (useDefault) {\n                                    setToDefaultIdentityServer(cli);\n                                    return;\n                                }\n                                throw new UserFriendlyError(\"slash_command|invite_3pid_needs_is_error\");\n                            });\n                        } else {\n                            return reject(new UserFriendlyError(\"slash_command|invite_3pid_needs_is_error\"));\n                        }\n                    }\n                    const inviter = new MultiInviter(cli, roomId);\n                    return success(\n                        prom\n                            .then(() => {\n                                return inviter.invite([address], reason);\n                            })\n                            .then(() => {\n                                if (inviter.getCompletionState(address) !== \"invited\") {\n                                    const errorStringFromInviterUtility = inviter.getErrorText(address);\n                                    if (errorStringFromInviterUtility) {\n                                        throw new Error(errorStringFromInviterUtility);\n                                    } else {\n                                        throw new UserFriendlyError(\"slash_command|invite_failed\", {\n                                            user: address,\n                                            roomId,\n                                            cause: undefined,\n                                        });\n                                    }\n                                }\n                            }),\n                    );\n                }\n            }\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.actions,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    goto,\n    join,\n    new Command({\n        command: \"part\",\n        args: \"[<room-address>]\",\n        description: _td(\"action|leave_room\"),\n        analyticsName: \"Part\",\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            let targetRoomId: string | undefined;\n            if (args) {\n                const matches = args.match(/^(\\S+)$/);\n                if (matches) {\n                    let roomAlias = matches[1];\n                    if (!roomAlias.startsWith(\"#\")) return reject(this.getUsage());\n\n                    if (!roomAlias.includes(\":\")) {\n                        roomAlias += \":\" + cli.getDomain();\n                    }\n\n                    // Try to find a room with this alias\n                    const rooms = cli.getRooms();\n                    targetRoomId = rooms.find((room) => {\n                        return room.getCanonicalAlias() === roomAlias || room.getAltAliases().includes(roomAlias);\n                    })?.roomId;\n                    if (!targetRoomId) {\n                        return reject(\n                            new UserFriendlyError(\"slash_command|part_unknown_alias\", {\n                                roomAlias,\n                                cause: undefined,\n                            }),\n                        );\n                    }\n                }\n            }\n\n            if (!targetRoomId) targetRoomId = roomId;\n            return success(leaveRoomBehaviour(cli, targetRoomId));\n        },\n        category: CommandCategories.actions,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"remove\",\n        aliases: [\"kick\"],\n        args: \"<user-id> [reason]\",\n        description: _td(\"slash_command|remove\"),\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                const [userId, reason] = splitAtFirstSpace(args);\n                if (userId) {\n                    return success(cli.kick(roomId, userId, reason));\n                }\n            }\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.admin,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"ban\",\n        args: \"<user-id> [reason]\",\n        description: _td(\"slash_command|ban\"),\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                const [userId, reason] = splitAtFirstSpace(args);\n                if (userId) {\n                    return success(cli.ban(roomId, userId, reason));\n                }\n            }\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.admin,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"unban\",\n        args: \"<user-id>\",\n        description: _td(\"slash_command|unban\"),\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                const matches = args.match(/^(\\S+)$/);\n                if (matches) {\n                    // Reset the user membership to \"leave\" to unban him\n                    return success(cli.unban(roomId, matches[1]));\n                }\n            }\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.admin,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"ignore\",\n        args: \"<user-id>\",\n        description: _td(\"slash_command|ignore\"),\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                const matches = args.match(/^(@[^:]+:\\S+)$/);\n                if (matches) {\n                    const userId = matches[1];\n                    const ignoredUsers = cli.getIgnoredUsers();\n                    ignoredUsers.push(userId); // de-duped internally in the js-sdk\n                    return success(\n                        cli.setIgnoredUsers(ignoredUsers).then(() => {\n                            Modal.createDialog(InfoDialog, {\n                                title: _t(\"slash_command|ignore_dialog_title\"),\n                                description: (\n                                    <div>\n                                        <p>{_t(\"slash_command|ignore_dialog_description\", { userId })}</p>\n                                    </div>\n                                ),\n                            });\n                        }),\n                    );\n                }\n            }\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.actions,\n    }),\n    new Command({\n        command: \"unignore\",\n        args: \"<user-id>\",\n        description: _td(\"slash_command|unignore\"),\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                const matches = args.match(/(^@[^:]+:\\S+$)/);\n                if (matches) {\n                    const userId = matches[1];\n                    const ignoredUsers = cli.getIgnoredUsers();\n                    const index = ignoredUsers.indexOf(userId);\n                    if (index !== -1) ignoredUsers.splice(index, 1);\n                    return success(\n                        cli.setIgnoredUsers(ignoredUsers).then(() => {\n                            Modal.createDialog(InfoDialog, {\n                                title: _t(\"slash_command|unignore_dialog_title\"),\n                                description: (\n                                    <div>\n                                        <p>{_t(\"slash_command|unignore_dialog_description\", { userId })}</p>\n                                    </div>\n                                ),\n                            });\n                        }),\n                    );\n                }\n            }\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.actions,\n    }),\n    op,\n    deop,\n    new Command({\n        command: \"devtools\",\n        description: _td(\"slash_command|devtools\"),\n        runFn: function (cli, roomId, threadRootId) {\n            Modal.createDialog(DevtoolsDialog, { roomId, threadRootId }, \"mx_DevtoolsDialog_wrapper\");\n            return success();\n        },\n        category: CommandCategories.advanced,\n    }),\n    new Command({\n        command: \"addwidget\",\n        args: \"<url | embed code | Jitsi url>\",\n        description: _td(\"slash_command|addwidget\"),\n        isEnabled: (cli) =>\n            SettingsStore.getValue(UIFeature.Widgets) &&\n            shouldShowComponent(UIComponent.AddIntegrations) &&\n            !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, widgetUrl) {\n            if (!widgetUrl) {\n                return reject(new UserFriendlyError(\"slash_command|addwidget_missing_url\"));\n            }\n\n            // Try and parse out a widget URL from iframes\n            if (widgetUrl.toLowerCase().startsWith(\"<iframe \")) {\n                const embed = new DOMParser().parseFromString(widgetUrl, \"text/html\").body;\n                if (embed?.childNodes?.length === 1) {\n                    const iframe = embed.firstElementChild;\n                    if (iframe?.tagName.toLowerCase() === \"iframe\") {\n                        logger.log(\"Pulling URL out of iframe (embed code)\");\n                        if (!iframe.hasAttribute(\"src\")) {\n                            return reject(new UserFriendlyError(\"slash_command|addwidget_iframe_missing_src\"));\n                        }\n                        widgetUrl = iframe.getAttribute(\"src\")!;\n                    }\n                }\n            }\n\n            if (!widgetUrl.startsWith(\"https://\") && !widgetUrl.startsWith(\"http://\")) {\n                return reject(new UserFriendlyError(\"slash_command|addwidget_invalid_protocol\"));\n            }\n            if (WidgetUtils.canUserModifyWidgets(cli, roomId)) {\n                const userId = cli.getUserId();\n                const nowMs = new Date().getTime();\n                const widgetId = encodeURIComponent(`${roomId}_${userId}_${nowMs}`);\n                let type = WidgetType.CUSTOM;\n                let name = \"Custom\";\n                let data = {};\n\n                // Make the widget a Jitsi widget if it looks like a Jitsi widget\n                const jitsiData = Jitsi.getInstance().parsePreferredConferenceUrl(widgetUrl);\n                if (jitsiData) {\n                    logger.log(\"Making /addwidget widget a Jitsi conference\");\n                    type = WidgetType.JITSI;\n                    name = \"Jitsi\";\n                    data = jitsiData;\n                    widgetUrl = WidgetUtils.getLocalJitsiWrapperUrl();\n                }\n\n                return success(WidgetUtils.setRoomWidget(cli, roomId, widgetId, type, widgetUrl, name, data));\n            } else {\n                return reject(new UserFriendlyError(\"slash_command|addwidget_no_permissions\"));\n            }\n        },\n        category: CommandCategories.admin,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"verify\",\n        args: \"<device-id> <device-fingerprint>\",\n        description: _td(\"slash_command|verify\"),\n        runFn: function (cli, _roomId, _threadId, args) {\n            if (args) {\n                const matches = args.match(/^(\\S+) +(\\S+)$/);\n                if (matches) {\n                    const deviceId = matches[1];\n                    const fingerprint = matches[2];\n\n                    const { finished } = Modal.createDialog(QuestionDialog, {\n                        title: _t(\"slash_command|manual_device_verification_confirm_title\"),\n                        description: _t(\"slash_command|manual_device_verification_confirm_description\"),\n                        button: _t(\"action|verify\"),\n                        danger: true,\n                    });\n\n                    return success(\n                        finished.then(([confirmed]) => {\n                            if (confirmed) manuallyVerifyDevice(cli, deviceId, fingerprint);\n                        }),\n                    );\n                }\n            }\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.advanced,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"discardsession\",\n        description: _td(\"slash_command|discardsession\"),\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId) {\n            try {\n                cli.getCrypto()?.forceDiscardSession(roomId);\n            } catch (e) {\n                return reject(e instanceof Error ? e.message : e);\n            }\n            return success();\n        },\n        category: CommandCategories.advanced,\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"rainbow\",\n        description: _td(\"slash_command|rainbow\"),\n        args: \"<message>\",\n        runFn: function (cli, roomId, threadId, args) {\n            if (!args) return reject(this.getUsage());\n            return successSync(ContentHelpers.makeHtmlMessage(args, textToHtmlRainbow(args)));\n        },\n        category: CommandCategories.messages,\n    }),\n    new Command({\n        command: \"rainbowme\",\n        description: _td(\"slash_command|rainbowme\"),\n        args: \"<message>\",\n        runFn: function (cli, roomId, threadId, args) {\n            if (!args) return reject(this.getUsage());\n            return successSync(ContentHelpers.makeHtmlEmote(args, textToHtmlRainbow(args)));\n        },\n        category: CommandCategories.messages,\n    }),\n    new Command({\n        command: \"help\",\n        description: _td(\"slash_command|help\"),\n        runFn: function (cli, roomId, threadId, args) {\n            Modal.createDialog(SlashCommandHelpDialog, { roomId });\n            return success();\n        },\n        category: CommandCategories.advanced,\n    }),\n    new Command({\n        command: \"whois\",\n        description: _td(\"slash_command|whois\"),\n        args: \"<user-id>\",\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, userId) {\n            if (!userId || !userId.startsWith(\"@\") || !userId.includes(\":\")) {\n                return reject(this.getUsage());\n            }\n\n            const member = cli.getRoom(roomId)?.getMember(userId);\n            dis.dispatch<ViewUserPayload>({\n                action: Action.ViewUser,\n                // XXX: We should be using a real member object and not assuming what the receiver wants.\n                member: member || ({ userId } as User),\n            });\n            return success();\n        },\n        category: CommandCategories.advanced,\n    }),\n    new Command({\n        command: \"rageshake\",\n        aliases: [\"bugreport\"],\n        description: _td(\"slash_command|rageshake\"),\n        isEnabled: () => !!SdkConfig.get().bug_report_endpoint_url,\n        args: \"<description>\",\n        runFn: function (cli, roomId, threadId, args) {\n            return success(\n                Modal.createDialog(BugReportDialog, {\n                    initialText: args,\n                }).finished,\n            );\n        },\n        category: CommandCategories.advanced,\n    }),\n    new Command({\n        command: \"query\",\n        description: _td(\"slash_command|query\"),\n        args: \"<user-id>\",\n        runFn: function (cli, roomId, threadId, userId) {\n            // easter-egg for now: look up phone numbers through the thirdparty API\n            // (very dumb phone number detection...)\n            const isPhoneNumber = userId && /^\\+?[0123456789]+$/.test(userId);\n            if (!userId || ((!userId.startsWith(\"@\") || !userId.includes(\":\")) && !isPhoneNumber)) {\n                return reject(this.getUsage());\n            }\n\n            return success(\n                (async (): Promise<void> => {\n                    if (isPhoneNumber) {\n                        const results = await LegacyCallHandler.instance.pstnLookup(userId);\n                        if (!results || results.length === 0 || !results[0].userid) {\n                            throw new UserFriendlyError(\"slash_command|query_not_found_phone_number\");\n                        }\n                        userId = results[0].userid;\n                    }\n\n                    const roomId = await ensureDMExists(cli, userId);\n                    if (!roomId) throw new Error(\"Failed to ensure DM exists\");\n\n                    dis.dispatch<ViewRoomPayload>({\n                        action: Action.ViewRoom,\n                        room_id: roomId,\n                        metricsTrigger: \"SlashCommand\",\n                        metricsViaKeyboard: true,\n                    });\n                })(),\n            );\n        },\n        category: CommandCategories.actions,\n    }),\n    new Command({\n        command: \"msg\",\n        description: _td(\"slash_command|msg\"),\n        args: \"<user-id> [<message>]\",\n        runFn: function (cli, roomId, threadId, args) {\n            if (args) {\n                // matches the first whitespace delimited group and then the rest of the string\n                const [userId, msg] = splitAtFirstSpace(args);\n                if (userId !== \"\") {\n                    if (userId && userId.startsWith(\"@\") && userId.includes(\":\")) {\n                        return success(\n                            (async (): Promise<void> => {\n                                const roomId = await ensureDMExists(cli, userId);\n                                if (!roomId) throw new Error(\"Failed to ensure DM exists\");\n\n                                dis.dispatch<ViewRoomPayload>({\n                                    action: Action.ViewRoom,\n                                    room_id: roomId,\n                                    metricsTrigger: \"SlashCommand\",\n                                    metricsViaKeyboard: true,\n                                });\n                                if (msg) {\n                                    cli.sendTextMessage(roomId, msg);\n                                }\n                            })(),\n                        );\n                    }\n                }\n            }\n\n            return reject(this.getUsage());\n        },\n        category: CommandCategories.actions,\n    }),\n    new Command({\n        command: \"holdcall\",\n        description: _td(\"slash_command|holdcall\"),\n        category: CommandCategories.other,\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            const call = LegacyCallHandler.instance.getCallForRoom(roomId);\n            if (!call) {\n                return reject(new UserFriendlyError(\"slash_command|no_active_call\"));\n            }\n            call.setRemoteOnHold(true);\n            return success();\n        },\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"unholdcall\",\n        description: _td(\"slash_command|unholdcall\"),\n        category: CommandCategories.other,\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            const call = LegacyCallHandler.instance.getCallForRoom(roomId);\n            if (!call) {\n                return reject(new UserFriendlyError(\"slash_command|no_active_call\"));\n            }\n            call.setRemoteOnHold(false);\n            return success();\n        },\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"converttodm\",\n        description: _td(\"slash_command|converttodm\"),\n        category: CommandCategories.other,\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            const room = cli.getRoom(roomId);\n            if (!room) return reject(new UserFriendlyError(\"slash_command|could_not_find_room\"));\n            return success(guessAndSetDMRoom(room, true));\n        },\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n    new Command({\n        command: \"converttoroom\",\n        description: _td(\"slash_command|converttoroom\"),\n        category: CommandCategories.other,\n        isEnabled: (cli) => !isCurrentLocalRoom(cli),\n        runFn: function (cli, roomId, threadId, args) {\n            const room = cli.getRoom(roomId);\n            if (!room) return reject(new UserFriendlyError(\"slash_command|could_not_find_room\"));\n            return success(guessAndSetDMRoom(room, false));\n        },\n        renderingTypes: [TimelineRenderingType.Room],\n    }),\n\n    // Command definitions for autocompletion ONLY:\n    // /me is special because its not handled by SlashCommands.js and is instead done inside the Composer classes\n    new Command({\n        command: \"me\",\n        args: \"<message>\",\n        description: _td(\"slash_command|me\"),\n        category: CommandCategories.messages,\n        hideCompletionAfterSpace: true,\n    }),\n\n    ...CHAT_EFFECTS.map((effect) => {\n        return new Command({\n            command: effect.command,\n            description: effect.description(),\n            args: \"<message>\",\n            runFn: function (cli, roomId, threadId, args) {\n                let content: IContent;\n                if (!args) {\n                    content = ContentHelpers.makeEmoteMessage(effect.fallbackMessage());\n                } else {\n                    content = {\n                        msgtype: effect.msgType,\n                        body: args,\n                    };\n                }\n                dis.dispatch({ action: `effects.${effect.command}` });\n                return successSync(content);\n            },\n            category: CommandCategories.effects,\n            renderingTypes: [TimelineRenderingType.Room],\n        });\n    }),\n];\n\n// build a map from names and aliases to the Command objects.\nexport const CommandMap = new Map<string, Command>();\nCommands.forEach((cmd) => {\n    CommandMap.set(cmd.command, cmd);\n    cmd.aliases.forEach((alias) => {\n        CommandMap.set(alias, cmd);\n    });\n});\n\n/**\n * If the supplied input starts with \"/<command>\", returns an object with these\n * properties:\n *\n * cmd - the string following the / up to some whitespace\n * args - the string (if any) after first whitespace\n *\n * If not, returns {}\n */\nexport function parseCommandString(input: string): { cmd?: string; args?: string } {\n    const trimmedInput = input.trimStart();\n    if (trimmedInput.charAt(0) !== \"/\") {\n        return {};\n    }\n\n    const withoutSlash = trimmedInput.slice(1);\n    const [cmd, args] = splitAtFirstSpace(withoutSlash);\n\n    return { cmd, args };\n}\n\ninterface ICmd {\n    cmd?: Command;\n    args?: string;\n}\n\n/**\n * Split the supplied string into one or two strings separated by the first\n * region of white space we can find.\n */\nexport function splitAtFirstSpace(args: string): [string, string?] {\n    const trimmedArgs = args.trim();\n    const i = trimmedArgs.search(/\\s+/);\n    if (i === -1) {\n        return [trimmedArgs];\n    } else {\n        const first = trimmedArgs.slice(0, i);\n        const second = trimmedArgs.slice(i + 1).trimStart();\n        if (second === \"\") {\n            return [first];\n        } else {\n            return [first, second];\n        }\n    }\n}\n\n/**\n * Process the given text for /commands and returns a parsed command that can be used for running the operation.\n * @param {string} roomId The room ID where the command was issued.\n * @param {string} input The raw text input by the user.\n * @return {ICmd} The parsed command object.\n * Returns an empty object if the input didn't match a command.\n */\nexport function getCommand(roomId: string, input: string): ICmd {\n    const { cmd, args } = parseCommandString(input);\n\n    if (cmd && CommandMap.has(cmd) && CommandMap.get(cmd)!.isEnabled(MatrixClientPeg.get(), roomId)) {\n        return {\n            cmd: CommandMap.get(cmd),\n            args,\n        };\n    }\n    return {};\n}\n","/*\nCopyright 2018-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport EventEmitter from \"events\";\nimport { type MatrixEvent, RoomStateEvent, type RoomState } from \"matrix-js-sdk/src/matrix\";\n\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport WidgetUtils from \"../utils/WidgetUtils\";\nimport { WidgetMessagingStore } from \"./widgets/WidgetMessagingStore\";\n\nexport enum ActiveWidgetStoreEvent {\n    // Indicates a change in the currently persistent widget\n    Persistence = \"persistence\",\n    // Indicate changes in the currently docked widgets\n    Dock = \"dock\",\n    Undock = \"undock\",\n}\n\n/**\n * Stores information about the widgets active in the app right now:\n *  * What widget is set to remain always-on-screen, if any\n *    Only one widget may be 'always on screen' at any one time.\n *  * Reference counts to keep track of whether a widget is kept docked or alive\n *    by any components\n */\nexport default class ActiveWidgetStore extends EventEmitter {\n    private static internalInstance: ActiveWidgetStore;\n    private persistentWidgetId: string | null = null;\n    private persistentRoomId: string | null = null;\n    private dockedWidgetsByUid = new Map<string, number>();\n\n    public static get instance(): ActiveWidgetStore {\n        if (!ActiveWidgetStore.internalInstance) {\n            ActiveWidgetStore.internalInstance = new ActiveWidgetStore();\n        }\n        return ActiveWidgetStore.internalInstance;\n    }\n\n    public start(): void {\n        MatrixClientPeg.safeGet().on(RoomStateEvent.Events, this.onRoomStateEvents);\n    }\n\n    public stop(): void {\n        MatrixClientPeg.get()?.removeListener(RoomStateEvent.Events, this.onRoomStateEvents);\n    }\n\n    private onRoomStateEvents = (ev: MatrixEvent, { roomId }: RoomState): void => {\n        // XXX: This listens for state events in order to remove the active widget.\n        // Everything else relies on views listening for events and calling setters\n        // on this class which is terrible. This store should just listen for events\n        // and keep itself up to date.\n        // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n        if (ev.getType() === \"im.vector.modular.widgets\") {\n            this.destroyPersistentWidget(ev.getStateKey()!, roomId);\n        }\n    };\n\n    public destroyPersistentWidget(widgetId: string, roomId: string | null): void {\n        if (!this.getWidgetPersistence(widgetId, roomId)) return;\n        // We first need to set the widget persistence to false\n        this.setWidgetPersistence(widgetId, roomId, false);\n        // Then we can stop the messaging. Stopping the messaging emits - we might move the widget out of sight.\n        // If we would do this before setting the persistence to false, it would stay in the DOM (hidden) because\n        // its still persistent. We need to avoid this.\n        WidgetMessagingStore.instance.stopMessagingByUid(WidgetUtils.calcWidgetUid(widgetId, roomId ?? undefined));\n    }\n\n    public setWidgetPersistence(widgetId: string, roomId: string | null, val: boolean): void {\n        const isPersisted = this.getWidgetPersistence(widgetId, roomId);\n\n        if (isPersisted && !val) {\n            this.persistentWidgetId = null;\n            this.persistentRoomId = null;\n        } else if (!isPersisted && val) {\n            this.persistentWidgetId = widgetId;\n            this.persistentRoomId = roomId;\n        }\n        this.emit(ActiveWidgetStoreEvent.Persistence);\n    }\n\n    public getWidgetPersistence(widgetId: string, roomId: string | null): boolean {\n        return this.persistentWidgetId === widgetId && this.persistentRoomId === roomId;\n    }\n\n    public getPersistentWidgetId(): string | null {\n        return this.persistentWidgetId;\n    }\n\n    public getPersistentRoomId(): string | null {\n        return this.persistentRoomId;\n    }\n\n    // Registers the given widget as being docked somewhere in the UI (not a PiP),\n    // to allow its lifecycle to be tracked.\n    public dockWidget(widgetId: string, roomId: string | null): void {\n        const uid = WidgetUtils.calcWidgetUid(widgetId, roomId ?? undefined);\n        const refs = this.dockedWidgetsByUid.get(uid) ?? 0;\n        this.dockedWidgetsByUid.set(uid, refs + 1);\n        if (refs === 0) this.emit(ActiveWidgetStoreEvent.Dock);\n    }\n\n    public undockWidget(widgetId: string, roomId: string | null): void {\n        const uid = WidgetUtils.calcWidgetUid(widgetId, roomId ?? undefined);\n        const refs = this.dockedWidgetsByUid.get(uid);\n        if (refs) this.dockedWidgetsByUid.set(uid, refs - 1);\n        if (refs === 1) this.emit(ActiveWidgetStoreEvent.Undock);\n    }\n\n    // Determines whether the given widget is docked anywhere in the UI (not a PiP)\n    public isDocked(widgetId: string, roomId: string | null): boolean {\n        const uid = WidgetUtils.calcWidgetUid(widgetId, roomId ?? undefined);\n        const refs = this.dockedWidgetsByUid.get(uid) ?? 0;\n        return refs > 0;\n    }\n\n    // Determines whether the given widget is being kept alive in the UI, including PiPs\n    public isLive(widgetId: string, roomId: string | null): boolean {\n        return this.isDocked(widgetId, roomId) || this.getWidgetPersistence(widgetId, roomId);\n    }\n}\n\nwindow.mxActiveWidgetStore = ActiveWidgetStore.instance;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EventEmitter } from \"events\";\nimport AwaitLock from \"await-lock\";\n\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport { type MatrixDispatcher } from \"../dispatcher/dispatcher\";\n\n/**\n * The event/channel to listen for in an AsyncStore.\n */\nexport const UPDATE_EVENT = \"update\";\n\n/**\n * Represents a minimal store which works similar to Flux stores. Instead\n * of everything needing to happen in a dispatch cycle, everything can\n * happen async to that cycle.\n *\n * The store operates by using Object.assign() to mutate state - it sends the\n * state objects (current and new) through the function onto a new empty\n * object. Because of this, it is recommended to break out your state to be as\n * safe as possible. The state mutations are also locked, preventing concurrent\n * writes.\n *\n * All updates to the store happen on the UPDATE_EVENT event channel with the\n * one argument being the instance of the store.\n *\n * To update the state, use updateState() and preferably await the result to\n * help prevent lock conflicts.\n */\nexport abstract class AsyncStore<T extends object> extends EventEmitter {\n    private storeState: Readonly<T>;\n    private lock = new AwaitLock();\n    private readonly dispatcherRef: string;\n\n    /**\n     * Creates a new AsyncStore using the given dispatcher.\n     * @param {Dispatcher<ActionPayload>} dispatcher The dispatcher to rely upon.\n     * @param {T} initialState The initial state for the store.\n     */\n    protected constructor(\n        private dispatcher: MatrixDispatcher,\n        initialState: T = <T>{},\n    ) {\n        super();\n\n        this.dispatcherRef = dispatcher.register(this.onDispatch.bind(this));\n        this.storeState = initialState;\n    }\n\n    /**\n     * The current state of the store. Cannot be mutated.\n     */\n    protected get state(): T {\n        return this.storeState;\n    }\n\n    /**\n     * Stops the store's listening functions, such as the listener to the dispatcher.\n     */\n    protected stop(): void {\n        this.dispatcher.unregister(this.dispatcherRef);\n    }\n\n    /**\n     * Updates the state of the store.\n     * @param {T|*} newState The state to update in the store using Object.assign()\n     */\n    protected async updateState(newState: T | object): Promise<void> {\n        await this.lock.acquireAsync();\n        try {\n            this.storeState = Object.freeze(Object.assign(<T>{}, this.storeState, newState));\n            this.emit(UPDATE_EVENT, this);\n        } finally {\n            await this.lock.release();\n        }\n    }\n\n    /**\n     * Resets the store's to the provided state or an empty object.\n     * @param {T|*} newState The new state of the store.\n     * @param {boolean} quiet If true, the function will not raise an UPDATE_EVENT.\n     */\n    protected async reset(newState: T | object | null = null, quiet = false): Promise<void> {\n        await this.lock.acquireAsync();\n        try {\n            this.storeState = Object.freeze(<T>(newState || {}));\n            if (!quiet) this.emit(UPDATE_EVENT, this);\n        } finally {\n            await this.lock.release();\n        }\n    }\n\n    /**\n     * Called when the dispatcher broadcasts a dispatch event.\n     * @param {ActionPayload} payload The event being dispatched.\n     */\n    protected abstract onDispatch(payload: ActionPayload): void;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { AsyncStore } from \"./AsyncStore\";\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport { ReadyWatchingStore } from \"./ReadyWatchingStore\";\nimport { type MatrixDispatcher } from \"../dispatcher/dispatcher\";\n\nexport abstract class AsyncStoreWithClient<T extends object> extends AsyncStore<T> {\n    protected readyStore: ReadyWatchingStore;\n\n    protected constructor(dispatcher: MatrixDispatcher, initialState: T = <T>{}) {\n        super(dispatcher, initialState);\n\n        // Create an anonymous class to avoid code duplication\n        const asyncStore = this; // eslint-disable-line @typescript-eslint/no-this-alias\n        this.readyStore = new (class extends ReadyWatchingStore {\n            public get mxClient(): MatrixClient | null {\n                return this.matrixClient ?? null;\n            }\n\n            protected async onReady(): Promise<any> {\n                return asyncStore.onReady();\n            }\n\n            protected async onNotReady(): Promise<any> {\n                return asyncStore.onNotReady();\n            }\n        })(dispatcher);\n    }\n\n    public async start(): Promise<void> {\n        await this.readyStore.start();\n    }\n\n    public get matrixClient(): MatrixClient | null {\n        return this.readyStore.mxClient;\n    }\n\n    protected async onReady(): Promise<void> {\n        // Default implementation is to do nothing.\n    }\n\n    protected async onNotReady(): Promise<void> {\n        // Default implementation is to do nothing.\n    }\n\n    protected abstract onAction(payload: ActionPayload): Promise<void>;\n\n    protected async onDispatch(payload: ActionPayload): Promise<void> {\n        await this.onAction(payload);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room, RoomEvent, ClientEvent } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { isNullOrUndefined } from \"matrix-js-sdk/src/utils\";\n\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { AsyncStoreWithClient } from \"./AsyncStoreWithClient\";\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport { arrayHasDiff, filterBoolean } from \"../utils/arrays\";\nimport { SettingLevel } from \"../settings/SettingLevel\";\nimport { Action } from \"../dispatcher/actions\";\nimport { type SettingUpdatedPayload } from \"../dispatcher/payloads/SettingUpdatedPayload\";\nimport { type ViewRoomPayload } from \"../dispatcher/payloads/ViewRoomPayload\";\nimport { type JoinRoomPayload } from \"../dispatcher/payloads/JoinRoomPayload\";\n\nconst MAX_ROOMS = 20; // arbitrary\nconst AUTOJOIN_WAIT_THRESHOLD_MS = 90000; // 90s, the time we wait for an autojoined room to show up\n\ninterface IState {\n    enabled?: boolean;\n    rooms?: Room[];\n}\n\nexport class BreadcrumbsStore extends AsyncStoreWithClient<IState> {\n    private static readonly internalInstance = (() => {\n        const instance = new BreadcrumbsStore();\n        instance.start();\n        return instance;\n    })();\n\n    private waitingRooms: { roomId: string; addedTs: number }[] = [];\n\n    private constructor() {\n        super(defaultDispatcher);\n\n        SettingsStore.monitorSetting(\"breadcrumb_rooms\", null);\n        SettingsStore.monitorSetting(\"breadcrumbs\", null);\n    }\n\n    public static get instance(): BreadcrumbsStore {\n        return BreadcrumbsStore.internalInstance;\n    }\n\n    public get rooms(): Room[] {\n        return this.state.rooms || [];\n    }\n\n    public get visible(): boolean {\n        return !!this.state.enabled && this.meetsRoomRequirement;\n    }\n\n    /**\n     * Do we have enough rooms to justify showing the breadcrumbs?\n     * (Or is the labs feature enabled?)\n     *\n     * @returns true if there are at least 20 visible rooms.\n     */\n    public get meetsRoomRequirement(): boolean {\n        const msc3946ProcessDynamicPredecessor = SettingsStore.getValue(\"feature_dynamic_room_predecessors\");\n        return !!this.matrixClient && this.matrixClient.getVisibleRooms(msc3946ProcessDynamicPredecessor).length >= 20;\n    }\n\n    protected async onAction(payload: SettingUpdatedPayload | ViewRoomPayload | JoinRoomPayload): Promise<void> {\n        if (!this.matrixClient) return;\n        if (payload.action === Action.SettingUpdated) {\n            if (payload.settingName === \"breadcrumb_rooms\") {\n                await this.updateRooms();\n            } else if (payload.settingName === \"breadcrumbs\") {\n                await this.updateState({ enabled: SettingsStore.getValue(\"breadcrumbs\", null) });\n            }\n        } else if (payload.action === Action.ViewRoom) {\n            if (payload.auto_join && payload.room_id && !this.matrixClient.getRoom(payload.room_id)) {\n                // Queue the room instead of pushing it immediately. We're probably just\n                // waiting for a room join to complete.\n                this.waitingRooms.push({ roomId: payload.room_id, addedTs: Date.now() });\n            } else {\n                // The tests might not result in a valid room object.\n                const room = this.matrixClient.getRoom(payload.room_id);\n                const membership = room?.getMyMembership();\n                if (room && membership === KnownMembership.Join) await this.appendRoom(room);\n            }\n        } else if (payload.action === Action.JoinRoom) {\n            const room = this.matrixClient.getRoom(payload.roomId);\n            if (room) await this.appendRoom(room);\n        }\n    }\n\n    protected async onReady(): Promise<void> {\n        await this.updateRooms();\n        await this.updateState({ enabled: SettingsStore.getValue(\"breadcrumbs\", null) });\n\n        if (this.matrixClient) {\n            this.matrixClient.on(RoomEvent.MyMembership, this.onMyMembership);\n            this.matrixClient.on(ClientEvent.Room, this.onRoom);\n        }\n    }\n\n    protected async onNotReady(): Promise<void> {\n        if (this.matrixClient) {\n            this.matrixClient.removeListener(RoomEvent.MyMembership, this.onMyMembership);\n            this.matrixClient.removeListener(ClientEvent.Room, this.onRoom);\n        }\n    }\n\n    private onMyMembership = async (room: Room): Promise<void> => {\n        // Only turn on breadcrumbs is the user hasn't explicitly turned it off again.\n        const settingValueRaw = SettingsStore.getValue(\"breadcrumbs\", null, /*excludeDefault=*/ true);\n        if (this.meetsRoomRequirement && isNullOrUndefined(settingValueRaw)) {\n            await SettingsStore.setValue(\"breadcrumbs\", null, SettingLevel.ACCOUNT, true);\n        }\n    };\n\n    private onRoom = async (room: Room): Promise<void> => {\n        const waitingRoom = this.waitingRooms.find((r) => r.roomId === room.roomId);\n        if (!waitingRoom) return;\n        this.waitingRooms.splice(this.waitingRooms.indexOf(waitingRoom), 1);\n\n        if (Date.now() - waitingRoom.addedTs > AUTOJOIN_WAIT_THRESHOLD_MS) return; // Too long ago.\n        await this.appendRoom(room);\n    };\n\n    private async updateRooms(): Promise<void> {\n        let roomIds = SettingsStore.getValue(\"breadcrumb_rooms\");\n        if (!roomIds || roomIds.length === 0) roomIds = [];\n\n        const rooms = filterBoolean(roomIds.map((r) => this.matrixClient?.getRoom(r)));\n        const currentRooms = this.state.rooms || [];\n        if (!arrayHasDiff(rooms, currentRooms)) return; // no change (probably echo)\n        await this.updateState({ rooms });\n    }\n\n    private async appendRoom(room: Room): Promise<void> {\n        let updated = false;\n        const rooms = (this.state.rooms || []).slice(); // cheap clone\n        const msc3946ProcessDynamicPredecessor = SettingsStore.getValue(\"feature_dynamic_room_predecessors\");\n\n        // If the room is upgraded, use that room instead. We'll also splice out\n        // any children of the room.\n        const history = this.matrixClient?.getRoomUpgradeHistory(room.roomId, true, msc3946ProcessDynamicPredecessor);\n        if (history && history.length > 1) {\n            room = history[history.length - 1]; // Last room is most recent in history\n\n            // Take out any room that isn't the most recent room\n            for (let i = 0; i < history.length - 1; i++) {\n                const idx = rooms.findIndex((r) => r.roomId === history[i].roomId);\n                if (idx !== -1) {\n                    rooms.splice(idx, 1);\n                    updated = true;\n                }\n            }\n        }\n\n        // Remove the existing room, if it is present\n        const existingIdx = rooms.findIndex((r) => r.roomId === room.roomId);\n\n        // If we're focusing on the first room no-op\n        if (existingIdx !== 0) {\n            if (existingIdx !== -1) {\n                rooms.splice(existingIdx, 1);\n            }\n\n            // Splice the room to the start of the list\n            rooms.splice(0, 0, room);\n            updated = true;\n        }\n\n        if (rooms.length > MAX_ROOMS) {\n            // This looks weird, but it's saying to start at the MAX_ROOMS point in the\n            // list and delete everything after it.\n            rooms.splice(MAX_ROOMS, rooms.length - MAX_ROOMS);\n            updated = true;\n        }\n\n        if (updated) {\n            // Update the breadcrumbs\n            await this.updateState({ rooms });\n            const roomIds = rooms.map((r) => r.roomId);\n            if (roomIds.length > 0) {\n                await SettingsStore.setValue(\"breadcrumb_rooms\", null, SettingLevel.ACCOUNT, roomIds);\n            }\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type MatrixRTCSession, MatrixRTCSessionManagerEvents, type Transport } from \"matrix-js-sdk/src/matrixrtc\";\nimport { MatrixError, type EmptyObject, type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport { UPDATE_EVENT } from \"./AsyncStore\";\nimport { AsyncStoreWithClient } from \"./AsyncStoreWithClient\";\nimport WidgetStore from \"./WidgetStore\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { SettingLevel } from \"../settings/SettingLevel\";\nimport { Call, CallEvent, ConnectionState } from \"../models/Call\";\n\nexport enum CallStoreEvent {\n    // Signals a change in the call associated with a given room\n    Call = \"call\",\n    // Signals a change in the active calls\n    ConnectedCalls = \"connected_calls\",\n    // Signals a change in the configured RTC transports.\n    TransportsUpdated = \"transports_updated\",\n}\n\nexport class CallStore extends AsyncStoreWithClient<EmptyObject> {\n    private static _instance: CallStore;\n    public static get instance(): CallStore {\n        if (!this._instance) {\n            this._instance = new CallStore();\n            this._instance.start();\n        }\n        return this._instance;\n    }\n\n    private readonly configuredMatrixRTCTransports = new Set<Transport>();\n\n    private constructor() {\n        super(defaultDispatcher);\n        this.setMaxListeners(100); // One for each RoomTile\n    }\n\n    protected async onAction(): Promise<void> {\n        // nothing to do\n    }\n\n    /**\n     * Fetch transports used by MatrixRTC services, such as Element Call.\n     * This function is called once during Store startup which means we don't refetch\n     * transports every time we need to check for Element Call support.\n     */\n    protected async fetchTransports(): Promise<void> {\n        if (!this.matrixClient) return;\n        this.configuredMatrixRTCTransports.clear();\n        // Prefer checking the proper endpoint for transports.\n        try {\n            const transports = await this.matrixClient._unstable_getRTCTransports();\n            transports.forEach((t) => this.configuredMatrixRTCTransports.add(t));\n        } catch (ex) {\n            // Expected, MSC not implemented.\n            if (ex instanceof MatrixError === false || ex.errcode !== \"M_NOT_FOUND\") {\n                logger.warn(\"Unexpected error when trying to fetch RTC transports\", ex);\n            }\n        }\n        // See https://github.com/matrix-org/matrix-spec-proposals/blob/d61969a9a3696b6c54d7987b1643b5bc03670927/proposals/4143-matrix-rtc.md#discovery-of-foci-using-well-knownmatrixclient\n        // This well-known option has since been removed from the spec but is still widely deployed.\n        await this.matrixClient.waitForClientWellKnown();\n        const foci = this.matrixClient.getClientWellKnown()?.[\"org.matrix.msc4143.rtc_foci\"];\n        if (Array.isArray(foci)) {\n            foci.forEach((foci) => this.configuredMatrixRTCTransports.add(foci));\n        }\n        this.emit(CallStoreEvent.TransportsUpdated);\n    }\n\n    protected async onReady(): Promise<any> {\n        if (!this.matrixClient) return;\n        // Fetch transports, but don't await the result.\n        void this.fetchTransports();\n        // We assume that the calls present in a room are a function of room\n        // widgets and group calls, so we initialize the room map here and then\n        // update it whenever those change\n        for (const room of this.matrixClient.getRooms()) {\n            this.updateRoom(room);\n        }\n        this.matrixClient.matrixRTC.on(MatrixRTCSessionManagerEvents.SessionStarted, this.onRTCSessionStart);\n        WidgetStore.instance.on(UPDATE_EVENT, this.onWidgets);\n\n        // If the room ID of a previously connected call is still in settings at\n        // this time, that's a sign that we failed to disconnect from it\n        // properly, and need to clean up after ourselves\n        const uncleanlyDisconnectedRoomIds = SettingsStore.getValue(\"activeCallRoomIds\");\n        if (uncleanlyDisconnectedRoomIds.length) {\n            await Promise.all([\n                ...uncleanlyDisconnectedRoomIds.map(async (uncleanlyDisconnectedRoomId): Promise<void> => {\n                    logger.log(`Cleaning up call state for room ${uncleanlyDisconnectedRoomId}`);\n                    await this.getCall(uncleanlyDisconnectedRoomId)?.clean();\n                }),\n                SettingsStore.setValue(\"activeCallRoomIds\", null, SettingLevel.DEVICE, []),\n            ]);\n        }\n    }\n\n    protected async onNotReady(): Promise<any> {\n        for (const [call, listenerMap] of this.callListeners) {\n            // It's important that we remove the listeners before destroying the\n            // call, because otherwise the call's onDestroy callback would fire\n            // and immediately repopulate the map\n            for (const [event, listener] of listenerMap) call.off(event, listener);\n            call.destroy();\n        }\n        this.callListeners.clear();\n        this.calls.clear();\n        this._connectedCalls.clear();\n        this.configuredMatrixRTCTransports.clear();\n\n        this.matrixClient?.matrixRTC.off(MatrixRTCSessionManagerEvents.SessionStarted, this.onRTCSessionStart);\n        WidgetStore.instance.off(UPDATE_EVENT, this.onWidgets);\n    }\n\n    private _connectedCalls: Set<Call> = new Set();\n    /**\n     * The calls to which the user is currently connected.\n     */\n    public get connectedCalls(): Set<Call> {\n        return this._connectedCalls;\n    }\n    private set connectedCalls(value: Set<Call>) {\n        this._connectedCalls = value;\n        this.emit(CallStoreEvent.ConnectedCalls, value);\n\n        // The room IDs are persisted to settings so we can detect unclean disconnects\n        SettingsStore.setValue(\n            \"activeCallRoomIds\",\n            null,\n            SettingLevel.DEVICE,\n            [...value].map((call) => call.roomId),\n        );\n    }\n\n    private calls = new Map<string, Call>(); // Key is room ID\n    private callListeners = new Map<Call, Map<CallEvent, (...args: unknown[]) => unknown>>();\n\n    private inUpdateRoom = false;\n    private updateRoom(room: Room): void {\n        // XXX: This method is guarded with the flag this.inUpdateRoom because\n        // we need to block this method from calling itself recursively. That\n        // could happen, for instance, if Call.get adds a new virtual widget to\n        // the WidgetStore, firing a WidgetStore update that we don't actually\n        // care about. Without the guard we could get duplicate Call objects\n        // fighting for control over the same widget.\n        if (!this.inUpdateRoom && !this.calls.has(room.roomId)) {\n            this.inUpdateRoom = true;\n            const call = Call.get(room);\n\n            if (call) {\n                const onConnectionState = (state: ConnectionState): void => {\n                    if (state === ConnectionState.Connected) {\n                        this.connectedCalls = new Set([...this.connectedCalls, call]);\n                    } else if (state === ConnectionState.Disconnected) {\n                        this.connectedCalls = new Set([...this.connectedCalls].filter((c) => c !== call));\n                    }\n                };\n                const onDestroy = (): void => {\n                    this.calls.delete(room.roomId);\n                    for (const [event, listener] of this.callListeners.get(call)!) call.off(event, listener);\n                    this.updateRoom(room);\n                };\n\n                call.on(CallEvent.ConnectionState, onConnectionState);\n                call.on(CallEvent.Destroy, onDestroy);\n\n                this.calls.set(room.roomId, call);\n                this.callListeners.set(\n                    call,\n                    new Map<CallEvent, (...args: any[]) => unknown>([\n                        [CallEvent.ConnectionState, onConnectionState],\n                        [CallEvent.Destroy, onDestroy],\n                    ]),\n                );\n            }\n\n            this.emit(CallStoreEvent.Call, call, room.roomId);\n            this.inUpdateRoom = false;\n        }\n    }\n\n    /**\n     * Gets the call associated with the given room, if any.\n     * @param {string} roomId The room's ID.\n     * @returns {Call | null} The call.\n     */\n    public getCall(roomId: string): Call | null {\n        return this.calls.get(roomId) ?? null;\n    }\n\n    /**\n     * Gets the active call associated with the given room, if any.\n     * @param roomId The room's ID.\n     * @returns The active call.\n     */\n    public getActiveCall(roomId: string): Call | null {\n        const call = this.getCall(roomId);\n        return call !== null && this.connectedCalls.has(call) ? call : null;\n    }\n\n    private onWidgets = (roomId: string | null): void => {\n        if (!this.matrixClient) return;\n        if (roomId === null) {\n            // This store happened to start before the widget store was done\n            // loading all rooms, so we need to initialize each room again\n            for (const room of this.matrixClient.getRooms()) {\n                this.updateRoom(room);\n            }\n        } else {\n            const room = this.matrixClient.getRoom(roomId);\n            // Widget updates can arrive before the room does, empirically\n            if (room !== null) this.updateRoom(room);\n        }\n    };\n\n    public getConfiguredRTCTransports(): Transport[] {\n        return [...this.configuredMatrixRTCTransports];\n    }\n\n    private onRTCSessionStart = (roomId: string, session: MatrixRTCSession): void => {\n        this.updateRoom(session.room);\n    };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport EventEmitter from \"events\";\n\nimport { type ComponentClass } from \"../@types/common\";\nimport { UPDATE_EVENT } from \"./AsyncStore\";\n\nexport type ToastReference = symbol;\n\nexport default class NonUrgentToastStore extends EventEmitter {\n    private static _instance: NonUrgentToastStore;\n\n    private toasts = new Map<ToastReference, ComponentClass>();\n\n    public static get instance(): NonUrgentToastStore {\n        if (!NonUrgentToastStore._instance) {\n            NonUrgentToastStore._instance = new NonUrgentToastStore();\n        }\n        return NonUrgentToastStore._instance;\n    }\n\n    public get components(): ComponentClass[] {\n        return Array.from(this.toasts.values());\n    }\n\n    public addToast(c: ComponentClass): ToastReference {\n        const ref: ToastReference = Symbol();\n        this.toasts.set(ref, c);\n        this.emit(UPDATE_EVENT);\n        return ref;\n    }\n\n    public removeToast(ref: ToastReference): void {\n        this.toasts.delete(ref);\n        this.emit(UPDATE_EVENT);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { debounce } from \"lodash\";\nimport {\n    type Beacon,\n    type BeaconIdentifier,\n    BeaconEvent,\n    type MatrixEvent,\n    type Room,\n    type RoomMember,\n    type RoomState,\n    RoomStateEvent,\n    ContentHelpers,\n    type MBeaconInfoEventContent,\n    M_BEACON,\n} from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport { AsyncStoreWithClient } from \"./AsyncStoreWithClient\";\nimport { arrayDiff } from \"../utils/arrays\";\nimport {\n    type ClearWatchCallback,\n    GeolocationError,\n    mapGeolocationPositionToTimedGeo,\n    sortBeaconsByLatestCreation,\n    type TimedGeoUri,\n    watchPosition,\n    getCurrentPosition,\n} from \"../utils/beacon\";\nimport { doMaybeLocalRoomAction } from \"../utils/local-room\";\nimport SettingsStore from \"../settings/SettingsStore\";\n\nconst isOwnBeacon = (beacon: Beacon, userId: string): boolean => beacon.beaconInfoOwner === userId;\n\nexport enum OwnBeaconStoreEvent {\n    LivenessChange = \"OwnBeaconStore.LivenessChange\",\n    MonitoringLivePosition = \"OwnBeaconStore.MonitoringLivePosition\",\n    LocationPublishError = \"LocationPublishError\",\n    BeaconUpdateError = \"BeaconUpdateError\",\n}\n\nconst MOVING_UPDATE_INTERVAL = 5000;\nconst STATIC_UPDATE_INTERVAL = 30000;\n\nconst BAIL_AFTER_CONSECUTIVE_ERROR_COUNT = 2;\n\ntype OwnBeaconStoreState = {\n    beacons: Map<BeaconIdentifier, Beacon>;\n    beaconLocationPublishErrorCounts: Map<BeaconIdentifier, number>;\n    beaconUpdateErrors: Map<BeaconIdentifier, Error>;\n    beaconsByRoomId: Map<Room[\"roomId\"], Set<BeaconIdentifier>>;\n    liveBeaconIds: BeaconIdentifier[];\n};\n\nconst CREATED_BEACONS_KEY = \"mx_live_beacon_created_id\";\nconst removeLocallyCreateBeaconEventId = (eventId: string): void => {\n    const ids = getLocallyCreatedBeaconEventIds();\n    window.localStorage.setItem(CREATED_BEACONS_KEY, JSON.stringify(ids.filter((id) => id !== eventId)));\n};\nconst storeLocallyCreateBeaconEventId = (eventId: string): void => {\n    const ids = getLocallyCreatedBeaconEventIds();\n    window.localStorage.setItem(CREATED_BEACONS_KEY, JSON.stringify([...ids, eventId]));\n};\n\nconst getLocallyCreatedBeaconEventIds = (): string[] => {\n    let ids: string[];\n    try {\n        ids = JSON.parse(window.localStorage.getItem(CREATED_BEACONS_KEY) ?? \"[]\");\n        if (!Array.isArray(ids)) {\n            throw new Error(\"Invalid stored value\");\n        }\n    } catch (error) {\n        logger.error(\"Failed to retrieve locally created beacon event ids\", error);\n        ids = [];\n    }\n    return ids;\n};\nexport class OwnBeaconStore extends AsyncStoreWithClient<OwnBeaconStoreState> {\n    private static readonly internalInstance = (() => {\n        const instance = new OwnBeaconStore();\n        instance.start();\n        return instance;\n    })();\n    // users beacons, keyed by event type\n    public readonly beacons = new Map<BeaconIdentifier, Beacon>();\n    public readonly beaconsByRoomId = new Map<Room[\"roomId\"], Set<BeaconIdentifier>>();\n    /**\n     * Track over the wire errors for published positions\n     * Counts consecutive wire errors per beacon\n     * Reset on successful publish of location\n     */\n    public readonly beaconLocationPublishErrorCounts = new Map<BeaconIdentifier, number>();\n    public readonly beaconUpdateErrors = new Map<BeaconIdentifier, unknown>();\n    /**\n     * ids of live beacons\n     * ordered by creation time descending\n     */\n    private liveBeaconIds: BeaconIdentifier[] = [];\n    private locationInterval?: number;\n    private clearPositionWatch?: ClearWatchCallback;\n    /**\n     * Track when the last position was published\n     * So we can manually get position on slow interval\n     * when the target is stationary\n     */\n    private lastPublishedPositionTimestamp?: number;\n    /**\n     * Ref returned from watchSetting for the MSC3946 labs flag\n     */\n    private dynamicWatcherRef: string | undefined;\n\n    public constructor() {\n        super(defaultDispatcher);\n    }\n\n    public static get instance(): OwnBeaconStore {\n        return OwnBeaconStore.internalInstance;\n    }\n\n    /**\n     * True when we have live beacons\n     * and geolocation.watchPosition is active\n     */\n    public get isMonitoringLiveLocation(): boolean {\n        return !!this.clearPositionWatch;\n    }\n\n    protected async onNotReady(): Promise<void> {\n        if (this.matrixClient) {\n            this.matrixClient.removeListener(BeaconEvent.LivenessChange, this.onBeaconLiveness);\n            this.matrixClient.removeListener(BeaconEvent.New, this.onNewBeacon);\n            this.matrixClient.removeListener(BeaconEvent.Update, this.onUpdateBeacon);\n            this.matrixClient.removeListener(BeaconEvent.Destroy, this.onDestroyBeacon);\n            this.matrixClient.removeListener(RoomStateEvent.Members, this.onRoomStateMembers);\n        }\n        SettingsStore.unwatchSetting(this.dynamicWatcherRef);\n\n        this.clearBeacons();\n    }\n\n    private clearBeacons(): void {\n        this.beacons.forEach((beacon) => beacon.destroy());\n\n        this.stopPollingLocation();\n        this.beacons.clear();\n        this.beaconsByRoomId.clear();\n        this.liveBeaconIds = [];\n        this.beaconLocationPublishErrorCounts.clear();\n        this.beaconUpdateErrors.clear();\n    }\n\n    protected async onReady(): Promise<void> {\n        if (this.matrixClient) {\n            this.matrixClient.on(BeaconEvent.LivenessChange, this.onBeaconLiveness);\n            this.matrixClient.on(BeaconEvent.New, this.onNewBeacon);\n            this.matrixClient.on(BeaconEvent.Update, this.onUpdateBeacon);\n            this.matrixClient.on(BeaconEvent.Destroy, this.onDestroyBeacon);\n            this.matrixClient.on(RoomStateEvent.Members, this.onRoomStateMembers);\n        }\n        this.dynamicWatcherRef = SettingsStore.watchSetting(\n            \"feature_dynamic_room_predecessors\",\n            null,\n            this.reinitialiseBeaconState,\n        );\n\n        this.initialiseBeaconState();\n    }\n\n    protected async onAction(payload: ActionPayload): Promise<void> {\n        // we don't actually do anything here\n    }\n\n    public hasLiveBeacons = (roomId?: string): boolean => {\n        return !!this.getLiveBeaconIds(roomId).length;\n    };\n\n    /**\n     * Some live beacon has a wire error\n     * Optionally filter by room\n     */\n    public hasLocationPublishErrors = (roomId?: string): boolean => {\n        return this.getLiveBeaconIds(roomId).some(this.beaconHasLocationPublishError);\n    };\n\n    /**\n     * If a beacon has failed to publish position\n     * past the allowed consecutive failure count (BAIL_AFTER_CONSECUTIVE_ERROR_COUNT)\n     * Then consider it to have an error\n     */\n    public beaconHasLocationPublishError = (beaconId: string): boolean => {\n        const counts = this.beaconLocationPublishErrorCounts.get(beaconId);\n        return counts !== undefined && counts >= BAIL_AFTER_CONSECUTIVE_ERROR_COUNT;\n    };\n\n    public resetLocationPublishError = (beaconId: string): void => {\n        this.incrementBeaconLocationPublishErrorCount(beaconId, false);\n\n        // always publish to all live beacons together\n        // instead of just one that was changed\n        // to keep lastPublishedTimestamp simple\n        // and extra published locations don't hurt\n        this.publishCurrentLocationToBeacons();\n    };\n\n    public getLiveBeaconIds = (roomId?: string): string[] => {\n        if (!roomId) {\n            return this.liveBeaconIds;\n        }\n        return this.liveBeaconIds.filter((beaconId) => this.beaconsByRoomId.get(roomId)?.has(beaconId));\n    };\n\n    public getLiveBeaconIdsWithLocationPublishError = (roomId?: string): string[] => {\n        return this.getLiveBeaconIds(roomId).filter(this.beaconHasLocationPublishError);\n    };\n\n    public getBeaconById = (beaconId: string): Beacon | undefined => {\n        return this.beacons.get(beaconId);\n    };\n\n    public stopBeacon = async (beaconIdentifier: string): Promise<void> => {\n        const beacon = this.beacons.get(beaconIdentifier);\n        // if no beacon, or beacon is already explicitly set isLive: false\n        // do nothing\n        if (!beacon?.beaconInfo?.live) {\n            return;\n        }\n\n        await this.updateBeaconEvent(beacon, { live: false });\n        // prune from local store\n        removeLocallyCreateBeaconEventId(beacon.beaconInfoId);\n    };\n\n    /**\n     * Listeners\n     */\n\n    private onNewBeacon = (_event: MatrixEvent, beacon: Beacon): void => {\n        if (!this.matrixClient || !isOwnBeacon(beacon, this.matrixClient.getUserId()!)) {\n            return;\n        }\n        this.addBeacon(beacon);\n        this.checkLiveness();\n    };\n\n    /**\n     * This will be called when a beacon is replaced\n     */\n    private onUpdateBeacon = (_event: MatrixEvent, beacon: Beacon): void => {\n        if (!this.matrixClient || !isOwnBeacon(beacon, this.matrixClient.getUserId()!)) {\n            return;\n        }\n\n        this.checkLiveness();\n        beacon.monitorLiveness();\n    };\n\n    private onDestroyBeacon = (beaconIdentifier: BeaconIdentifier): void => {\n        // check if we care about this beacon\n        if (!this.beacons.has(beaconIdentifier)) {\n            return;\n        }\n\n        this.checkLiveness();\n    };\n\n    private onBeaconLiveness = (isLive: boolean, beacon: Beacon): void => {\n        // check if we care about this beacon\n        if (!this.beacons.has(beacon.identifier)) {\n            return;\n        }\n\n        // beacon expired, update beacon to un-alive state\n        if (!isLive) {\n            this.stopBeacon(beacon.identifier);\n        }\n\n        this.checkLiveness();\n\n        this.emit(OwnBeaconStoreEvent.LivenessChange, this.getLiveBeaconIds());\n    };\n\n    /**\n     * Check for changes in membership in rooms with beacons\n     * and stop monitoring beacons in rooms user is no longer member of\n     */\n    private onRoomStateMembers = (_event: MatrixEvent, roomState: RoomState, member: RoomMember): void => {\n        // no beacons for this room, ignore\n        if (\n            !this.matrixClient ||\n            !this.beaconsByRoomId.has(roomState.roomId) ||\n            member.userId !== this.matrixClient.getUserId()\n        ) {\n            return;\n        }\n\n        // TODO check powerlevels here\n        // in PSF-797\n\n        // stop watching beacons in rooms where user is no longer a member\n        if (member.membership === KnownMembership.Leave || member.membership === KnownMembership.Ban) {\n            this.beaconsByRoomId.get(roomState.roomId)?.forEach(this.removeBeacon);\n            this.beaconsByRoomId.delete(roomState.roomId);\n        }\n    };\n\n    /**\n     * State management\n     */\n\n    /**\n     * Live beacon ids that do not have wire errors\n     */\n    private get healthyLiveBeaconIds(): string[] {\n        return this.liveBeaconIds.filter(\n            (beaconId) => !this.beaconHasLocationPublishError(beaconId) && !this.beaconUpdateErrors.has(beaconId),\n        );\n    }\n\n    /**\n     * @internal public for test only\n     */\n    public reinitialiseBeaconState = (): void => {\n        this.clearBeacons();\n        this.initialiseBeaconState();\n    };\n\n    private initialiseBeaconState = (): void => {\n        if (!this.matrixClient) return;\n        const userId = this.matrixClient.getSafeUserId();\n        const visibleRooms = this.matrixClient.getVisibleRooms(\n            SettingsStore.getValue(\"feature_dynamic_room_predecessors\"),\n        );\n\n        visibleRooms.forEach((room) => {\n            const roomState = room.currentState;\n            const beacons = roomState.beacons;\n            const ownBeaconsArray = [...beacons.values()].filter((beacon) => isOwnBeacon(beacon, userId));\n            ownBeaconsArray.forEach((beacon) => this.addBeacon(beacon));\n        });\n\n        this.checkLiveness();\n    };\n\n    private addBeacon = (beacon: Beacon): void => {\n        this.beacons.set(beacon.identifier, beacon);\n\n        if (!this.beaconsByRoomId.has(beacon.roomId)) {\n            this.beaconsByRoomId.set(beacon.roomId, new Set<string>());\n        }\n\n        this.beaconsByRoomId.get(beacon.roomId)!.add(beacon.identifier);\n\n        beacon.monitorLiveness();\n    };\n\n    /**\n     * Remove listeners for a given beacon\n     * remove from state\n     * and update liveness if changed\n     */\n    private removeBeacon = (beaconId: string): void => {\n        if (!this.beacons.has(beaconId)) {\n            return;\n        }\n        this.beacons.get(beaconId)!.destroy();\n        this.beacons.delete(beaconId);\n\n        this.checkLiveness();\n    };\n\n    private checkLiveness = (): void => {\n        const locallyCreatedBeaconEventIds = getLocallyCreatedBeaconEventIds();\n        const prevLiveBeaconIds = this.getLiveBeaconIds();\n        this.liveBeaconIds = [...this.beacons.values()]\n            .filter(\n                (beacon) =>\n                    beacon.isLive &&\n                    // only beacons created on this device should be shared to\n                    locallyCreatedBeaconEventIds.includes(beacon.beaconInfoId),\n            )\n            .sort(sortBeaconsByLatestCreation)\n            .map((beacon) => beacon.identifier);\n\n        const diff = arrayDiff(prevLiveBeaconIds, this.liveBeaconIds);\n\n        if (diff.added.length || diff.removed.length) {\n            this.emit(OwnBeaconStoreEvent.LivenessChange, this.liveBeaconIds);\n        }\n\n        // publish current location immediately\n        // when there are new live beacons\n        // and we already have a live monitor\n        // so first position is published quickly\n        // even when target is stationary\n        //\n        // when there is no existing live monitor\n        // it will be created below by togglePollingLocation\n        // and publish first position quickly\n        if (diff.added.length && this.isMonitoringLiveLocation) {\n            this.publishCurrentLocationToBeacons();\n        }\n\n        // if overall liveness changed\n        if (!!prevLiveBeaconIds?.length !== !!this.liveBeaconIds.length) {\n            this.togglePollingLocation();\n        }\n    };\n\n    public createLiveBeacon = async (\n        roomId: Room[\"roomId\"],\n        beaconInfoContent: MBeaconInfoEventContent,\n    ): Promise<void> => {\n        if (!this.matrixClient) return;\n        // explicitly stop any live beacons this user has\n        // to ensure they remain stopped\n        // if the new replacing beacon is redacted\n        const existingLiveBeaconIdsForRoom = this.getLiveBeaconIds(roomId);\n        await Promise.all(existingLiveBeaconIdsForRoom.map((beaconId) => this.stopBeacon(beaconId)));\n\n        // eslint-disable-next-line camelcase\n        const { event_id } = await doMaybeLocalRoomAction(\n            roomId,\n            (actualRoomId: string) => this.matrixClient!.unstable_createLiveBeacon(actualRoomId, beaconInfoContent),\n            this.matrixClient,\n        );\n\n        storeLocallyCreateBeaconEventId(event_id);\n    };\n\n    /**\n     * Geolocation\n     */\n\n    private togglePollingLocation = (): void => {\n        if (!!this.liveBeaconIds.length) {\n            this.startPollingLocation();\n        } else {\n            this.stopPollingLocation();\n        }\n    };\n\n    private startPollingLocation = async (): Promise<void> => {\n        // clear any existing interval\n        this.stopPollingLocation();\n\n        try {\n            this.clearPositionWatch = watchPosition(this.onWatchedPosition, this.onGeolocationError);\n        } catch (error) {\n            if (error instanceof Error) {\n                this.onGeolocationError(error.message as GeolocationError);\n            } else {\n                console.error(\"Unexpected error\", error);\n            }\n            // don't set locationInterval if geolocation failed to setup\n            return;\n        }\n\n        this.locationInterval = window.setInterval(() => {\n            if (!this.lastPublishedPositionTimestamp) {\n                return;\n            }\n            // if position was last updated STATIC_UPDATE_INTERVAL ms ago or more\n            // get our position and publish it\n            if (this.lastPublishedPositionTimestamp <= Date.now() - STATIC_UPDATE_INTERVAL) {\n                this.publishCurrentLocationToBeacons();\n            }\n        }, STATIC_UPDATE_INTERVAL);\n\n        this.emit(OwnBeaconStoreEvent.MonitoringLivePosition);\n    };\n\n    private stopPollingLocation = (): void => {\n        clearInterval(this.locationInterval);\n        this.locationInterval = undefined;\n        this.lastPublishedPositionTimestamp = undefined;\n\n        if (this.clearPositionWatch) {\n            this.clearPositionWatch();\n            this.clearPositionWatch = undefined;\n        }\n\n        this.emit(OwnBeaconStoreEvent.MonitoringLivePosition);\n    };\n\n    private onWatchedPosition = (position: GeolocationPosition): void => {\n        const timedGeoPosition = mapGeolocationPositionToTimedGeo(position);\n\n        // if this is our first position, publish immediately\n        if (!this.lastPublishedPositionTimestamp) {\n            this.publishLocationToBeacons(timedGeoPosition);\n        } else {\n            this.debouncedPublishLocationToBeacons(timedGeoPosition);\n        }\n    };\n\n    private onGeolocationError = async (error: GeolocationError): Promise<void> => {\n        logger.error(\"Geolocation failed\", error);\n\n        // other errors are considered non-fatal\n        // and self recovering\n        if (![GeolocationError.Unavailable, GeolocationError.PermissionDenied].includes(error)) {\n            return;\n        }\n\n        this.stopPollingLocation();\n        // kill live beacons when location permissions are revoked\n        await Promise.all(this.liveBeaconIds.map(this.stopBeacon));\n    };\n\n    /**\n     * Gets the current location\n     * (as opposed to using watched location)\n     * and publishes it to all live beacons\n     */\n    private publishCurrentLocationToBeacons = async (): Promise<void> => {\n        try {\n            const position = await getCurrentPosition();\n            this.publishLocationToBeacons(mapGeolocationPositionToTimedGeo(position));\n        } catch (error) {\n            if (error instanceof Error) {\n                this.onGeolocationError(error.message as GeolocationError);\n            } else {\n                console.error(\"Unexpected error\", error);\n            }\n        }\n    };\n\n    /**\n     * MatrixClient api\n     */\n\n    /**\n     * Updates beacon with provided content update\n     * Records error in beaconUpdateErrors\n     * rethrows\n     */\n    private updateBeaconEvent = async (\n        beacon: Beacon,\n        update: Partial<ContentHelpers.BeaconInfoState>,\n    ): Promise<void> => {\n        const { description, timeout, timestamp, live, assetType } = {\n            ...beacon.beaconInfo,\n            ...update,\n        };\n\n        const updateContent = ContentHelpers.makeBeaconInfoContent(timeout, live, description, assetType, timestamp);\n\n        try {\n            await this.matrixClient!.unstable_setLiveBeacon(beacon.roomId, updateContent);\n            // cleanup any errors\n            const hadError = this.beaconUpdateErrors.has(beacon.identifier);\n            if (hadError) {\n                this.beaconUpdateErrors.delete(beacon.identifier);\n                this.emit(OwnBeaconStoreEvent.BeaconUpdateError, beacon.identifier, false);\n            }\n        } catch (error) {\n            logger.error(\"Failed to update beacon\", error);\n            this.beaconUpdateErrors.set(beacon.identifier, error);\n            this.emit(OwnBeaconStoreEvent.BeaconUpdateError, beacon.identifier, true);\n\n            throw error;\n        }\n    };\n\n    /**\n     * Sends m.location events to all live beacons\n     * Sets last published beacon\n     */\n    private publishLocationToBeacons = async (position: TimedGeoUri): Promise<void> => {\n        this.lastPublishedPositionTimestamp = Date.now();\n        await Promise.all(\n            this.healthyLiveBeaconIds.map((beaconId) =>\n                this.beacons.has(beaconId) ? this.sendLocationToBeacon(this.beacons.get(beaconId)!, position) : null,\n            ),\n        );\n    };\n\n    private debouncedPublishLocationToBeacons = debounce(this.publishLocationToBeacons, MOVING_UPDATE_INTERVAL);\n\n    /**\n     * Sends m.location event to referencing given beacon\n     */\n    private sendLocationToBeacon = async (beacon: Beacon, { geoUri, timestamp }: TimedGeoUri): Promise<void> => {\n        const content = ContentHelpers.makeBeaconContent(geoUri, timestamp, beacon.beaconInfoId);\n        try {\n            await this.matrixClient!.sendEvent(beacon.roomId, M_BEACON.name, content);\n            this.incrementBeaconLocationPublishErrorCount(beacon.identifier, false);\n        } catch (error) {\n            logger.error(error);\n            this.incrementBeaconLocationPublishErrorCount(beacon.identifier, true);\n        }\n    };\n\n    /**\n     * Manage beacon wire error count\n     * - clear count for beacon when not error\n     * - increment count for beacon when is error\n     * - emit if beacon error count crossed threshold\n     */\n    private incrementBeaconLocationPublishErrorCount = (beaconId: string, isError: boolean): void => {\n        const hadError = this.beaconHasLocationPublishError(beaconId);\n\n        if (isError) {\n            // increment error count\n            this.beaconLocationPublishErrorCounts.set(\n                beaconId,\n                (this.beaconLocationPublishErrorCounts.get(beaconId) ?? 0) + 1,\n            );\n        } else {\n            // clear any error count\n            this.beaconLocationPublishErrorCounts.delete(beaconId);\n        }\n\n        if (this.beaconHasLocationPublishError(beaconId) !== hadError) {\n            this.emit(OwnBeaconStoreEvent.LocationPublishError, beaconId);\n        }\n    };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type MatrixEvent,\n    RoomStateEvent,\n    MatrixError,\n    type User,\n    UserEvent,\n    EventType,\n} from \"matrix-js-sdk/src/matrix\";\nimport { throttle } from \"lodash\";\n\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport { AsyncStoreWithClient } from \"./AsyncStoreWithClient\";\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { _t } from \"../languageHandler\";\nimport { mediaFromMxc } from \"../customisations/Media\";\n\ninterface IState {\n    displayName?: string;\n    avatarUrl?: string;\n    fetchedAt?: number;\n}\n\nconst KEY_DISPLAY_NAME = \"mx_profile_displayname\";\nconst KEY_AVATAR_URL = \"mx_profile_avatar_url\";\n\nexport class OwnProfileStore extends AsyncStoreWithClient<IState> {\n    private static readonly internalInstance = (() => {\n        const instance = new OwnProfileStore();\n        instance.start();\n        return instance;\n    })();\n\n    private monitoredUser: User | null = null;\n\n    public constructor() {\n        // seed from localstorage because otherwise we won't get these values until a whole network\n        // round-trip after the client is ready, and we often load widgets in that time, and we'd\n        // and up passing them an incorrect display name\n        super(defaultDispatcher, {\n            displayName: window.localStorage.getItem(KEY_DISPLAY_NAME) || undefined,\n            avatarUrl: window.localStorage.getItem(KEY_AVATAR_URL) || undefined,\n        });\n    }\n\n    public static get instance(): OwnProfileStore {\n        return OwnProfileStore.internalInstance;\n    }\n\n    /**\n     * Gets the display name for the user, or null if not present.\n     */\n    public get displayName(): string | null {\n        if (!this.matrixClient) return this.state.displayName || null;\n\n        if (this.matrixClient.isGuest()) {\n            return _t(\"common|guest\");\n        } else if (this.state.displayName) {\n            return this.state.displayName;\n        } else {\n            return this.matrixClient.getUserId();\n        }\n    }\n\n    public get isProfileInfoFetched(): boolean {\n        return !!this.state.fetchedAt;\n    }\n\n    /**\n     * Gets the MXC URI of the user's avatar, or null if not present.\n     */\n    public get avatarMxc(): string | null {\n        return this.state.avatarUrl || null;\n    }\n\n    /**\n     * Gets the user's avatar as an HTTP URL of the given size. If the user's\n     * avatar is not present, this returns null.\n     * @param size The size of the avatar. If zero, a full res copy of the avatar\n     * will be returned as an HTTP URL.\n     * @returns The HTTP URL of the user's avatar\n     */\n    public getHttpAvatarUrl(size = 0): string | null {\n        if (!this.avatarMxc) return null;\n        const media = mediaFromMxc(this.avatarMxc);\n        if (!size || size <= 0) {\n            return media.srcHttp;\n        } else {\n            return media.getSquareThumbnailHttp(size);\n        }\n    }\n\n    protected async onNotReady(): Promise<void> {\n        this.onProfileUpdate.cancel();\n        if (this.monitoredUser) {\n            this.monitoredUser.removeListener(UserEvent.DisplayName, this.onProfileUpdate);\n            this.monitoredUser.removeListener(UserEvent.AvatarUrl, this.onProfileUpdate);\n        }\n        this.matrixClient?.removeListener(RoomStateEvent.Events, this.onStateEvents);\n        await this.reset({});\n    }\n\n    protected async onReady(): Promise<void> {\n        if (!this.matrixClient) return;\n        const myUserId = this.matrixClient.getSafeUserId();\n        this.monitoredUser = this.matrixClient.getUser(myUserId);\n        if (this.monitoredUser) {\n            this.monitoredUser.on(UserEvent.DisplayName, this.onProfileUpdate);\n            this.monitoredUser.on(UserEvent.AvatarUrl, this.onProfileUpdate);\n        }\n\n        // We also have to listen for membership events for ourselves as the above User events\n        // are fired only with presence, which matrix.org (and many others) has disabled.\n        this.matrixClient.on(RoomStateEvent.Events, this.onStateEvents);\n\n        await this.onProfileUpdate(); // trigger an initial update\n    }\n\n    protected async onAction(payload: ActionPayload): Promise<void> {\n        // we don't actually do anything here\n    }\n\n    private onProfileUpdate = throttle(\n        async (): Promise<void> => {\n            if (!this.matrixClient) return;\n            // We specifically do not use the User object we stored for profile info as it\n            // could easily be wrong (such as per-room instead of global profile).\n\n            let profileInfo: { displayname?: string; avatar_url?: string } = {\n                displayname: undefined,\n                avatar_url: undefined,\n            };\n\n            try {\n                profileInfo = await this.matrixClient.getProfileInfo(this.matrixClient.getSafeUserId());\n            } catch (error: unknown) {\n                if (!(error instanceof MatrixError) || error.errcode !== \"M_NOT_FOUND\") {\n                    /**\n                     * Raise any other error than M_NOT_FOUND.\n                     * M_NOT_FOUND could occur if there is no user profile.\n                     * {@link https://spec.matrix.org/v1.7/client-server-api/#get_matrixclientv3profileuserid}\n                     * We should then assume an empty profile, emit UPDATE_EVENT etc..\n                     */\n                    throw error;\n                }\n            }\n\n            if (profileInfo.displayname) {\n                window.localStorage.setItem(KEY_DISPLAY_NAME, profileInfo.displayname);\n            } else {\n                window.localStorage.removeItem(KEY_DISPLAY_NAME);\n            }\n\n            if (profileInfo.avatar_url) {\n                window.localStorage.setItem(KEY_AVATAR_URL, profileInfo.avatar_url);\n            } else {\n                window.localStorage.removeItem(KEY_AVATAR_URL);\n            }\n\n            await this.updateState({\n                displayName: profileInfo.displayname,\n                avatarUrl: profileInfo.avatar_url,\n                fetchedAt: Date.now(),\n            });\n        },\n        200,\n        { trailing: true, leading: true },\n    );\n\n    private onStateEvents = async (ev: MatrixEvent): Promise<void> => {\n        const myUserId = MatrixClientPeg.safeGet().getUserId();\n        if (ev.getType() === EventType.RoomMember && ev.getSender() === myUserId && ev.getStateKey() === myUserId) {\n            await this.onProfileUpdate();\n        }\n    };\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2021, 2022 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type MatrixClient, SyncState } from \"matrix-js-sdk/src/matrix\";\nimport { EventEmitter } from \"events\";\n\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport { type IDestroyable } from \"../utils/IDestroyable\";\nimport { Action } from \"../dispatcher/actions\";\nimport { type MatrixDispatcher } from \"../dispatcher/dispatcher\";\n\nexport abstract class ReadyWatchingStore extends EventEmitter implements IDestroyable {\n    protected matrixClient?: MatrixClient;\n    private dispatcherRef?: string;\n\n    public constructor(protected readonly dispatcher: MatrixDispatcher) {\n        super();\n    }\n\n    public async start(): Promise<void> {\n        this.dispatcherRef = this.dispatcher.register(this.onAction);\n\n        // MatrixClientPeg can be undefined in tests because of circular dependencies with other stores\n        const matrixClient = MatrixClientPeg?.get();\n        if (matrixClient) {\n            this.matrixClient = matrixClient;\n            await this.onReady();\n        }\n    }\n\n    public get mxClient(): MatrixClient | null {\n        return this.matrixClient ?? null; // for external readonly access\n    }\n\n    public useUnitTestClient(cli: MatrixClient): void {\n        this.matrixClient = cli;\n    }\n\n    public destroy(): void {\n        this.dispatcher.unregister(this.dispatcherRef);\n    }\n\n    protected async onReady(): Promise<void> {\n        // Default implementation is to do nothing.\n    }\n\n    protected async onNotReady(): Promise<void> {\n        // Default implementation is to do nothing.\n    }\n\n    protected onDispatcherAction(payload: ActionPayload): void {\n        // Default implementation is to do nothing.\n    }\n\n    private onAction = async (payload: ActionPayload): Promise<void> => {\n        this.onDispatcherAction(payload);\n\n        if (payload.action === \"MatrixActions.sync\") {\n            // Only set the client on the transition into the PREPARED state.\n            // Everything after this is unnecessary (we only need to know once we have a client)\n            // and we intentionally don't set the client before this point to avoid stores\n            // updating for every event emitted during the cached sync.\n            if (\n                payload.prevState !== SyncState.Prepared &&\n                payload.state === SyncState.Prepared &&\n                this.matrixClient !== payload.matrixClient\n            ) {\n                if (this.matrixClient) {\n                    await this.onNotReady();\n                }\n                this.matrixClient = payload.matrixClient;\n                await this.onReady();\n            }\n        } else if (payload.action === Action.ClientNotViable || payload.action === Action.OnLoggedOut) {\n            if (this.matrixClient) {\n                await this.onNotReady();\n                this.matrixClient = undefined;\n            }\n        }\n    };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport EventEmitter from \"events\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type JSX } from \"react\";\n\nimport type React from \"react\";\nimport { type ComponentClass } from \"../@types/common\";\n\nexport interface IToast<C extends ComponentClass> {\n    key: string;\n    // higher priority number will be shown on top of lower priority\n    priority: number;\n    title?: string;\n    icon?: JSX.Element;\n    component: C;\n    className?: string;\n    bodyClassName?: string;\n\n    /**\n     * What to do if the user clicks the close button. If this is undefined, the\n     * close button is not displayed.\n     *\n     * Note: the close button is only displayed if the toast has a title (i.e. if {@link title} is truthy).\n     */\n    onCloseButtonClicked?: () => void;\n\n    props?: Omit<React.ComponentProps<C>, \"toastKey\">; // toastKey is injected by ToastContainer\n}\n\n/**\n * Holds the active toasts\n */\nexport default class ToastStore extends EventEmitter {\n    private toasts: IToast<any>[] = [];\n\n    public static sharedInstance(): ToastStore {\n        if (!window.mxToastStore) window.mxToastStore = new ToastStore();\n        return window.mxToastStore;\n    }\n\n    public reset(): void {\n        this.toasts = [];\n    }\n\n    /**\n     * Add or replace a toast\n     * If a toast with the same toastKey already exists, the given toast will replace it\n     * Toasts are always added underneath any toasts of the same priority, so existing\n     * toasts stay at the top unless a higher priority one arrives (better to not change the\n     * toast unless necessary).\n     *\n     * @param {object} newToast The new toast\n     */\n    public addOrReplaceToast<C extends ComponentClass>(newToast: IToast<C>): void {\n        const oldIndex = this.toasts.findIndex((t) => t.key === newToast.key);\n        if (oldIndex === -1) {\n            logger.info(`Opening toast with key '${newToast.key}': title '${newToast.title}'`);\n            let newIndex = this.toasts.length;\n            while (newIndex > 0 && this.toasts[newIndex - 1].priority < newToast.priority) --newIndex;\n            this.toasts.splice(newIndex, 0, newToast);\n        } else {\n            logger.info(`Replacing existing toast with key '${newToast.key}': title now '${newToast.title}'`);\n            this.toasts[oldIndex] = newToast;\n        }\n        this.emit(\"update\");\n    }\n\n    public dismissToast(key: string): void {\n        const length = this.toasts.length;\n        this.toasts = this.toasts.filter((t) => t.key !== key);\n        if (length !== this.toasts.length) {\n            logger.info(`Removed toast with key '${key}'`);\n            this.emit(\"update\");\n        }\n    }\n\n    /**\n     * Is a toast currently present on the store.\n     * @param key The toast key to look for.\n     */\n    public hasToast(key: string): boolean {\n        return this.toasts.some((toast) => toast.key === key);\n    }\n\n    public getToasts(): IToast<any>[] {\n        return this.toasts;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport EventEmitter from \"events\";\n\nexport enum UI_EVENTS {\n    Resize = \"resize\",\n}\n\nexport default class UIStore extends EventEmitter {\n    private static _instance: UIStore | null = null;\n\n    private resizeObserver: ResizeObserver;\n\n    private uiElementDimensions = new Map<string, DOMRectReadOnly>();\n    private trackedUiElements = new Map<Element, string>();\n\n    public windowWidth: number;\n    public windowHeight: number;\n\n    public constructor() {\n        super();\n\n        // eslint-disable-next-line no-restricted-properties\n        this.windowWidth = window.innerWidth;\n        // eslint-disable-next-line no-restricted-properties\n        this.windowHeight = window.innerHeight;\n\n        this.resizeObserver = new ResizeObserver(this.resizeObserverCallback);\n        this.resizeObserver.observe(document.body);\n    }\n\n    public static get instance(): UIStore {\n        if (!UIStore._instance) {\n            UIStore._instance = new UIStore();\n        }\n        return UIStore._instance;\n    }\n\n    public static destroy(): void {\n        if (UIStore._instance) {\n            UIStore._instance.resizeObserver.disconnect();\n            UIStore._instance.removeAllListeners();\n            UIStore._instance = null;\n        }\n    }\n\n    public getElementDimensions(name: string): DOMRectReadOnly | undefined {\n        return this.uiElementDimensions.get(name);\n    }\n\n    public trackElementDimensions(name: string, element: Element): void {\n        this.trackedUiElements.set(element, name);\n        this.resizeObserver.observe(element);\n    }\n\n    public stopTrackingElementDimensions(name: string): void {\n        let trackedElement: Element | undefined;\n        this.trackedUiElements.forEach((trackedElementName, element) => {\n            if (trackedElementName === name) {\n                trackedElement = element;\n            }\n        });\n        if (trackedElement) {\n            this.resizeObserver.unobserve(trackedElement);\n            this.uiElementDimensions.delete(name);\n            this.trackedUiElements.delete(trackedElement);\n        }\n    }\n\n    public isTrackingElementDimensions(name: string): boolean {\n        return this.uiElementDimensions.has(name);\n    }\n\n    private resizeObserverCallback = (entries: ResizeObserverEntry[]): void => {\n        const windowEntry = entries.find((entry) => entry.target === document.body);\n\n        if (windowEntry) {\n            this.windowWidth = windowEntry.contentRect.width;\n            this.windowHeight = windowEntry.contentRect.height;\n        }\n\n        entries.forEach((entry) => {\n            const trackedElementName = this.trackedUiElements.get(entry.target);\n            if (trackedElementName) {\n                this.uiElementDimensions.set(trackedElementName, entry.contentRect);\n                this.emit(trackedElementName, UI_EVENTS.Resize, entry);\n            }\n        });\n\n        this.emit(UI_EVENTS.Resize, entries);\n    };\n}\n\nwindow.mxUIStore = UIStore.instance;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport EventEmitter from \"events\";\nimport { type IWidget } from \"matrix-widget-api\";\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { type WidgetType } from \"../widgets/WidgetType\";\n\n/**\n * Acts as a place to get & set widget state, storing local echo state and\n * proxying through state from the js-sdk.\n */\nclass WidgetEchoStore extends EventEmitter {\n    private roomWidgetEcho: {\n        [roomId: string]: {\n            [widgetId: string]: IWidget;\n        };\n    };\n\n    public constructor() {\n        super();\n\n        this.roomWidgetEcho = {\n            // Map as below. Object is the content of the widget state event,\n            // so for widgets that have been deleted locally, the object is empty.\n            // roomId: {\n            //     widgetId: IWidget\n            // }\n        };\n    }\n\n    /**\n     * Gets the widgets for a room, subtracting those that are pending deletion.\n     * Widgets that are pending addition are not included, since widgets are\n     * represented as MatrixEvents, so to do this we'd have to create fake MatrixEvents,\n     * and we don't really need the actual widget events anyway since we just want to\n     * show a spinner / prevent widgets being added twice.\n     *\n     * @param {string} roomId The ID of the room to get widgets for\n     * @param {MatrixEvent[]} currentRoomWidgets Current widgets for the room\n     * @returns {MatrixEvent[]} List of widgets in the room, minus any pending removal\n     */\n    public getEchoedRoomWidgets(roomId: string, currentRoomWidgets: MatrixEvent[]): MatrixEvent[] {\n        const echoedWidgets: MatrixEvent[] = [];\n\n        const roomEchoState = Object.assign({}, this.roomWidgetEcho[roomId]);\n\n        for (const w of currentRoomWidgets) {\n            const widgetId = w.getStateKey()!;\n            // If there's no echo, or the echo still has a widget present, show the *old* widget\n            // we don't include widgets that have changed for the same reason we don't include new ones,\n            // ie. we'd need to fake matrix events to do so and there's currently no need.\n            if (!roomEchoState[widgetId] || Object.keys(roomEchoState[widgetId]).length !== 0) {\n                echoedWidgets.push(w);\n            }\n            delete roomEchoState[widgetId];\n        }\n\n        return echoedWidgets;\n    }\n\n    public roomHasPendingWidgetsOfType(roomId: string, currentRoomWidgets: MatrixEvent[], type?: WidgetType): boolean {\n        const roomEchoState = Object.assign({}, this.roomWidgetEcho[roomId]);\n\n        // any widget IDs that are already in the room are not pending, so\n        // echoes for them don't count as pending.\n        for (const w of currentRoomWidgets) {\n            const widgetId = w.getStateKey()!;\n            delete roomEchoState[widgetId];\n        }\n\n        // if there's anything left then there are pending widgets.\n        if (type === undefined) {\n            return Object.keys(roomEchoState).length > 0;\n        } else {\n            return Object.values(roomEchoState).some((widget) => {\n                return type.matches(widget.type);\n            });\n        }\n    }\n\n    public roomHasPendingWidgets(roomId: string, currentRoomWidgets: MatrixEvent[]): boolean {\n        return this.roomHasPendingWidgetsOfType(roomId, currentRoomWidgets);\n    }\n\n    public setRoomWidgetEcho(roomId: string, widgetId: string, state: IWidget): void {\n        if (this.roomWidgetEcho[roomId] === undefined) this.roomWidgetEcho[roomId] = {};\n\n        this.roomWidgetEcho[roomId][widgetId] = state;\n        this.emit(\"update\", roomId, widgetId);\n    }\n\n    public removeRoomWidgetEcho(roomId: string, widgetId: string): void {\n        delete this.roomWidgetEcho[roomId][widgetId];\n        if (Object.keys(this.roomWidgetEcho[roomId]).length === 0) delete this.roomWidgetEcho[roomId];\n        this.emit(\"update\", roomId, widgetId);\n    }\n}\n\nlet singletonWidgetEchoStore: WidgetEchoStore | null = null;\nif (!singletonWidgetEchoStore) {\n    singletonWidgetEchoStore = new WidgetEchoStore();\n}\nexport default singletonWidgetEchoStore!;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room, RoomStateEvent, type MatrixEvent, ClientEvent, type EmptyObject } from \"matrix-js-sdk/src/matrix\";\nimport { type IWidget } from \"matrix-widget-api\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport { AsyncStoreWithClient } from \"./AsyncStoreWithClient\";\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport WidgetEchoStore from \"../stores/WidgetEchoStore\";\nimport ActiveWidgetStore from \"../stores/ActiveWidgetStore\";\nimport WidgetUtils from \"../utils/WidgetUtils\";\nimport { UPDATE_EVENT } from \"./AsyncStore\";\nimport { type IApp } from \"../utils/WidgetUtils-types\";\n\nexport type { IApp };\n\nexport function isAppWidget(widget: IWidget | IApp): widget is IApp {\n    return \"roomId\" in widget && typeof widget.roomId === \"string\";\n}\nexport function isVirtualWidget(widget: IApp): boolean {\n    return widget.eventId === undefined;\n}\n\ninterface IRoomWidgets {\n    widgets: IApp[];\n}\n\n// TODO consolidate WidgetEchoStore into this\n// TODO consolidate ActiveWidgetStore into this\nexport default class WidgetStore extends AsyncStoreWithClient<EmptyObject> {\n    private static readonly internalInstance = (() => {\n        const instance = new WidgetStore();\n        instance.start();\n        return instance;\n    })();\n\n    private widgetMap = new Map<string, IApp>(); // Key is widget Unique ID (UID)\n    private roomMap = new Map<string, IRoomWidgets>(); // Key is room ID\n\n    private constructor() {\n        super(defaultDispatcher, {});\n\n        WidgetEchoStore.on(\"update\", this.onWidgetEchoStoreUpdate);\n    }\n\n    public static get instance(): WidgetStore {\n        return WidgetStore.internalInstance;\n    }\n\n    private initRoom(roomId: string): void {\n        if (!this.roomMap.has(roomId)) {\n            this.roomMap.set(roomId, {\n                widgets: [],\n            });\n        }\n    }\n\n    protected async onReady(): Promise<any> {\n        if (!this.matrixClient) return;\n        this.matrixClient.on(ClientEvent.Room, this.onRoom);\n        this.matrixClient.on(RoomStateEvent.Events, this.onRoomStateEvents);\n        this.matrixClient.getRooms().forEach((room: Room) => {\n            this.loadRoomWidgets(room);\n        });\n        this.emit(UPDATE_EVENT, null); // emit for all rooms\n    }\n\n    protected async onNotReady(): Promise<any> {\n        if (this.matrixClient) {\n            this.matrixClient.off(ClientEvent.Room, this.onRoom);\n            this.matrixClient.off(RoomStateEvent.Events, this.onRoomStateEvents);\n        }\n        this.widgetMap = new Map();\n        this.roomMap = new Map();\n        await this.reset({});\n    }\n\n    // We don't need this, but our contract says we do.\n    protected async onAction(payload: ActionPayload): Promise<void> {\n        return;\n    }\n\n    private onWidgetEchoStoreUpdate = (roomId: string): void => {\n        this.initRoom(roomId);\n        this.loadRoomWidgets(this.matrixClient?.getRoom(roomId) ?? null);\n        this.emit(UPDATE_EVENT, roomId);\n    };\n\n    private generateApps(room: Room): IApp[] {\n        return WidgetEchoStore.getEchoedRoomWidgets(room.roomId, WidgetUtils.getRoomWidgets(room)).map((ev) => {\n            return WidgetUtils.makeAppConfig(\n                ev.getStateKey()!,\n                ev.getContent(),\n                ev.getSender()!,\n                ev.getRoomId(),\n                ev.getId(),\n            );\n        });\n    }\n\n    private loadRoomWidgets(room: Room | null): void {\n        if (!room) return;\n        const roomInfo = this.roomMap.get(room.roomId) || <IRoomWidgets>{};\n        roomInfo.widgets = [];\n\n        // first clean out old widgets from the map which originate from this room\n        // otherwise we are out of sync with the rest of the app with stale widget events during removal\n        Array.from(this.widgetMap.values()).forEach((app) => {\n            if (app.roomId !== room.roomId) return; // skip - wrong room\n            if (isVirtualWidget(app)) {\n                // virtual widget - keep it\n                roomInfo.widgets.push(app);\n            } else {\n                this.widgetMap.delete(WidgetUtils.getWidgetUid(app));\n            }\n        });\n\n        let edited = false;\n        this.generateApps(room).forEach((app) => {\n            // Sanity check for https://github.com/vector-im/element-web/issues/15705\n            const existingApp = this.widgetMap.get(WidgetUtils.getWidgetUid(app));\n            if (existingApp) {\n                logger.warn(\n                    `Possible widget ID conflict for ${app.id} - wants to store in room ${app.roomId} ` +\n                        `but is currently stored as ${existingApp.roomId} - letting the want win`,\n                );\n            }\n\n            this.widgetMap.set(WidgetUtils.getWidgetUid(app), app);\n            roomInfo.widgets.push(app);\n            edited = true;\n        });\n        if (edited && !this.roomMap.has(room.roomId)) {\n            this.roomMap.set(room.roomId, roomInfo);\n        }\n\n        // If a persistent widget is active, check to see if it's just been removed.\n        // If it has, it needs to destroyed otherwise unmounting the node won't kill it\n        const persistentWidgetId = ActiveWidgetStore.instance.getPersistentWidgetId();\n        if (\n            persistentWidgetId &&\n            ActiveWidgetStore.instance.getPersistentRoomId() === room.roomId &&\n            !roomInfo.widgets.some((w) => w.id === persistentWidgetId)\n        ) {\n            logger.log(`Persistent widget ${persistentWidgetId} removed from room ${room.roomId}: destroying.`);\n            ActiveWidgetStore.instance.destroyPersistentWidget(persistentWidgetId, room.roomId);\n        }\n\n        this.emit(room.roomId);\n    }\n\n    private onRoom = (room: Room): void => {\n        this.initRoom(room.roomId);\n        this.loadRoomWidgets(room);\n        this.emit(UPDATE_EVENT, room.roomId);\n    };\n\n    private onRoomStateEvents = (ev: MatrixEvent): void => {\n        if (ev.getType() !== \"im.vector.modular.widgets\") return; // TODO: Support m.widget too\n        const roomId = ev.getRoomId()!;\n        this.initRoom(roomId);\n        this.loadRoomWidgets(this.matrixClient?.getRoom(roomId) ?? null);\n        this.emit(UPDATE_EVENT, roomId);\n    };\n\n    public get(widgetId: string, roomId: string | undefined): IApp | undefined {\n        return this.widgetMap.get(WidgetUtils.calcWidgetUid(widgetId, roomId));\n    }\n\n    public getRoom(roomId: string, initIfNeeded = false): IRoomWidgets {\n        if (initIfNeeded) this.initRoom(roomId); // internally handles \"if needed\"\n        return this.roomMap.get(roomId)!;\n    }\n\n    public getApps(roomId: string): IApp[] {\n        const roomInfo = this.getRoom(roomId);\n        return roomInfo?.widgets || [];\n    }\n\n    public addVirtualWidget(widget: IWidget, roomId: string): IApp {\n        this.initRoom(roomId);\n        const app = WidgetUtils.makeAppConfig(widget.id, widget, widget.creatorUserId, roomId, undefined);\n        this.widgetMap.set(WidgetUtils.getWidgetUid(app), app);\n        this.roomMap.get(roomId)!.widgets.push(app);\n        this.emit(UPDATE_EVENT, roomId);\n        return app;\n    }\n\n    public removeVirtualWidget(widgetId: string, roomId: string): void {\n        this.widgetMap.delete(WidgetUtils.calcWidgetUid(widgetId, roomId));\n        const roomApps = this.roomMap.get(roomId);\n        if (roomApps) {\n            roomApps.widgets = roomApps.widgets.filter((app) => !(app.id === widgetId && app.roomId === roomId));\n        }\n        this.emit(UPDATE_EVENT, roomId);\n    }\n}\n\nwindow.mxWidgetStore = WidgetStore.instance;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EchoTransaction, type RunFn, TransactionStatus } from \"./EchoTransaction\";\nimport { arrayFastClone } from \"../../utils/arrays\";\nimport { type IDestroyable } from \"../../utils/IDestroyable\";\nimport { Whenable } from \"../../utils/Whenable\";\n\nexport enum ContextTransactionState {\n    NotStarted,\n    PendingErrors,\n    AllSuccessful,\n}\n\nexport abstract class EchoContext extends Whenable<ContextTransactionState> implements IDestroyable {\n    private _transactions: EchoTransaction[] = [];\n    private _state = ContextTransactionState.NotStarted;\n\n    public get transactions(): EchoTransaction[] {\n        return arrayFastClone(this._transactions);\n    }\n\n    public get state(): ContextTransactionState {\n        return this._state;\n    }\n\n    public get firstFailedTime(): Date | null {\n        const failedTxn = this.transactions.find((t) => t.didPreviouslyFail || t.status === TransactionStatus.Error);\n        if (failedTxn) return failedTxn.startTime;\n        return null;\n    }\n\n    public disownTransaction(txn: EchoTransaction): void {\n        const idx = this._transactions.indexOf(txn);\n        if (idx >= 0) this._transactions.splice(idx, 1);\n        txn.destroy();\n        this.checkTransactions();\n    }\n\n    public beginTransaction(auditName: string, runFn: RunFn): EchoTransaction {\n        const txn = new EchoTransaction(auditName, runFn);\n        this._transactions.push(txn);\n        txn.whenAnything(this.checkTransactions);\n\n        // We have no intent to call the transaction again if it succeeds (in fact, it'll\n        // be really angry at us if we do), so call that the end of the road for the events.\n        txn.when(TransactionStatus.Success, () => txn.destroy());\n\n        return txn;\n    }\n\n    private checkTransactions = (): void => {\n        let status = ContextTransactionState.AllSuccessful;\n        for (const txn of this.transactions) {\n            if (txn.status === TransactionStatus.Error || txn.didPreviouslyFail) {\n                status = ContextTransactionState.PendingErrors;\n                break;\n            } else if (txn.status === TransactionStatus.Pending) {\n                status = ContextTransactionState.NotStarted;\n                // no break as we might hit something which broke\n            }\n        }\n        this._state = status;\n        this.notifyCondition(status);\n    };\n\n    public destroy(): void {\n        for (const txn of this.transactions) {\n            txn.destroy();\n        }\n        this._transactions = [];\n        super.destroy();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { EchoContext } from \"./EchoContext\";\n\nexport class RoomEchoContext extends EchoContext {\n    public constructor(public readonly room: Room) {\n        super();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ReactNode } from \"react\";\n\nimport BaseDialog from \"./BaseDialog\";\nimport { _t } from \"../../../languageHandler\";\nimport { EchoStore } from \"../../../stores/local-echo/EchoStore\";\nimport { formatTime } from \"../../../DateUtils\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\nimport { RoomEchoContext } from \"../../../stores/local-echo/RoomEchoContext\";\nimport RoomAvatar from \"../avatars/RoomAvatar\";\nimport { TransactionStatus } from \"../../../stores/local-echo/EchoTransaction\";\nimport Spinner from \"../elements/Spinner\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport { UPDATE_EVENT } from \"../../../stores/AsyncStore\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\n\ninterface IProps {\n    onFinished(): void;\n}\n\nexport default class ServerOfflineDialog extends React.PureComponent<IProps> {\n    public componentDidMount(): void {\n        EchoStore.instance.on(UPDATE_EVENT, this.onEchosUpdated);\n    }\n\n    public componentWillUnmount(): void {\n        EchoStore.instance.off(UPDATE_EVENT, this.onEchosUpdated);\n    }\n\n    private onEchosUpdated = (): void => {\n        this.forceUpdate(); // no state to worry about\n    };\n\n    private renderTimeline(): ReactNode[] {\n        return EchoStore.instance.contexts.map((c, i) => {\n            if (!c.firstFailedTime) return null; // not useful\n            if (!(c instanceof RoomEchoContext))\n                throw new Error(\"Cannot render unknown context: \" + c.constructor.name);\n            const header = (\n                <div className=\"mx_ServerOfflineDialog_content_context_timeline_header\">\n                    <RoomAvatar size=\"24px\" room={c.room} />\n                    <span>{c.room.name}</span>\n                </div>\n            );\n            const entries = c.transactions\n                .filter((t) => t.status === TransactionStatus.Error || t.didPreviouslyFail)\n                .map((t, j) => {\n                    let button = <Spinner size={19} />;\n                    if (t.status === TransactionStatus.Error) {\n                        button = (\n                            <AccessibleButton kind=\"link\" onClick={() => t.run()}>\n                                {_t(\"action|resend\")}\n                            </AccessibleButton>\n                        );\n                    }\n                    return (\n                        <div className=\"mx_ServerOfflineDialog_content_context_txn\" key={`txn-${j}`}>\n                            <span className=\"mx_ServerOfflineDialog_content_context_txn_desc\">{t.auditName}</span>\n                            {button}\n                        </div>\n                    );\n                });\n            return (\n                <div className=\"mx_ServerOfflineDialog_content_context\" key={`context-${i}`}>\n                    <div className=\"mx_ServerOfflineDialog_content_context_timestamp\">\n                        {formatTime(c.firstFailedTime, SettingsStore.getValue(\"showTwelveHourTimestamps\"))}\n                    </div>\n                    <div className=\"mx_ServerOfflineDialog_content_context_timeline\">\n                        {header}\n                        {entries}\n                    </div>\n                </div>\n            );\n        });\n    }\n\n    public render(): React.ReactNode {\n        let timeline = this.renderTimeline().filter((c) => !!c); // remove nulls for next check\n        if (timeline.length === 0) {\n            timeline = [<div key={1}>{_t(\"server_offline|empty_timeline\")}</div>];\n        }\n\n        const serverName = MatrixClientPeg.safeGet().getDomain();\n        return (\n            <BaseDialog\n                title={_t(\"server_offline|title\")}\n                className=\"mx_ServerOfflineDialog\"\n                contentId=\"mx_Dialog_content\"\n                onFinished={this.props.onFinished}\n                hasCancel={true}\n            >\n                <div className=\"mx_ServerOfflineDialog_content\">\n                    <p>{_t(\"server_offline|description\")}</p>\n                    <ul>\n                        <li>{_t(\"server_offline|description_1\", { serverName })}</li>\n                        <li>{_t(\"server_offline|description_2\")}</li>\n                        <li>{_t(\"server_offline|description_3\")}</li>\n                        <li>{_t(\"server_offline|description_4\")}</li>\n                        <li>{_t(\"server_offline|description_5\")}</li>\n                        <li>{_t(\"server_offline|description_6\")}</li>\n                        <li>{_t(\"server_offline|description_7\")}</li>\n                        <li>{_t(\"server_offline|description_8\")}</li>\n                    </ul>\n                    <hr />\n                    <h2>{_t(\"server_offline|recent_changes_heading\")}</h2>\n                    {timeline}\n                </div>\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { OfflineIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport Modal from \"../../../Modal\";\nimport ServerOfflineDialog from \"../dialogs/ServerOfflineDialog\";\n\nexport default class NonUrgentEchoFailureToast extends React.PureComponent {\n    private openDialog = (): void => {\n        Modal.createDialog(ServerOfflineDialog, {});\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <div className=\"mx_NonUrgentEchoFailureToast\">\n                <OfflineIcon />\n                {_t(\n                    \"error|non_urgent_echo_failure_toast\",\n                    {},\n                    {\n                        a: (sub) => (\n                            <AccessibleButton kind=\"link_inline\" onClick={this.openDialog}>\n                                {sub}\n                            </AccessibleButton>\n                        ),\n                    },\n                )}\n            </div>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { type GenericEchoChamber } from \"./GenericEchoChamber\";\nimport { RoomEchoChamber } from \"./RoomEchoChamber\";\nimport { RoomEchoContext } from \"./RoomEchoContext\";\nimport { AsyncStoreWithClient } from \"../AsyncStoreWithClient\";\nimport defaultDispatcher from \"../../dispatcher/dispatcher\";\nimport { type ActionPayload } from \"../../dispatcher/payloads\";\nimport { ContextTransactionState, type EchoContext } from \"./EchoContext\";\nimport NonUrgentToastStore, { type ToastReference } from \"../NonUrgentToastStore\";\nimport NonUrgentEchoFailureToast from \"../../components/views/toasts/NonUrgentEchoFailureToast\";\n\ninterface IState {\n    toastRef: ToastReference;\n}\n\ntype ContextKey = string;\n\nconst roomContextKey = (room: Room): ContextKey => `room-${room.roomId}`;\n\nexport class EchoStore extends AsyncStoreWithClient<IState> {\n    private static _instance: EchoStore;\n\n    private caches = new Map<ContextKey, GenericEchoChamber<any, any, any>>();\n\n    public constructor() {\n        super(defaultDispatcher);\n    }\n\n    public static get instance(): EchoStore {\n        if (!this._instance) {\n            this._instance = new EchoStore();\n            this._instance.start();\n        }\n        return this._instance;\n    }\n\n    public get contexts(): EchoContext[] {\n        return Array.from(this.caches.values()).map((e) => e.context);\n    }\n\n    public getOrCreateChamberForRoom(room: Room): RoomEchoChamber {\n        if (this.caches.has(roomContextKey(room))) {\n            return this.caches.get(roomContextKey(room)) as RoomEchoChamber;\n        }\n\n        const context = new RoomEchoContext(room);\n        context.whenAnything(() => this.checkContexts());\n\n        const echo = new RoomEchoChamber(context);\n        echo.setClient(this.matrixClient);\n        this.caches.set(roomContextKey(room), echo);\n\n        return echo;\n    }\n\n    private async checkContexts(): Promise<void> {\n        let hasOrHadError = false;\n        for (const echo of this.caches.values()) {\n            hasOrHadError = echo.context.state === ContextTransactionState.PendingErrors;\n            if (hasOrHadError) break;\n        }\n\n        if (hasOrHadError && !this.state.toastRef) {\n            const ref = NonUrgentToastStore.instance.addToast(NonUrgentEchoFailureToast);\n            await this.updateState({ toastRef: ref });\n        } else if (!hasOrHadError && this.state.toastRef) {\n            NonUrgentToastStore.instance.removeToast(this.state.toastRef);\n            await this.updateState({ toastRef: null });\n        }\n    }\n\n    protected async onReady(): Promise<any> {\n        if (!this.caches) return; // can only happen during initialization\n        for (const echo of this.caches.values()) {\n            echo.setClient(this.matrixClient);\n        }\n    }\n\n    protected async onNotReady(): Promise<any> {\n        for (const echo of this.caches.values()) {\n            echo.setClient(null);\n        }\n    }\n\n    protected async onAction(payload: ActionPayload): Promise<void> {}\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { type RoomEchoChamber } from \"./RoomEchoChamber\";\nimport { EchoStore } from \"./EchoStore\";\n\n/**\n * Semantic access to local echo\n */\nexport class EchoChamber {\n    private constructor() {}\n\n    public static forRoom(room: Room): RoomEchoChamber {\n        return EchoStore.instance.getOrCreateChamberForRoom(room);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { Whenable } from \"../../utils/Whenable\";\n\nexport type RunFn = () => Promise<void>;\n\nexport enum TransactionStatus {\n    Pending,\n    Success,\n    Error,\n}\n\nexport class EchoTransaction extends Whenable<TransactionStatus> {\n    private _status = TransactionStatus.Pending;\n    private didFail = false;\n\n    public readonly startTime = new Date();\n\n    public constructor(\n        public readonly auditName: string,\n        public runFn: RunFn,\n    ) {\n        super();\n    }\n\n    public get didPreviouslyFail(): boolean {\n        return this.didFail;\n    }\n\n    public get status(): TransactionStatus {\n        return this._status;\n    }\n\n    public run(): void {\n        if (this.status === TransactionStatus.Success) {\n            throw new Error(\"Cannot re-run a successful echo transaction\");\n        }\n        this.setStatus(TransactionStatus.Pending);\n        this.runFn()\n            .then(() => this.setStatus(TransactionStatus.Success))\n            .catch(() => this.setStatus(TransactionStatus.Error));\n    }\n\n    public cancel(): void {\n        // Success basically means \"done\"\n        this.setStatus(TransactionStatus.Success);\n    }\n\n    private setStatus(status: TransactionStatus): void {\n        this._status = status;\n        if (status === TransactionStatus.Error) {\n            this.didFail = true;\n        } else if (status === TransactionStatus.Success) {\n            this.didFail = false;\n        }\n        this.notifyCondition(status);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { EventEmitter } from \"events\";\n\nimport { type EchoContext } from \"./EchoContext\";\nimport { type EchoTransaction, type RunFn, TransactionStatus } from \"./EchoTransaction\";\n\nexport async function implicitlyReverted(): Promise<void> {\n    // do nothing :D\n}\n\nexport const PROPERTY_UPDATED = \"property_updated\";\n\nexport abstract class GenericEchoChamber<C extends EchoContext, K, V> extends EventEmitter {\n    private cache = new Map<K, { txn: EchoTransaction; val: V }>();\n    protected matrixClient: MatrixClient | null = null;\n\n    protected constructor(\n        public readonly context: C,\n        private lookupFn: (key: K) => V,\n    ) {\n        super();\n    }\n\n    public setClient(client: MatrixClient | null): void {\n        const oldClient = this.matrixClient;\n        this.matrixClient = client;\n        this.onClientChanged(oldClient, client);\n    }\n\n    protected abstract onClientChanged(oldClient: MatrixClient | null, newClient: MatrixClient | null): void;\n\n    /**\n     * Gets a value. If the key is in flight, the cached value will be returned. If\n     * the key is not in flight then the lookupFn provided to this class will be\n     * called instead.\n     * @param key The key to look up.\n     * @returns The value for the key.\n     */\n    public getValue(key: K): V {\n        return this.cache.has(key) ? this.cache.get(key)!.val : this.lookupFn(key);\n    }\n\n    private cacheVal(key: K, val: V, txn: EchoTransaction): void {\n        this.cache.set(key, { txn, val });\n        this.emit(PROPERTY_UPDATED, key);\n    }\n\n    private decacheKey(key: K): void {\n        if (this.cache.has(key)) {\n            this.context.disownTransaction(this.cache.get(key)!.txn);\n            this.cache.delete(key);\n            this.emit(PROPERTY_UPDATED, key);\n        }\n    }\n\n    protected markEchoReceived(key: K): void {\n        if (this.cache.has(key)) {\n            const txn = this.cache.get(key)!.txn;\n            this.context.disownTransaction(txn);\n            txn.cancel();\n        }\n        this.decacheKey(key);\n    }\n\n    public setValue(auditName: string, key: K, targetVal: V, runFn: RunFn, revertFn: RunFn): void {\n        // Cancel any pending transactions for the same key\n        if (this.cache.has(key)) {\n            this.cache.get(key)!.txn.cancel();\n        }\n\n        const ctxn = this.context.beginTransaction(auditName, runFn);\n        this.cacheVal(key, targetVal, ctxn); // set the cache now as it won't be updated by the .when() ladder below.\n\n        ctxn.when(TransactionStatus.Pending, () => this.cacheVal(key, targetVal, ctxn)).when(\n            TransactionStatus.Error,\n            () => revertFn(),\n        );\n\n        ctxn.run();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, ClientEvent, type MatrixClient, EventType } from \"matrix-js-sdk/src/matrix\";\n\nimport { GenericEchoChamber, implicitlyReverted, PROPERTY_UPDATED } from \"./GenericEchoChamber\";\nimport { getRoomNotifsState, type RoomNotifState, setRoomNotifsState } from \"../../RoomNotifs\";\nimport { type RoomEchoContext } from \"./RoomEchoContext\";\nimport { _t } from \"../../languageHandler\";\n\nexport enum CachedRoomKey {\n    NotificationVolume,\n}\n\nexport class RoomEchoChamber extends GenericEchoChamber<RoomEchoContext, CachedRoomKey, RoomNotifState | undefined> {\n    private properties = new Map<CachedRoomKey, RoomNotifState>();\n\n    public constructor(context: RoomEchoContext) {\n        super(context, (k) => this.properties.get(k));\n    }\n\n    protected onClientChanged(oldClient: MatrixClient | null, newClient: MatrixClient | null): void {\n        this.properties.clear();\n        oldClient?.removeListener(ClientEvent.AccountData, this.onAccountData);\n        if (newClient) {\n            // Register the listeners first\n            newClient.on(ClientEvent.AccountData, this.onAccountData);\n\n            // Then populate the properties map\n            this.updateNotificationVolume();\n        }\n    }\n\n    private onAccountData = (event: MatrixEvent): void => {\n        if (!this.matrixClient) return;\n        if (event.getType() === EventType.PushRules) {\n            const currentVolume = this.properties.get(CachedRoomKey.NotificationVolume);\n            const newVolume = getRoomNotifsState(this.matrixClient, this.context.room.roomId);\n            if (currentVolume !== newVolume) {\n                this.updateNotificationVolume();\n            }\n        }\n    };\n\n    private updateNotificationVolume(): void {\n        const state = this.matrixClient ? getRoomNotifsState(this.matrixClient, this.context.room.roomId) : null;\n        if (state) this.properties.set(CachedRoomKey.NotificationVolume, state);\n        else this.properties.delete(CachedRoomKey.NotificationVolume);\n        this.markEchoReceived(CachedRoomKey.NotificationVolume);\n        this.emit(PROPERTY_UPDATED, CachedRoomKey.NotificationVolume);\n    }\n\n    // ---- helpers below here ----\n\n    public get notificationVolume(): RoomNotifState | undefined {\n        return this.getValue(CachedRoomKey.NotificationVolume);\n    }\n\n    public set notificationVolume(v: RoomNotifState | undefined) {\n        if (v === undefined) return;\n        this.setValue(\n            _t(\"notifications|error_change_title\"),\n            CachedRoomKey.NotificationVolume,\n            v,\n            async (): Promise<void> => {\n                return setRoomNotifsState(this.context.room.client, this.context.room.roomId, v);\n            },\n            implicitlyReverted,\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { _t } from \"../../languageHandler\";\n\nexport enum NotificationLevel {\n    Muted,\n    // Inverted (None -> Red) because we do integer comparisons on this\n    None, // nothing special\n    // TODO: Remove bold with notifications: https://github.com/vector-im/element-web/issues/14227\n    Activity, // no badge, show as unread\n    Notification, // unread notified messages\n    Highlight, // unread pings\n    Unsent, // some messages failed to send\n}\n\nexport function humanReadableNotificationLevel(level: NotificationLevel): string {\n    switch (level) {\n        case NotificationLevel.None:\n            return _t(\"notifications|level_none\");\n        case NotificationLevel.Activity:\n            return _t(\"notifications|level_activity\");\n        case NotificationLevel.Notification:\n            return _t(\"notifications|level_notification\");\n        case NotificationLevel.Highlight:\n            return _t(\"notifications|level_highlight\");\n        case NotificationLevel.Unsent:\n            return _t(\"notifications|level_unsent\");\n        case NotificationLevel.Muted:\n            return _t(\"notifications|level_muted\");\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { TypedEventEmitter } from \"matrix-js-sdk/src/matrix\";\n\nimport { NotificationLevel } from \"./NotificationLevel\";\nimport { type IDestroyable } from \"../../utils/IDestroyable\";\nimport SettingsStore from \"../../settings/SettingsStore\";\n\nexport interface INotificationStateSnapshotParams {\n    symbol: string | null;\n    count: number;\n    level: NotificationLevel;\n    muted: boolean;\n    knocked: boolean;\n    invited: boolean;\n}\n\nexport enum NotificationStateEvents {\n    Update = \"update\",\n}\n\ntype EventHandlerMap = {\n    [NotificationStateEvents.Update]: () => void;\n};\n\nexport abstract class NotificationState\n    extends TypedEventEmitter<NotificationStateEvents, EventHandlerMap>\n    implements INotificationStateSnapshotParams, IDestroyable\n{\n    //\n    protected _symbol: string | null = null;\n    protected _count = 0;\n    protected _level: NotificationLevel = NotificationLevel.None;\n    protected _muted = false;\n    protected _knocked = false;\n    protected _invited = false;\n\n    private watcherReferences: string[] = [];\n\n    public constructor() {\n        super();\n        this.watcherReferences.push(\n            SettingsStore.watchSetting(\"feature_hidebold\", null, () => {\n                this.emit(NotificationStateEvents.Update);\n            }),\n        );\n    }\n\n    public get symbol(): string | null {\n        return this._symbol;\n    }\n\n    public get count(): number {\n        return this._count;\n    }\n\n    public get level(): NotificationLevel {\n        return this._level;\n    }\n\n    public get muted(): boolean {\n        return this._muted;\n    }\n\n    public get knocked(): boolean {\n        return this._knocked;\n    }\n\n    /**\n     * True if the notification is an invitation notification.\n     * Invite notifications are a special case of highlight notifications\n     */\n    public get invited(): boolean {\n        return this._invited;\n    }\n\n    public get isIdle(): boolean {\n        return this.level <= NotificationLevel.None;\n    }\n\n    /**\n     * True if the notification is higher than an activity notification or if the feature_hidebold is disabled with an activity notification.\n     * The \"unread\" term used here is different from the \"Unread\" in the UI. Unread in the UI doesn't include activity notifications even with feature_hidebold disabled.\n     */\n    public get isUnread(): boolean {\n        if (this.level > NotificationLevel.Activity) {\n            return true;\n        } else {\n            const hideBold = SettingsStore.getValue(\"feature_hidebold\");\n            return this.level === NotificationLevel.Activity && !hideBold;\n        }\n    }\n\n    /**\n     * True if the notification has a count or a symbol and is equal or greater than an NotificationLevel.Notification.\n     */\n    public get hasUnreadCount(): boolean {\n        return this.level >= NotificationLevel.Notification && (!!this.count || !!this.symbol);\n    }\n\n    /**\n     * True if the notification is a mention, an invitation, a knock or a unset message.\n     *\n     * @deprecated because the name is confusing. A mention is not an invitation, a knock or an unsent message.\n     * In case of a {@link RoomNotificationState}, use {@link RoomNotificationState.isMention} instead.\n     */\n    public get hasMentions(): boolean {\n        return this.level >= NotificationLevel.Highlight;\n    }\n\n    protected emitIfUpdated(snapshot: NotificationStateSnapshot): void {\n        if (snapshot.isDifferentFrom(this)) {\n            this.emit(NotificationStateEvents.Update);\n        }\n    }\n\n    protected snapshot(): NotificationStateSnapshot {\n        return new NotificationStateSnapshot(this);\n    }\n\n    public destroy(): void {\n        this.removeAllListeners(NotificationStateEvents.Update);\n        for (const watcherReference of this.watcherReferences) {\n            SettingsStore.unwatchSetting(watcherReference);\n        }\n        this.watcherReferences = [];\n    }\n}\n\nexport class NotificationStateSnapshot {\n    private readonly symbol: string | null;\n    private readonly count: number;\n    private readonly level: NotificationLevel;\n    private readonly muted: boolean;\n    private readonly knocked: boolean;\n    private readonly isInvitation: boolean;\n\n    public constructor(state: INotificationStateSnapshotParams) {\n        this.symbol = state.symbol;\n        this.count = state.count;\n        this.level = state.level;\n        this.muted = state.muted;\n        this.knocked = state.knocked;\n        this.isInvitation = state.invited;\n    }\n\n    public isDifferentFrom(other: INotificationStateSnapshotParams): boolean {\n        const before = {\n            count: this.count,\n            symbol: this.symbol,\n            level: this.level,\n            muted: this.muted,\n            knocked: this.knocked,\n            is: this.isInvitation,\n        };\n        const after = {\n            count: other.count,\n            symbol: other.symbol,\n            level: other.level,\n            muted: other.muted,\n            knocked: other.knocked,\n        };\n        return JSON.stringify(before) !== JSON.stringify(after);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { NotificationLevel } from \"./NotificationLevel\";\nimport { arrayDiff } from \"../../utils/arrays\";\nimport { type RoomNotificationState } from \"./RoomNotificationState\";\nimport { NotificationState, NotificationStateEvents } from \"./NotificationState\";\n\nexport type FetchRoomFn = (room: Room) => RoomNotificationState;\n\nexport class ListNotificationState extends NotificationState {\n    private rooms: Room[] = [];\n    private states: { [roomId: string]: RoomNotificationState } = {};\n\n    public constructor(\n        private byTileCount = false,\n        private getRoomFn: FetchRoomFn,\n    ) {\n        super();\n    }\n\n    public get symbol(): string | null {\n        return this._level === NotificationLevel.Unsent ? \"!\" : null;\n    }\n\n    public setRooms(rooms: Room[]): void {\n        // If we're only concerned about the tile count, don't bother setting up listeners.\n        if (this.byTileCount) {\n            this.rooms = rooms;\n            this.calculateTotalState();\n            return;\n        }\n\n        const oldRooms = this.rooms;\n        const diff = arrayDiff(oldRooms, rooms);\n        this.rooms = [...rooms];\n        for (const oldRoom of diff.removed) {\n            const state = this.states[oldRoom.roomId];\n            if (!state) continue; // We likely just didn't have a badge (race condition)\n            delete this.states[oldRoom.roomId];\n            state.off(NotificationStateEvents.Update, this.onRoomNotificationStateUpdate);\n        }\n        for (const newRoom of diff.added) {\n            const state = this.getRoomFn(newRoom);\n            state.on(NotificationStateEvents.Update, this.onRoomNotificationStateUpdate);\n            this.states[newRoom.roomId] = state;\n        }\n\n        this.calculateTotalState();\n    }\n\n    public getForRoom(room: Room): RoomNotificationState {\n        const state = this.states[room.roomId];\n        if (!state) throw new Error(\"Unknown room for notification state\");\n        return state;\n    }\n\n    public destroy(): void {\n        super.destroy();\n        for (const state of Object.values(this.states)) {\n            state.off(NotificationStateEvents.Update, this.onRoomNotificationStateUpdate);\n        }\n        this.states = {};\n    }\n\n    private onRoomNotificationStateUpdate = (): void => {\n        this.calculateTotalState();\n    };\n\n    private calculateTotalState(): void {\n        const snapshot = this.snapshot();\n\n        if (this.byTileCount) {\n            this._level = NotificationLevel.Highlight;\n            this._count = this.rooms.length;\n        } else {\n            this._count = 0;\n            this._level = NotificationLevel.None;\n            for (const state of Object.values(this.states)) {\n                this._count += state.count;\n                this._level = Math.max(this.level, state.level);\n            }\n        }\n\n        // finally, publish an update if needed\n        this.emitIfUpdated(snapshot);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { MatrixEventEvent, RoomEvent, ClientEvent } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport type { Room, MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport type { IDestroyable } from \"../../utils/IDestroyable\";\nimport { MatrixClientPeg } from \"../../MatrixClientPeg\";\nimport { readReceiptChangeIsFor } from \"../../utils/read-receipts\";\nimport * as RoomNotifs from \"../../RoomNotifs\";\nimport { NotificationState } from \"./NotificationState\";\nimport SettingsStore from \"../../settings/SettingsStore\";\nimport { MARKED_UNREAD_TYPE_STABLE, MARKED_UNREAD_TYPE_UNSTABLE } from \"../../utils/notifications\";\nimport { NotificationLevel } from \"./NotificationLevel\";\n\nexport class RoomNotificationState extends NotificationState implements IDestroyable {\n    public constructor(\n        public readonly room: Room,\n        private includeThreads: boolean,\n    ) {\n        super();\n        const cli = this.room.client;\n        this.room.on(RoomEvent.Receipt, this.handleReadReceipt);\n        this.room.on(RoomEvent.MyMembership, this.handleMembershipUpdate);\n        this.room.on(RoomEvent.LocalEchoUpdated, this.handleLocalEchoUpdated);\n        this.room.on(RoomEvent.Timeline, this.handleRoomEventUpdate);\n        this.room.on(RoomEvent.Redaction, this.handleRoomEventUpdate);\n        this.room.on(RoomEvent.AccountData, this.handleRoomAccountDataUpdate);\n\n        this.room.on(RoomEvent.UnreadNotifications, this.handleNotificationCountUpdate); // for server-sent counts\n        cli.on(MatrixEventEvent.Decrypted, this.onEventDecrypted);\n        cli.on(ClientEvent.AccountData, this.handleAccountDataUpdate);\n        this.updateNotificationState();\n    }\n\n    public destroy(): void {\n        super.destroy();\n        const cli = this.room.client;\n        this.room.removeListener(RoomEvent.Receipt, this.handleReadReceipt);\n        this.room.removeListener(RoomEvent.MyMembership, this.handleMembershipUpdate);\n        this.room.removeListener(RoomEvent.LocalEchoUpdated, this.handleLocalEchoUpdated);\n        this.room.removeListener(RoomEvent.Timeline, this.handleRoomEventUpdate);\n        this.room.removeListener(RoomEvent.Redaction, this.handleRoomEventUpdate);\n        this.room.removeListener(RoomEvent.AccountData, this.handleRoomAccountDataUpdate);\n        cli.removeListener(MatrixEventEvent.Decrypted, this.onEventDecrypted);\n        cli.removeListener(ClientEvent.AccountData, this.handleAccountDataUpdate);\n    }\n\n    /**\n     * True if the notification is a mention.\n     */\n    public get isMention(): boolean {\n        if (this.invited || this.knocked) return false;\n\n        return this.level === NotificationLevel.Highlight;\n    }\n\n    /**\n     * True if the notification is an unsent message.\n     */\n    public get isUnsentMessage(): boolean {\n        return this.level === NotificationLevel.Unsent;\n    }\n\n    /**\n     * Activity notifications are the lowest level of notification (except none and muted)\n     */\n    public get isActivityNotification(): boolean {\n        return this.level === NotificationLevel.Activity;\n    }\n\n    /**\n     * This is the case for notifications with a level:\n     * - is a knock\n     * - greater Activity\n     * - equal Activity and feature_hidebold is disabled.\n     */\n    public get hasAnyNotificationOrActivity(): boolean {\n        if (this.knocked) return true;\n\n        // If the feature_hidebold is enabled, we don't want to show activity notifications\n        const hideBold = SettingsStore.getValue(\"feature_hidebold\");\n        if (!hideBold && this.level === NotificationLevel.Activity) return true;\n\n        return this.level >= NotificationLevel.Notification;\n    }\n\n    /**\n     * True if the notification is a NotificationLevel.Notification.\n     */\n    public get isNotification(): boolean {\n        return this.level === NotificationLevel.Notification;\n    }\n\n    private handleLocalEchoUpdated = (): void => {\n        this.updateNotificationState();\n    };\n\n    private handleReadReceipt = (event: MatrixEvent, room: Room): void => {\n        if (!readReceiptChangeIsFor(event, MatrixClientPeg.safeGet())) return; // not our own - ignore\n        if (room.roomId !== this.room.roomId) return; // not for us - ignore\n        this.updateNotificationState();\n    };\n\n    private handleMembershipUpdate = (): void => {\n        this.updateNotificationState();\n    };\n\n    private handleNotificationCountUpdate = (): void => {\n        this.updateNotificationState();\n    };\n\n    private onEventDecrypted = (event: MatrixEvent): void => {\n        if (event.getRoomId() !== this.room.roomId) return; // ignore - not for us or notifications timeline\n\n        this.updateNotificationState();\n    };\n\n    private handleRoomEventUpdate = (event: MatrixEvent): void => {\n        if (event?.getRoomId() !== this.room.roomId) return; // ignore - not for us or notifications timeline\n        this.updateNotificationState();\n    };\n\n    private handleAccountDataUpdate = (ev: MatrixEvent): void => {\n        if (ev.getType() === \"m.push_rules\") {\n            this.updateNotificationState();\n        }\n    };\n\n    private handleRoomAccountDataUpdate = (ev: MatrixEvent): void => {\n        if ([MARKED_UNREAD_TYPE_STABLE, MARKED_UNREAD_TYPE_UNSTABLE].includes(ev.getType())) {\n            this.updateNotificationState();\n        }\n    };\n\n    private updateNotificationState(): void {\n        const snapshot = this.snapshot();\n        const { level, symbol, count, invited } = RoomNotifs.determineUnreadState(\n            this.room,\n            undefined,\n            this.includeThreads,\n        );\n        const muted =\n            RoomNotifs.getRoomNotifsState(this.room.client, this.room.roomId) === RoomNotifs.RoomNotifState.Mute;\n        const knocked =\n            SettingsStore.getValue(\"feature_ask_to_join\") && this.room.getMyMembership() === KnownMembership.Knock;\n        this._level = level;\n        this._symbol = symbol;\n        this._count = count;\n        this._muted = muted;\n        this._knocked = knocked;\n        this._invited = invited;\n\n        // finally, publish an update if needed\n        this.emitIfUpdated(snapshot);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { NotificationLevel } from \"./NotificationLevel\";\nimport { NotificationState } from \"./NotificationState\";\n\n/**\n * Summarizes a number of states into a unique snapshot. To populate, call\n * the add() function with the notification states to be included.\n *\n * Useful for community notification counts, global notification counts, etc.\n */\nexport class SummarizedNotificationState extends NotificationState {\n    private totalStatesWithUnread = 0;\n\n    public constructor() {\n        super();\n        this._symbol = null;\n        this._count = 0;\n        this._level = NotificationLevel.None;\n    }\n\n    public get numUnreadStates(): number {\n        return this.totalStatesWithUnread;\n    }\n\n    /**\n     * Append a notification state to this snapshot, taking the loudest NotificationColor\n     * of the two. By default this will not adopt the symbol of the other notification\n     * state to prevent the count from being lost in typical usage.\n     * @param other The other notification state to append.\n     * @param includeSymbol If true, the notification state's symbol will be taken if one\n     * is present.\n     */\n    public add(other: NotificationState, includeSymbol = false): void {\n        if (other.symbol && includeSymbol) {\n            this._symbol = other.symbol;\n        }\n        if (other.count) {\n            this._count += other.count;\n        }\n        if (other.level > this.level) {\n            this._level = other.level;\n        }\n        if (other.hasUnreadCount) {\n            this.totalStatesWithUnread++;\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room, ClientEvent, SyncState, type EmptyObject } from \"matrix-js-sdk/src/matrix\";\n\nimport { type ActionPayload } from \"../../dispatcher/payloads\";\nimport { AsyncStoreWithClient } from \"../AsyncStoreWithClient\";\nimport defaultDispatcher, { type MatrixDispatcher } from \"../../dispatcher/dispatcher\";\nimport { DefaultTagID, type TagID } from \"../room-list/models\";\nimport { type FetchRoomFn, ListNotificationState } from \"./ListNotificationState\";\nimport { RoomNotificationState } from \"./RoomNotificationState\";\nimport { SummarizedNotificationState } from \"./SummarizedNotificationState\";\nimport { VisibilityProvider } from \"../room-list/filters/VisibilityProvider\";\nimport { PosthogAnalytics } from \"../../PosthogAnalytics\";\nimport SettingsStore from \"../../settings/SettingsStore\";\n\nexport const UPDATE_STATUS_INDICATOR = Symbol(\"update-status-indicator\");\n\nexport class RoomNotificationStateStore extends AsyncStoreWithClient<EmptyObject> {\n    private static readonly internalInstance = (() => {\n        const instance = new RoomNotificationStateStore();\n        instance.start();\n        return instance;\n    })();\n    private roomMap = new Map<Room, RoomNotificationState>();\n\n    private listMap = new Map<TagID, ListNotificationState>();\n    private _globalState = new SummarizedNotificationState();\n\n    private constructor(dispatcher = defaultDispatcher) {\n        super(dispatcher, {});\n        SettingsStore.watchSetting(\"feature_dynamic_room_predecessors\", null, () => {\n            // We pass SyncState.Syncing here to \"simulate\" a sync happening.\n            // The code that receives these events actually doesn't care\n            // what state we pass, except that it behaves differently if we\n            // pass SyncState.Error.\n            this.emitUpdateIfStateChanged(SyncState.Syncing, false);\n        });\n    }\n\n    /**\n     * @internal Public for test only\n     */\n    public static testInstance(dispatcher: MatrixDispatcher): RoomNotificationStateStore {\n        return new RoomNotificationStateStore();\n    }\n\n    /**\n     * Gets a snapshot of notification state for all visible rooms. The number of states recorded\n     * on the SummarizedNotificationState is equivalent to rooms.\n     */\n    public get globalState(): SummarizedNotificationState {\n        return this._globalState;\n    }\n\n    /**\n     * Gets an instance of the list state class for the given tag.\n     * @param tagId The tag to get the notification state for.\n     * @returns The notification state for the tag.\n     */\n    public getListState(tagId: TagID): ListNotificationState {\n        if (this.listMap.has(tagId)) {\n            return this.listMap.get(tagId)!;\n        }\n\n        // TODO: Update if/when invites move out of the room list.\n        const useTileCount = tagId === DefaultTagID.Invite;\n        const getRoomFn: FetchRoomFn = (room: Room) => {\n            return this.getRoomState(room);\n        };\n        const state = new ListNotificationState(useTileCount, getRoomFn);\n        this.listMap.set(tagId, state);\n        return state;\n    }\n\n    /**\n     * Gets a copy of the notification state for a room. The consumer should not\n     * attempt to destroy the returned state as it may be shared with other\n     * consumers.\n     * @param room The room to get the notification state for.\n     * @returns The room's notification state.\n     */\n    public getRoomState(room: Room): RoomNotificationState {\n        if (!this.roomMap.has(room)) {\n            this.roomMap.set(room, new RoomNotificationState(room, false));\n        }\n        return this.roomMap.get(room)!;\n    }\n\n    public static get instance(): RoomNotificationStateStore {\n        return RoomNotificationStateStore.internalInstance;\n    }\n\n    private onSync = (state: SyncState, prevState: SyncState | null): void => {\n        this.emitUpdateIfStateChanged(state, state !== prevState);\n    };\n\n    /**\n     * If the SummarizedNotificationState of this room has changed, or forceEmit\n     * is true, emit an UPDATE_STATUS_INDICATOR event.\n     *\n     * @internal public for test\n     */\n    public emitUpdateIfStateChanged = (state: SyncState, forceEmit: boolean): void => {\n        if (!this.matrixClient) return;\n        // Only count visible rooms to not torment the user with notification counts in rooms they can't see.\n        // This will include highlights from the previous version of the room internally\n        const msc3946ProcessDynamicPredecessor = SettingsStore.getValue(\"feature_dynamic_room_predecessors\");\n        const globalState = new SummarizedNotificationState();\n        const visibleRooms = this.matrixClient.getVisibleRooms(msc3946ProcessDynamicPredecessor);\n\n        let numFavourites = 0;\n        for (const room of visibleRooms) {\n            if (VisibilityProvider.instance.isRoomVisible(room)) {\n                globalState.add(this.getRoomState(room));\n\n                if (room.tags[DefaultTagID.Favourite] && !room.getType()) numFavourites++;\n            }\n        }\n\n        PosthogAnalytics.instance.setProperty(\"numFavouriteRooms\", numFavourites);\n\n        if (\n            this.globalState.symbol !== globalState.symbol ||\n            this.globalState.count !== globalState.count ||\n            this.globalState.level !== globalState.level ||\n            this.globalState.numUnreadStates !== globalState.numUnreadStates ||\n            forceEmit\n        ) {\n            this._globalState = globalState;\n            this.emit(UPDATE_STATUS_INDICATOR, globalState, state);\n        }\n    };\n\n    protected async onReady(): Promise<void> {\n        this.matrixClient?.on(ClientEvent.Sync, this.onSync);\n    }\n\n    protected async onNotReady(): Promise<any> {\n        this.matrixClient?.off(ClientEvent.Sync, this.onSync);\n        for (const roomState of this.roomMap.values()) {\n            roomState.destroy();\n        }\n    }\n\n    // We don't need this, but our contract says we do.\n    protected async onAction(payload: ActionPayload): Promise<void> {}\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, type Room, type RoomMember, type User } from \"matrix-js-sdk/src/matrix\";\nimport { type VerificationRequest } from \"matrix-js-sdk/src/crypto-api\";\n\nimport { type RightPanelPhases } from \"./RightPanelStorePhases\";\n\nexport interface IRightPanelCardState {\n    member?: RoomMember | User;\n    verificationRequest?: VerificationRequest;\n    verificationRequestPromise?: Promise<VerificationRequest>;\n    widgetId?: string;\n    // Room3pidMemberInfo, Space3pidMemberInfo,\n    memberInfoEvent?: MatrixEvent;\n    // threads\n    threadHeadEvent?: MatrixEvent;\n    initialEvent?: MatrixEvent;\n    isInitialEventHighlighted?: boolean;\n    initialEventScrollIntoView?: boolean;\n    // room summary\n    focusRoomSearch?: boolean;\n}\n\nexport interface IRightPanelCardStateStored {\n    memberId?: string;\n    // we do not store the things associated with verification\n    widgetId?: string;\n    // 3pidMemberInfo\n    memberInfoEventId?: string;\n    // threads\n    threadHeadEventId?: string;\n    initialEventId?: string;\n    isInitialEventHighlighted?: boolean;\n    initialEventScrollIntoView?: boolean;\n}\n\nexport interface IRightPanelCard {\n    phase: RightPanelPhases | null;\n    state?: IRightPanelCardState;\n}\n\nexport interface IRightPanelCardStored {\n    phase: RightPanelPhases | null;\n    state?: IRightPanelCardStateStored;\n}\n\nexport interface IRightPanelForRoom {\n    isOpen: boolean;\n    history: Array<IRightPanelCard>;\n}\n\nexport type IRightPanelForRoomStored = {\n    isOpen: boolean;\n    history: Array<IRightPanelCardStored>;\n};\n\nexport function convertToStorePanel(cacheRoom?: IRightPanelForRoom): IRightPanelForRoomStored | undefined {\n    if (!cacheRoom) return undefined;\n    const storeHistory = [...cacheRoom.history].map((panelState) => convertCardToStore(panelState));\n    return { isOpen: cacheRoom.isOpen, history: storeHistory };\n}\n\nexport function convertToStatePanel(storeRoom: IRightPanelForRoomStored | null, room: Room): IRightPanelForRoom | null {\n    if (!storeRoom) return storeRoom;\n    const stateHistory = [...storeRoom.history].map((panelStateStore) => convertStoreToCard(panelStateStore, room));\n    return { history: stateHistory, isOpen: storeRoom.isOpen };\n}\n\nexport function convertCardToStore(panelState: IRightPanelCard): IRightPanelCardStored {\n    const state = panelState.state ?? {};\n    const stateStored: IRightPanelCardStateStored = {\n        widgetId: state.widgetId,\n        isInitialEventHighlighted: state.isInitialEventHighlighted,\n        initialEventScrollIntoView: state.initialEventScrollIntoView,\n        threadHeadEventId: !!state?.threadHeadEvent?.getId() ? state.threadHeadEvent.getId() : undefined,\n        memberInfoEventId: !!state?.memberInfoEvent?.getId() ? state.memberInfoEvent.getId() : undefined,\n        initialEventId: !!state?.initialEvent?.getId() ? state.initialEvent.getId() : undefined,\n        memberId: !!state?.member?.userId ? state.member.userId : undefined,\n    };\n\n    return { state: stateStored, phase: panelState.phase };\n}\n\nfunction convertStoreToCard(panelStateStore: IRightPanelCardStored, room: Room): IRightPanelCard {\n    const stateStored = panelStateStore.state ?? {};\n    const state: IRightPanelCardState = {\n        widgetId: stateStored.widgetId,\n        isInitialEventHighlighted: stateStored.isInitialEventHighlighted,\n        initialEventScrollIntoView: stateStored.initialEventScrollIntoView,\n        threadHeadEvent: !!stateStored?.threadHeadEventId\n            ? room.findEventById(stateStored.threadHeadEventId)\n            : undefined,\n        memberInfoEvent: !!stateStored?.memberInfoEventId\n            ? room.findEventById(stateStored.memberInfoEventId)\n            : undefined,\n        initialEvent: !!stateStored?.initialEventId ? room.findEventById(stateStored.initialEventId) : undefined,\n        member: (!!stateStored?.memberId && room.getMember(stateStored.memberId)) || undefined,\n    };\n\n    return { state: state, phase: panelStateStore.phase };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { CryptoEvent } from \"matrix-js-sdk/src/crypto-api\";\n\nimport defaultDispatcher from \"../../dispatcher/dispatcher\";\nimport { pendingVerificationRequestForUser } from \"../../verification\";\nimport SettingsStore from \"../../settings/SettingsStore\";\nimport { RightPanelPhases } from \"./RightPanelStorePhases\";\nimport { SettingLevel } from \"../../settings/SettingLevel\";\nimport { UPDATE_EVENT } from \"../AsyncStore\";\nimport { ReadyWatchingStore } from \"../ReadyWatchingStore\";\nimport {\n    convertToStatePanel,\n    convertToStorePanel,\n    type IRightPanelCard,\n    type IRightPanelCardState,\n    type IRightPanelForRoom,\n} from \"./RightPanelStoreIPanelState\";\nimport { type ActionPayload } from \"../../dispatcher/payloads\";\nimport { Action } from \"../../dispatcher/actions\";\nimport { type ActiveRoomChangedPayload } from \"../../dispatcher/payloads/ActiveRoomChangedPayload\";\nimport { SdkContextClass } from \"../../contexts/SDKContext\";\nimport { MatrixClientPeg } from \"../../MatrixClientPeg\";\n\n/**\n * @see RightPanelStore#generateHistoryForPhase\n */\nfunction getPhasesForPhase(phase: IRightPanelCard[\"phase\"]): RightPanelPhases[] {\n    switch (phase) {\n        case RightPanelPhases.ThreadPanel:\n        case RightPanelPhases.MemberList:\n        case RightPanelPhases.PinnedMessages:\n            return [RightPanelPhases.RoomSummary];\n        case RightPanelPhases.MemberInfo:\n        case RightPanelPhases.ThreePidMemberInfo:\n            return [RightPanelPhases.RoomSummary, RightPanelPhases.MemberList];\n        default:\n            return [];\n    }\n}\n\n/**\n * A class for tracking the state of the right panel between layouts and\n * sessions. This state includes a history for each room. Each history element\n * contains the phase (e.g. RightPanelPhase.RoomMemberInfo) and the state (e.g.\n * the member) associated with it.\n */\nexport default class RightPanelStore extends ReadyWatchingStore {\n    private static internalInstance: RightPanelStore;\n\n    private global?: IRightPanelForRoom;\n    private byRoom: { [roomId: string]: IRightPanelForRoom } = {};\n    private viewedRoomId: string | null = null;\n\n    private constructor() {\n        super(defaultDispatcher);\n        this.reset();\n    }\n\n    /**\n     * Resets the store. Intended for test usage only.\n     */\n    public reset(): void {\n        this.global = undefined;\n        this.byRoom = {};\n        this.viewedRoomId = null;\n    }\n\n    protected async onReady(): Promise<any> {\n        this.viewedRoomId = SdkContextClass.instance.roomViewStore.getRoomId();\n        this.matrixClient?.on(CryptoEvent.VerificationRequestReceived, this.onVerificationRequestUpdate);\n        this.loadCacheFromSettings();\n        this.emitAndUpdateSettings();\n    }\n\n    protected async onNotReady(): Promise<any> {\n        this.matrixClient?.off(CryptoEvent.VerificationRequestReceived, this.onVerificationRequestUpdate);\n    }\n\n    protected onDispatcherAction(payload: ActionPayload): void {\n        switch (payload.action) {\n            case Action.ActiveRoomChanged: {\n                const changePayload = <ActiveRoomChangedPayload>payload;\n                this.handleViewedRoomChange(changePayload.oldRoomId, changePayload.newRoomId);\n                break;\n            }\n\n            case Action.FocusMessageSearch: {\n                if (this.currentCard.phase !== RightPanelPhases.RoomSummary) {\n                    this.setCard({ phase: RightPanelPhases.RoomSummary, state: { focusRoomSearch: true } });\n                }\n                this.show(null);\n            }\n        }\n    }\n\n    // Getters\n    /**\n     * If you are calling this from a component that already knows about a\n     * specific room from props / state, then it's best to prefer\n     * `isOpenForRoom` below to ensure all your data is for a single room\n     * during room changes.\n     */\n    public get isOpen(): boolean {\n        return this.byRoom[this.viewedRoomId ?? \"\"]?.isOpen ?? false;\n    }\n\n    public isOpenForRoom(roomId: string): boolean {\n        return this.byRoom[roomId]?.isOpen ?? false;\n    }\n\n    public get roomPhaseHistory(): Array<IRightPanelCard> {\n        return this.byRoom[this.viewedRoomId ?? \"\"]?.history ?? [];\n    }\n\n    /**\n     * If you are calling this from a component that already knows about a\n     * specific room from props / state, then it's best to prefer\n     * `currentCardForRoom` below to ensure all your data is for a single room\n     * during room changes.\n     */\n    public get currentCard(): IRightPanelCard {\n        const hist = this.roomPhaseHistory;\n        if (hist.length >= 1) {\n            return hist[hist.length - 1];\n        }\n        return { state: {}, phase: null };\n    }\n\n    public currentCardForRoom(roomId: string): IRightPanelCard {\n        const hist = this.byRoom[roomId]?.history ?? [];\n        if (hist.length > 0) {\n            return hist[hist.length - 1];\n        }\n        return { state: {}, phase: null };\n    }\n\n    public get previousCard(): IRightPanelCard {\n        const hist = this.roomPhaseHistory;\n        if (hist?.length >= 2) {\n            return hist[hist.length - 2];\n        }\n        return { state: {}, phase: null };\n    }\n\n    /**\n     * This function behaves as following:\n     * - If the same phase is sent along with a non-empty state, only the state is updated and history is retained.\n     * - If the provided phase is different to the current phase:\n     *     - Existing history is thrown away.\n     *     - New card is added along with a different history, see {@link generateHistoryForPhase}\n     *\n     * If the right panel was set, this function also shows the right panel.\n     */\n    public setCard(card: IRightPanelCard, allowClose = true, roomId?: string): void {\n        const rId = roomId ?? this.viewedRoomId ?? \"\";\n        const redirect = this.getVerificationRedirect(card);\n        const targetPhase = redirect?.phase ?? card.phase;\n        const cardState = redirect?.state ?? (Object.keys(card.state ?? {}).length === 0 ? undefined : card.state);\n\n        // Checks for wrong SetRightPanelPhase requests\n        if (!this.isPhaseValid(targetPhase, Boolean(rId))) return;\n\n        if (targetPhase === this.currentCardForRoom(rId)?.phase && !!cardState) {\n            // Update state: set right panel with a new state but keep the phase (don't know it this is ever needed...)\n            const hist = this.byRoom[rId]?.history ?? [];\n            hist[hist.length - 1].state = cardState;\n            this.emitAndUpdateSettings();\n        } else if (targetPhase !== this.currentCardForRoom(rId)?.phase || !this.byRoom[rId]) {\n            // Set right panel and initialize/erase history\n            const history = this.generateHistoryForPhase(targetPhase!, cardState ?? {});\n            this.byRoom[rId] = { history, isOpen: true };\n            this.emitAndUpdateSettings();\n        } else {\n            this.show(rId);\n            this.emitAndUpdateSettings();\n        }\n    }\n\n    public setCards(cards: IRightPanelCard[], allowClose = true, roomId: string | null = null): void {\n        // This function sets the history of the right panel and shows the right panel if not already visible.\n        const rId = roomId ?? this.viewedRoomId ?? \"\";\n        const history = cards.map((c) => ({ phase: c.phase, state: c.state ?? {} }));\n        this.byRoom[rId] = { history, isOpen: true };\n        this.show(rId);\n        this.emitAndUpdateSettings();\n    }\n\n    // Appends a card to the history and shows the right panel if not already visible\n    public pushCard(card: IRightPanelCard, allowClose = true, roomId: string | null = null): void {\n        const rId = roomId ?? this.viewedRoomId ?? \"\";\n        const redirect = this.getVerificationRedirect(card);\n        const targetPhase = redirect?.phase ?? card.phase;\n        const pState = redirect?.state ?? card.state ?? {};\n\n        // Checks for wrong SetRightPanelPhase requests\n        if (!this.isPhaseValid(targetPhase, Boolean(rId))) return;\n\n        const roomCache = this.byRoom[rId];\n        if (!!roomCache) {\n            // append new phase\n            roomCache.history.push({ state: pState, phase: targetPhase });\n            roomCache.isOpen = allowClose ? roomCache.isOpen : true;\n        } else {\n            // setup room panel cache with the new card\n            this.byRoom[rId] = {\n                history: [{ phase: targetPhase, state: pState }],\n                // if there was no right panel store object the the panel was closed -> keep it closed, except if allowClose==false\n                isOpen: !allowClose,\n            };\n        }\n        this.show(rId);\n        this.emitAndUpdateSettings();\n    }\n\n    public popCard(roomId: string | null = null): IRightPanelCard | undefined {\n        const rId = roomId ?? this.viewedRoomId ?? \"\";\n        if (!this.byRoom[rId]) return;\n\n        const removedCard = this.byRoom[rId].history.pop();\n        this.emitAndUpdateSettings();\n        return removedCard;\n    }\n\n    public togglePanel(roomId: string | null): void {\n        const rId = roomId ?? this.viewedRoomId ?? \"\";\n        if (!this.byRoom[rId]) return;\n\n        this.byRoom[rId].isOpen = !this.byRoom[rId].isOpen;\n        this.emitAndUpdateSettings();\n    }\n\n    public show(roomId: string | null): void {\n        if (!this.isOpenForRoom(roomId ?? this.viewedRoomId ?? \"\")) {\n            this.togglePanel(roomId);\n        }\n    }\n\n    public hide(roomId: string | null): void {\n        if (this.isOpenForRoom(roomId ?? this.viewedRoomId ?? \"\")) {\n            this.togglePanel(roomId);\n        }\n    }\n\n    /**\n     * Helper to show a right panel phase.\n     * If the UI is already showing that phase, the right panel will be hidden.\n     *\n     * Calling the same phase twice with a different state will update the current\n     * phase and push the old state in the right panel history.\n     * @param phase The right panel phase.\n     * @param cardState The state within the phase.\n     */\n    public showOrHidePhase(phase: RightPanelPhases, cardState?: Partial<IRightPanelCardState>): void {\n        if (this.currentCard.phase === phase && !cardState && this.isOpen) {\n            this.togglePanel(null);\n        } else {\n            this.setCard({ phase, state: cardState });\n            if (!this.isOpen) this.togglePanel(null);\n        }\n    }\n\n    /**\n     * For a given phase, generates card history such that it looks\n     * similar to how an user typically would reach said phase in the app.\n     * eg: User would usually reach the memberlist via room-info panel, so\n     * that history is added.\n     */\n    private generateHistoryForPhase(\n        phase: IRightPanelCard[\"phase\"],\n        cardState?: Partial<IRightPanelCardState>,\n    ): IRightPanelCard[] {\n        const card = { phase, state: cardState };\n        if (!this.isCardStateValid(card)) {\n            /**\n             * If the card we're adding is not valid, then we just return\n             * an empty history.\n             * This is to avoid a scenario where, for eg, you set a member info\n             * card with invalid card state (no member) but the member list is\n             * shown since the created history is valid except for the last card.\n             */\n            return [];\n        }\n        const cards = getPhasesForPhase(phase).map((p) => ({ phase: p, state: {} }));\n        return [...cards, card];\n    }\n\n    private loadCacheFromSettings(): void {\n        if (this.viewedRoomId) {\n            const room = this.mxClient?.getRoom(this.viewedRoomId);\n            if (!!room) {\n                this.global =\n                    this.global ??\n                    convertToStatePanel(SettingsStore.getValue(\"RightPanel.phasesGlobal\"), room) ??\n                    undefined;\n                this.byRoom[this.viewedRoomId] =\n                    this.byRoom[this.viewedRoomId] ??\n                    convertToStatePanel(SettingsStore.getValue(\"RightPanel.phases\", this.viewedRoomId), room) ??\n                    undefined;\n            } else {\n                logger.warn(\n                    \"Could not restore the right panel after load because there was no associated room object.\",\n                );\n            }\n        }\n    }\n\n    private emitAndUpdateSettings(): void {\n        this.filterValidCards(this.global);\n        const storePanelGlobal = convertToStorePanel(this.global);\n        SettingsStore.setValue(\"RightPanel.phasesGlobal\", null, SettingLevel.DEVICE, storePanelGlobal);\n\n        if (!!this.viewedRoomId) {\n            const panelThisRoom = this.byRoom[this.viewedRoomId];\n            this.filterValidCards(panelThisRoom);\n            const storePanelThisRoom = convertToStorePanel(panelThisRoom);\n            SettingsStore.setValue(\n                \"RightPanel.phases\",\n                this.viewedRoomId,\n                SettingLevel.ROOM_DEVICE,\n                storePanelThisRoom,\n            );\n        }\n        this.emit(UPDATE_EVENT, null);\n    }\n\n    private filterValidCards(rightPanelForRoom?: IRightPanelForRoom): void {\n        if (!rightPanelForRoom?.history) return;\n        rightPanelForRoom.history = rightPanelForRoom.history.filter((card) => this.isCardStateValid(card));\n        if (!rightPanelForRoom.history.length) {\n            rightPanelForRoom.isOpen = false;\n        }\n    }\n\n    private isCardStateValid(card: IRightPanelCard): boolean {\n        // this function does a sanity check on the card. this is required because\n        // some phases require specific state properties that might not be available.\n        // This can be caused on if element is reloaded and the tries to reload right panel data from id's stored in the local storage.\n        // we store id's of users and matrix events. If are not yet fetched on reload the right panel cannot display them.\n        // or potentially other errors.\n        // (A nicer fix could be to indicate, that the right panel is loading if there is missing state data and re-emit if the data is available)\n        switch (card.phase) {\n            case RightPanelPhases.ThreadView:\n                if (!card.state?.threadHeadEvent) {\n                    logger.warn(\"removed card from right panel because of missing threadHeadEvent in card state\");\n                }\n                return !!card.state?.threadHeadEvent;\n            case RightPanelPhases.MemberInfo:\n            case RightPanelPhases.EncryptionPanel:\n                if (!card.state?.member) {\n                    logger.warn(\"removed card from right panel because of missing member in card state\");\n                }\n                return !!card.state?.member;\n            case RightPanelPhases.ThreePidMemberInfo:\n                if (!card.state?.memberInfoEvent) {\n                    logger.warn(\"removed card from right panel because of missing memberInfoEvent in card state\");\n                }\n                return !!card.state?.memberInfoEvent;\n            case RightPanelPhases.Widget:\n                if (!card.state?.widgetId) {\n                    logger.warn(\"removed card from right panel because of missing widgetId in card state\");\n                }\n                return !!card.state?.widgetId;\n        }\n        return true;\n    }\n\n    private getVerificationRedirect(card: IRightPanelCard): IRightPanelCard | null {\n        if (card.phase === RightPanelPhases.MemberInfo && card.state) {\n            // RightPanelPhases.RoomMemberInfo -> needs to be changed to RightPanelPhases.EncryptionPanel if there is a pending verification request\n            const { member } = card.state;\n            const pendingRequest = member\n                ? pendingVerificationRequestForUser(MatrixClientPeg.safeGet(), member)\n                : undefined;\n            if (pendingRequest) {\n                return {\n                    phase: RightPanelPhases.EncryptionPanel,\n                    state: {\n                        verificationRequest: pendingRequest,\n                        member,\n                    },\n                };\n            }\n        }\n        return null;\n    }\n\n    private isPhaseValid(targetPhase: RightPanelPhases | null, isViewingRoom: boolean): boolean {\n        if (!targetPhase || !RightPanelPhases[targetPhase]) {\n            logger.warn(`Tried to switch right panel to unknown phase: ${targetPhase}`);\n            return false;\n        }\n        if (!isViewingRoom) {\n            logger.warn(\n                `Tried to switch right panel to a room phase: ${targetPhase}, ` +\n                    `but we are currently not viewing a room`,\n            );\n            return false;\n        }\n        return true;\n    }\n\n    private onVerificationRequestUpdate = (): void => {\n        if (!this.currentCard?.state) return;\n        const { member } = this.currentCard.state;\n        if (!member) return;\n        const pendingRequest = pendingVerificationRequestForUser(MatrixClientPeg.safeGet(), member);\n        if (pendingRequest) {\n            this.currentCard.state.verificationRequest = pendingRequest;\n            this.emitAndUpdateSettings();\n        }\n    };\n\n    private handleViewedRoomChange(oldRoomId: string | null, newRoomId: string | null): void {\n        if (!this.mxClient) return; // not ready, onReady will handle the first room\n        this.viewedRoomId = newRoomId;\n        // load values from byRoomCache with the viewedRoomId.\n        this.loadCacheFromSettings();\n\n        // when we're switching to a room, clear out any stale MemberInfo cards\n        // in order to fix https://github.com/vector-im/element-web/issues/21487\n        if (this.currentCard?.phase !== RightPanelPhases.EncryptionPanel) {\n            const panel = this.byRoom[this.viewedRoomId ?? \"\"];\n            if (panel?.history) {\n                panel.history = panel.history.filter(\n                    (card: IRightPanelCard) =>\n                        card.phase != RightPanelPhases.MemberInfo && card.phase != RightPanelPhases.ThreePidMemberInfo,\n                );\n            }\n        }\n        // when we're switching to a room, clear out thread permalinks to not get you stuck in the middle of the thread\n        // in order to fix https://github.com/matrix-org/matrix-react-sdk/pull/11011\n        if (this.currentCard?.phase === RightPanelPhases.ThreadView && this.currentCard.state) {\n            this.currentCard.state.initialEvent = undefined;\n            this.currentCard.state.isInitialEventHighlighted = undefined;\n            this.currentCard.state.initialEventScrollIntoView = undefined;\n        }\n\n        this.emitAndUpdateSettings();\n    }\n\n    public static get instance(): RightPanelStore {\n        if (!this.internalInstance) {\n            this.internalInstance = new RightPanelStore();\n            this.internalInstance.start();\n        }\n        return this.internalInstance;\n    }\n}\n\nwindow.mxRightPanelStore = RightPanelStore.instance;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { _t } from \"../../languageHandler\";\n\n// These are in their own file because of circular imports being a problem.\nexport enum RightPanelPhases {\n    // Room & Space stuff\n    MemberList = \"MemberList\",\n    MemberInfo = \"MemberInfo\",\n    ThreePidMemberInfo = \"ThreePidMemberInfo\",\n\n    // Room stuff\n    FilePanel = \"FilePanel\",\n    NotificationPanel = \"NotificationPanel\",\n    EncryptionPanel = \"EncryptionPanel\",\n    RoomSummary = \"RoomSummary\",\n    Widget = \"Widget\",\n    PinnedMessages = \"PinnedMessages\",\n    Timeline = \"Timeline\",\n    Extensions = \"Extensions\",\n\n    // Thread stuff\n    ThreadView = \"ThreadView\",\n    ThreadPanel = \"ThreadPanel\",\n}\n\nexport function backLabelForPhase(phase: RightPanelPhases | null): string | null {\n    switch (phase) {\n        case RightPanelPhases.ThreadPanel:\n            return _t(\"common|threads\");\n        case RightPanelPhases.Timeline:\n            return _t(\"chat_card_back_action_label\");\n        case RightPanelPhases.RoomSummary:\n            return _t(\"room_summary_card_back_action_label\");\n        case RightPanelPhases.MemberList:\n            return _t(\"member_list_back_action_label\");\n        case RightPanelPhases.ThreadView:\n            return _t(\"thread_view_back_action_label\");\n    }\n    return null;\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type { Room } from \"matrix-js-sdk/src/matrix\";\n\nexport interface Sorter {\n    /**\n     * Performs an initial sort of rooms and returns a new array containing\n     * the result.\n     * @param rooms An array of rooms.\n     */\n    sort(rooms: Room[]): Room[];\n    /**\n     * The comparator used for sorting.\n     * @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/sort#comparefn\n     * @param roomA Room\n     * @param roomB Room\n     */\n    comparator(roomA: Room, roomB: Room): number;\n    /**\n     * A string that uniquely identifies this given sorter.\n     */\n    type: SortingAlgorithm;\n}\n\n/**\n * All the available sorting algorithms.\n */\nexport const enum SortingAlgorithm {\n    Unread = \"Unread\",\n    Recency = \"Recency\",\n    Alphabetic = \"Alphabetic\",\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { DefaultTagID, type TagID } from \"../models\";\n\nexport function isSelf(event: MatrixEvent): boolean {\n    const selfUserId = MatrixClientPeg.safeGet().getSafeUserId();\n    if (event.getType() === \"m.room.member\") {\n        return event.getStateKey() === selfUserId;\n    }\n    return event.getSender() === selfUserId;\n}\n\nexport function shouldPrefixMessagesIn(roomId: string, tagId?: TagID): boolean {\n    if (tagId !== DefaultTagID.DM) return true;\n\n    // We don't prefix anything in 1:1s\n    const room = MatrixClientPeg.safeGet().getRoom(roomId);\n    if (!room) return true;\n    return room.currentState.getJoinedMemberCount() !== 2;\n}\n\nexport function getSenderName(event: MatrixEvent): string {\n    return event.sender?.name ?? event.getSender() ?? \"\";\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, type PollStartEventContent } from \"matrix-js-sdk/src/matrix\";\nimport { InvalidEventError } from \"matrix-js-sdk/src/extensible_events_v1/InvalidEventError\";\nimport { PollStartEvent } from \"matrix-js-sdk/src/extensible_events_v1/PollStartEvent\";\n\nimport { type IPreview } from \"./IPreview\";\nimport { type TagID } from \"../models\";\nimport { _t, sanitizeForTranslation } from \"../../../languageHandler\";\nimport { getSenderName, isSelf, shouldPrefixMessagesIn } from \"./utils\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\n\nexport class PollStartEventPreview implements IPreview {\n    public static contextType = MatrixClientContext;\n    declare public context: React.ContextType<typeof MatrixClientContext>;\n\n    public getTextFor(event: MatrixEvent, tagId?: TagID, isThread?: boolean): string | null {\n        let eventContent = event.getContent();\n\n        if (event.isRelation(\"m.replace\")) {\n            // It's an edit, generate the preview on the new text\n            eventContent = event.getContent()[\"m.new_content\"];\n        }\n\n        // Check we have the information we need, and bail out if not\n        if (!eventContent) {\n            return null;\n        }\n\n        try {\n            const poll = new PollStartEvent({\n                type: event.getType(),\n                content: eventContent as PollStartEventContent,\n            });\n\n            let question = poll.question.text.trim();\n            question = sanitizeForTranslation(question);\n\n            if (isThread || isSelf(event) || !shouldPrefixMessagesIn(event.getRoomId()!, tagId)) {\n                return question;\n            } else {\n                return _t(\"event_preview|m.text\", { senderName: getSenderName(event), message: question });\n            }\n        } catch (e) {\n            if (e instanceof InvalidEventError) {\n                return null;\n            }\n            throw e; // re-throw unknown errors\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type Room,\n    RelationType,\n    type MatrixEvent,\n    type Thread,\n    M_POLL_START,\n    RoomEvent,\n    type EmptyObject,\n} from \"matrix-js-sdk/src/matrix\";\nimport { isNullOrUndefined } from \"matrix-js-sdk/src/utils\";\n\nimport { type ActionPayload } from \"../../dispatcher/payloads\";\nimport { AsyncStoreWithClient } from \"../AsyncStoreWithClient\";\nimport defaultDispatcher from \"../../dispatcher/dispatcher\";\nimport { MessageEventPreview } from \"./previews/MessageEventPreview\";\nimport { PollStartEventPreview } from \"./previews/PollStartEventPreview\";\nimport { type TagID } from \"./models\";\nimport { LegacyCallInviteEventPreview } from \"./previews/LegacyCallInviteEventPreview\";\nimport { LegacyCallAnswerEventPreview } from \"./previews/LegacyCallAnswerEventPreview\";\nimport { LegacyCallHangupEvent } from \"./previews/LegacyCallHangupEvent\";\nimport { StickerEventPreview } from \"./previews/StickerEventPreview\";\nimport { ReactionEventPreview } from \"./previews/ReactionEventPreview\";\nimport { UPDATE_EVENT } from \"../AsyncStore\";\nimport { type IPreview } from \"./previews/IPreview\";\nimport shouldHideEvent from \"../../shouldHideEvent\";\nimport SettingsStore from \"../../settings/SettingsStore\";\n\n// Emitted event for when a room's preview has changed. First argument will the room for which\n// the change happened.\nconst ROOM_PREVIEW_CHANGED = \"room_preview_changed\";\n\nconst PREVIEWS: Record<\n    string,\n    {\n        isState: boolean;\n        previewer: IPreview;\n    }\n> = {\n    \"m.room.message\": {\n        isState: false,\n        previewer: new MessageEventPreview(),\n    },\n    \"m.call.invite\": {\n        isState: false,\n        previewer: new LegacyCallInviteEventPreview(),\n    },\n    \"m.call.answer\": {\n        isState: false,\n        previewer: new LegacyCallAnswerEventPreview(),\n    },\n    \"m.call.hangup\": {\n        isState: false,\n        previewer: new LegacyCallHangupEvent(),\n    },\n    \"m.sticker\": {\n        isState: false,\n        previewer: new StickerEventPreview(),\n    },\n    \"m.reaction\": {\n        isState: false,\n        previewer: new ReactionEventPreview(),\n    },\n    [M_POLL_START.name]: {\n        isState: false,\n        previewer: new PollStartEventPreview(),\n    },\n    [M_POLL_START.altName]: {\n        isState: false,\n        previewer: new PollStartEventPreview(),\n    },\n};\n\n// The maximum number of events we're willing to look back on to get a preview.\nconst MAX_EVENTS_BACKWARDS = 50;\n\n// type merging ftw\ntype TAG_ANY = \"im.vector.any\"; // eslint-disable-line @typescript-eslint/naming-convention\nconst TAG_ANY: TAG_ANY = \"im.vector.any\";\n\nexport interface MessagePreview {\n    event: MatrixEvent;\n    isThreadReply: boolean;\n    text: string;\n}\n\nconst isThreadReply = (event: MatrixEvent): boolean => {\n    // a thread root event cannot be a thread reply\n    if (event.isThreadRoot) return false;\n\n    const thread = event.getThread();\n\n    // it cannot be a thread reply if there is no thread\n    if (!thread) return false;\n\n    const relation = event.getRelation();\n\n    if (\n        !!relation &&\n        relation.rel_type === RelationType.Annotation &&\n        relation.event_id === thread.rootEvent?.getId()\n    ) {\n        // annotations on the thread root are not a thread reply\n        return false;\n    }\n\n    return true;\n};\n\nconst mkMessagePreview = (text: string, event: MatrixEvent): MessagePreview => {\n    return {\n        event,\n        text,\n        isThreadReply: isThreadReply(event),\n    };\n};\n\nexport class MessagePreviewStore extends AsyncStoreWithClient<EmptyObject> {\n    private static readonly internalInstance = (() => {\n        const instance = new MessagePreviewStore();\n        instance.start();\n        return instance;\n    })();\n\n    /**\n     * @internal Public for test only\n     */\n    public static testInstance(): MessagePreviewStore {\n        return new MessagePreviewStore();\n    }\n\n    // null indicates the preview is empty / irrelevant\n    private previews = new Map<string, Map<TagID | TAG_ANY, MessagePreview | null>>();\n\n    private constructor() {\n        super(defaultDispatcher, {});\n    }\n\n    public static get instance(): MessagePreviewStore {\n        return MessagePreviewStore.internalInstance;\n    }\n\n    public static getPreviewChangedEventName(room: Room): string {\n        return `${ROOM_PREVIEW_CHANGED}:${room?.roomId}`;\n    }\n\n    /**\n     * Gets the pre-translated preview for a given room\n     * @param room The room to get the preview for.\n     * @param inTagId The tag ID in which the room resides\n     * @returns The preview, or null if none present.\n     */\n    public async getPreviewForRoom(room: Room, inTagId: TagID): Promise<MessagePreview | null> {\n        if (!room) return null; // invalid room, just return nothing\n\n        if (!this.previews.has(room.roomId)) await this.generatePreview(room, inTagId);\n\n        const previews = this.previews.get(room.roomId);\n        if (!previews) return null;\n\n        if (previews.has(inTagId)) {\n            return previews.get(inTagId)!;\n        }\n        return previews.get(TAG_ANY) ?? null;\n    }\n\n    public generatePreviewForEvent(event: MatrixEvent): string {\n        const previewDef = PREVIEWS[event.getType()];\n        return previewDef?.previewer.getTextFor(event, undefined, true) ?? \"\";\n    }\n\n    private async generatePreview(room: Room, tagId?: TagID): Promise<void> {\n        const events = [...room.getLiveTimeline().getEvents(), ...room.getPendingEvents()];\n\n        const isNewRoomListEnabled = SettingsStore.getValue(\"feature_new_room_list\");\n        if (!isNewRoomListEnabled) {\n            // add last reply from each thread\n            room.getThreads().forEach((thread: Thread): void => {\n                const lastReply = thread.lastReply();\n                if (lastReply) events.push(lastReply);\n            });\n        }\n\n        // sort events from oldest to newest\n        events.sort((a: MatrixEvent, b: MatrixEvent) => {\n            return a.getTs() - b.getTs();\n        });\n\n        if (!events) return; // should only happen in tests\n\n        let map = this.previews.get(room.roomId);\n        if (!map) {\n            map = new Map<TagID | TAG_ANY, MessagePreview | null>();\n            this.previews.set(room.roomId, map);\n        }\n\n        // Set the tags so we know what to generate\n        if (!map.has(TAG_ANY)) map.set(TAG_ANY, null);\n        if (tagId && !map.has(tagId)) map.set(tagId, null);\n\n        let changed = false;\n        for (let i = events.length - 1; i >= 0; i--) {\n            if (i === events.length - MAX_EVENTS_BACKWARDS) {\n                // limit reached - clear the preview by breaking out of the loop\n                break;\n            }\n\n            const event = events[i];\n\n            await this.matrixClient?.decryptEventIfNeeded(event);\n            const shouldHide = shouldHideEvent(event);\n            if (shouldHide) continue;\n            const previewDef = PREVIEWS[event.getType()];\n            if (!previewDef) continue;\n            if (previewDef.isState && isNullOrUndefined(event.getStateKey())) continue;\n\n            const anyPreviewText = previewDef.previewer.getTextFor(event);\n            if (!anyPreviewText) continue; // not previewable for some reason\n\n            changed = changed || anyPreviewText !== map.get(TAG_ANY)?.text;\n            map.set(TAG_ANY, mkMessagePreview(anyPreviewText, event));\n\n            const tagsToGenerate = Array.from(map.keys()).filter((t) => t !== TAG_ANY); // we did the any tag above\n            for (const genTagId of tagsToGenerate) {\n                const realTagId = genTagId === TAG_ANY ? undefined : genTagId;\n                const preview = previewDef.previewer.getTextFor(event, realTagId);\n\n                if (preview === anyPreviewText) {\n                    changed = changed || anyPreviewText !== map.get(genTagId)?.text;\n                    map.delete(genTagId);\n                } else {\n                    changed = changed || preview !== map.get(genTagId)?.text;\n                    map.set(genTagId, preview ? mkMessagePreview(anyPreviewText, event) : null);\n                }\n            }\n\n            if (changed) {\n                // We've muted the underlying Map, so just emit that we've changed.\n                this.previews.set(room.roomId, map);\n                this.emit(UPDATE_EVENT, this);\n                this.emit(MessagePreviewStore.getPreviewChangedEventName(room), room);\n            }\n            return; // we're done\n        }\n\n        // At this point, we didn't generate a preview so clear it\n        this.previews.set(room.roomId, new Map<TagID | TAG_ANY, MessagePreview | null>());\n        this.emit(UPDATE_EVENT, this);\n        this.emit(MessagePreviewStore.getPreviewChangedEventName(room), room);\n    }\n\n    protected async onAction(payload: ActionPayload): Promise<void> {\n        if (!this.matrixClient) return;\n\n        if (payload.action === \"MatrixActions.Room.timeline\" || payload.action === \"MatrixActions.Event.decrypted\") {\n            const event = payload.event; // TODO: Type out the dispatcher\n            const roomId = event.getRoomId();\n            const isHistoricalEvent = payload.hasOwnProperty(\"isLiveEvent\") && !payload.isLiveEvent;\n\n            if (!roomId || !this.previews.has(roomId) || isHistoricalEvent) return;\n\n            const room = this.matrixClient.getRoom(roomId);\n\n            if (!room) return;\n\n            await this.generatePreview(room, TAG_ANY);\n        }\n    }\n\n    protected async onReady(): Promise<void> {\n        if (!this.matrixClient) return;\n        this.matrixClient.on(RoomEvent.LocalEchoUpdated, this.onLocalEchoUpdated);\n    }\n\n    protected async onNotReady(): Promise<void> {\n        if (!this.matrixClient) return;\n        this.matrixClient.off(RoomEvent.LocalEchoUpdated, this.onLocalEchoUpdated);\n    }\n\n    protected onLocalEchoUpdated = async (ev: MatrixEvent, room: Room): Promise<void> => {\n        if (!this.previews.has(room.roomId)) return;\n        await this.generatePreview(room, TAG_ANY);\n    };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, MsgType, RelationType } from \"matrix-js-sdk/src/matrix\";\n\nimport { type IPreview } from \"./IPreview\";\nimport { type TagID } from \"../models\";\nimport { _t, sanitizeForTranslation } from \"../../../languageHandler\";\nimport { getSenderName, isSelf, shouldPrefixMessagesIn } from \"./utils\";\nimport { getHtmlText } from \"../../../HtmlUtils\";\nimport { stripHTMLReply, stripPlainReply } from \"../../../utils/Reply\";\n\nexport class MessageEventPreview implements IPreview {\n    public getTextFor(event: MatrixEvent, tagId?: TagID, isThread?: boolean): string | null {\n        let eventContent = event.getContent();\n\n        if (event.isRelation(RelationType.Replace)) {\n            // It's an edit, generate the preview on the new text\n            eventContent = event.getContent()[\"m.new_content\"];\n        }\n\n        if (!eventContent?.[\"body\"]) return null; // invalid for our purposes\n\n        let body = eventContent[\"body\"].trim();\n        if (!body) return null; // invalid event, no preview\n        // A msgtype is actually required in the spec but the app is a bit softer on this requirement\n        const msgtype = eventContent[\"msgtype\"] ?? MsgType.Text;\n\n        const hasHtml = eventContent.format === \"org.matrix.custom.html\" && eventContent.formatted_body;\n        if (hasHtml) {\n            body = eventContent.formatted_body;\n        }\n\n        // XXX: Newer relations have a getRelation() function which is not compatible with replies.\n        if (event.getWireContent()[\"m.relates_to\"]?.[\"m.in_reply_to\"]) {\n            // If this is a reply, get the real reply and use that\n            if (hasHtml) {\n                body = (stripHTMLReply(body) || \"\").trim();\n            } else {\n                body = (stripPlainReply(body) || \"\").trim();\n            }\n            if (!body) return null; // invalid event, no preview\n        }\n\n        if (hasHtml) {\n            const sanitised = getHtmlText(body.replace(/<br\\/?>/gi, \"\\n\")); // replace line breaks before removing them\n            // run it through DOMParser to fixup encoded html entities\n            body = new DOMParser().parseFromString(sanitised, \"text/html\").documentElement.textContent;\n        }\n\n        body = sanitizeForTranslation(body);\n\n        if (msgtype === MsgType.Emote) {\n            return _t(\"event_preview|m.emote\", { senderName: getSenderName(event), emote: body });\n        }\n\n        const roomId = event.getRoomId();\n\n        if (isThread || isSelf(event) || (roomId && !shouldPrefixMessagesIn(roomId, tagId))) {\n            return body;\n        } else {\n            return _t(\"event_preview|m.text\", { senderName: getSenderName(event), message: body });\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { type IPreview } from \"./IPreview\";\nimport { type TagID } from \"../models\";\nimport { getSenderName, isSelf, shouldPrefixMessagesIn } from \"./utils\";\nimport { _t } from \"../../../languageHandler\";\n\nexport class LegacyCallInviteEventPreview implements IPreview {\n    public getTextFor(event: MatrixEvent, tagId?: TagID): string {\n        if (shouldPrefixMessagesIn(event.getRoomId()!, tagId)) {\n            if (isSelf(event)) {\n                return _t(\"event_preview|m.call.invite|you\");\n            } else {\n                return _t(\"event_preview|m.call.invite|user\", { senderName: getSenderName(event) });\n            }\n        } else {\n            if (isSelf(event)) {\n                return _t(\"event_preview|m.call.invite|dm_send\");\n            } else {\n                return _t(\"event_preview|m.call.invite|dm_receive\", { senderName: getSenderName(event) });\n            }\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { type IPreview } from \"./IPreview\";\nimport { type TagID } from \"../models\";\nimport { getSenderName, isSelf, shouldPrefixMessagesIn } from \"./utils\";\nimport { _t } from \"../../../languageHandler\";\n\nexport class LegacyCallAnswerEventPreview implements IPreview {\n    public getTextFor(event: MatrixEvent, tagId?: TagID): string {\n        if (shouldPrefixMessagesIn(event.getRoomId()!, tagId)) {\n            if (isSelf(event)) {\n                return _t(\"event_preview|m.call.answer|you\");\n            } else {\n                return _t(\"event_preview|m.call.answer|user\", { senderName: getSenderName(event) });\n            }\n        } else {\n            return _t(\"event_preview|m.call.answer|dm\");\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { type IPreview } from \"./IPreview\";\nimport { type TagID } from \"../models\";\nimport { getSenderName, isSelf, shouldPrefixMessagesIn } from \"./utils\";\nimport { _t } from \"../../../languageHandler\";\n\nexport class LegacyCallHangupEvent implements IPreview {\n    public getTextFor(event: MatrixEvent, tagId?: TagID): string {\n        if (shouldPrefixMessagesIn(event.getRoomId()!, tagId)) {\n            if (isSelf(event)) {\n                return _t(\"event_preview|m.call.hangup|you\");\n            } else {\n                return _t(\"event_preview|m.call.hangup|user\", { senderName: getSenderName(event) });\n            }\n        } else {\n            return _t(\"timeline|m.call.hangup|dm\");\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { type IPreview } from \"./IPreview\";\nimport { type TagID } from \"../models\";\nimport { getSenderName, isSelf, shouldPrefixMessagesIn } from \"./utils\";\nimport { _t } from \"../../../languageHandler\";\n\nexport class StickerEventPreview implements IPreview {\n    public getTextFor(event: MatrixEvent, tagId?: TagID, isThread?: boolean): string | null {\n        const stickerName = event.getContent()[\"body\"];\n        if (!stickerName) return null;\n\n        if (isThread || isSelf(event) || !shouldPrefixMessagesIn(event.getRoomId()!, tagId)) {\n            return stickerName;\n        } else {\n            return _t(\"event_preview|m.sticker\", { senderName: getSenderName(event), stickerName });\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\n\nimport { type IPreview } from \"./IPreview\";\nimport { type TagID } from \"../models\";\nimport { getSenderName, isSelf } from \"./utils\";\nimport { _t } from \"../../../languageHandler\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { MessagePreviewStore } from \"../MessagePreviewStore\";\n\nexport class ReactionEventPreview implements IPreview {\n    public getTextFor(event: MatrixEvent, tagId?: TagID, isThread?: boolean): string | null {\n        const roomId = event.getRoomId();\n        if (!roomId) return null; // not a room event\n\n        const relation = event.getRelation();\n        if (!relation) return null; // invalid reaction (probably redacted)\n\n        const reaction = relation.key;\n        if (!reaction) return null; // invalid reaction (unknown format)\n\n        const cli = MatrixClientPeg.get();\n        const room = cli?.getRoom(roomId);\n        const relatedEvent = relation.event_id ? room?.findEventById(relation.event_id) : null;\n        if (!relatedEvent) return null;\n\n        const message = MessagePreviewStore.instance.generatePreviewForEvent(relatedEvent);\n        if (isSelf(event)) {\n            return _t(\"event_preview|m.reaction|you\", {\n                reaction,\n                message,\n            });\n        }\n\n        return _t(\"event_preview|m.reaction|user\", {\n            sender: getSenderName(event),\n            reaction,\n            message,\n        });\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type TagID } from \"./models\";\n\nconst TILE_HEIGHT_PX = 44;\n\ninterface ISerializedListLayout {\n    numTiles: number;\n    showPreviews: boolean;\n    collapsed: boolean;\n}\n\nexport class ListLayout {\n    private _n = 0;\n    private _previews = false;\n    private _collapsed = false;\n\n    public constructor(public readonly tagId: TagID) {\n        const serialized = localStorage.getItem(this.key);\n        if (serialized) {\n            // We don't use the setters as they cause writes.\n            const parsed = <ISerializedListLayout>JSON.parse(serialized);\n            this._n = parsed.numTiles;\n            this._previews = parsed.showPreviews;\n            this._collapsed = parsed.collapsed;\n        }\n    }\n\n    public get isCollapsed(): boolean {\n        return this._collapsed;\n    }\n\n    public set isCollapsed(v: boolean) {\n        this._collapsed = v;\n        this.save();\n    }\n\n    public get showPreviews(): boolean {\n        return this._previews;\n    }\n\n    public set showPreviews(v: boolean) {\n        this._previews = v;\n        this.save();\n    }\n\n    public get tileHeight(): number {\n        return TILE_HEIGHT_PX;\n    }\n\n    private get key(): string {\n        return `mx_sublist_layout_${this.tagId}_boxed`;\n    }\n\n    public get visibleTiles(): number {\n        if (this._n === 0) return this.defaultVisibleTiles;\n        return Math.max(this._n, this.minVisibleTiles);\n    }\n\n    public set visibleTiles(v: number) {\n        this._n = v;\n        this.save();\n    }\n\n    public get minVisibleTiles(): number {\n        return 1;\n    }\n\n    public get defaultVisibleTiles(): number {\n        // This number is what \"feels right\", and mostly subject to design's opinion.\n        return 8;\n    }\n\n    public tilesWithPadding(n: number, paddingPx: number): number {\n        return this.pixelsToTiles(this.tilesToPixelsWithPadding(n, paddingPx));\n    }\n\n    public tilesToPixelsWithPadding(n: number, paddingPx: number): number {\n        return this.tilesToPixels(n) + paddingPx;\n    }\n\n    public tilesToPixels(n: number): number {\n        return n * this.tileHeight;\n    }\n\n    public pixelsToTiles(px: number): number {\n        return px / this.tileHeight;\n    }\n\n    public reset(): void {\n        localStorage.removeItem(this.key);\n    }\n\n    private save(): void {\n        localStorage.setItem(this.key, JSON.stringify(this.serialize()));\n    }\n\n    private serialize(): ISerializedListLayout {\n        return {\n            numTiles: this.visibleTiles,\n            showPreviews: this.showPreviews,\n            collapsed: this.isCollapsed,\n        };\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type EmptyObject } from \"matrix-js-sdk/src/matrix\";\n\nimport { type TagID } from \"./models\";\nimport { ListLayout } from \"./ListLayout\";\nimport { AsyncStoreWithClient } from \"../AsyncStoreWithClient\";\nimport defaultDispatcher from \"../../dispatcher/dispatcher\";\nimport { type ActionPayload } from \"../../dispatcher/payloads\";\n\nexport default class RoomListLayoutStore extends AsyncStoreWithClient<EmptyObject> {\n    private static internalInstance: RoomListLayoutStore;\n\n    private readonly layoutMap = new Map<TagID, ListLayout>();\n\n    public constructor() {\n        super(defaultDispatcher);\n    }\n\n    public static get instance(): RoomListLayoutStore {\n        if (!this.internalInstance) {\n            this.internalInstance = new RoomListLayoutStore();\n            this.internalInstance.start();\n        }\n        return RoomListLayoutStore.internalInstance;\n    }\n\n    public ensureLayoutExists(tagId: TagID): void {\n        if (!this.layoutMap.has(tagId)) {\n            this.layoutMap.set(tagId, new ListLayout(tagId));\n        }\n    }\n\n    public getLayoutFor(tagId: TagID): ListLayout {\n        if (!this.layoutMap.has(tagId)) {\n            this.layoutMap.set(tagId, new ListLayout(tagId));\n        }\n        return this.layoutMap.get(tagId)!;\n    }\n\n    // Note: this primarily exists for debugging, and isn't really intended to be used by anything.\n    public async resetLayouts(): Promise<void> {\n        logger.warn(\"Resetting layouts for room list\");\n        for (const layout of this.layoutMap.values()) {\n            layout.reset();\n        }\n    }\n\n    protected async onNotReady(): Promise<any> {\n        // On logout, clear the map.\n        this.layoutMap.clear();\n    }\n\n    // We don't need this function, but our contract says we do\n    protected async onAction(payload: ActionPayload): Promise<void> {}\n}\n\nwindow.mxRoomListLayoutStore = RoomListLayoutStore.instance;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { type EventEmitter } from \"events\";\n\nexport const FILTER_CHANGED = \"filter_changed\";\n\n/**\n * A filter condition for the room list, determining if a room\n * should be shown or not.\n *\n * All filter conditions are expected to be stable executions,\n * meaning that given the same input the same answer will be\n * returned (thus allowing caching). As such, filter conditions\n * can, but shouldn't, do heavier logic and not worry about being\n * called constantly by the room list. When the condition changes\n * such that different inputs lead to different answers (such\n * as a change in the user's input), this emits FILTER_CHANGED.\n */\nexport interface IFilterCondition extends EventEmitter {\n    /**\n     * Determines if a given room should be visible under this\n     * condition.\n     * @param room The room to check.\n     * @returns True if the room should be visible.\n     */\n    isVisible(room: Room): boolean;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { SortAlgorithm } from \"../models\";\nimport { ManualAlgorithm } from \"./ManualAlgorithm\";\nimport { type IAlgorithm } from \"./IAlgorithm\";\nimport { type TagID } from \"../../models\";\nimport { RecentAlgorithm } from \"./RecentAlgorithm\";\nimport { AlphabeticAlgorithm } from \"./AlphabeticAlgorithm\";\n\nconst ALGORITHM_INSTANCES: { [algorithm in SortAlgorithm]: IAlgorithm } = {\n    [SortAlgorithm.Recent]: new RecentAlgorithm(),\n    [SortAlgorithm.Alphabetic]: new AlphabeticAlgorithm(),\n    [SortAlgorithm.Manual]: new ManualAlgorithm(),\n};\n\n/**\n * Gets an instance of the defined algorithm\n * @param {SortAlgorithm} algorithm The algorithm to get an instance of.\n * @returns {IAlgorithm} The algorithm instance.\n */\nexport function getSortingAlgorithmInstance(algorithm: SortAlgorithm): IAlgorithm {\n    if (!ALGORITHM_INSTANCES[algorithm]) {\n        throw new Error(`${algorithm} is not a known algorithm`);\n    }\n\n    return ALGORITHM_INSTANCES[algorithm];\n}\n\n/**\n * Sorts rooms in a given tag according to the algorithm given.\n * @param {Room[]} rooms The rooms to sort.\n * @param {TagID} tagId The tag in which the sorting is occurring.\n * @param {SortAlgorithm} algorithm The algorithm to use for sorting.\n * @returns {Room[]} Returns the sorted rooms.\n */\nexport function sortRoomsWithAlgorithm(rooms: Room[], tagId: TagID, algorithm: SortAlgorithm): Room[] {\n    return getSortingAlgorithmInstance(algorithm).sortRooms(rooms, tagId);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { type TagID } from \"../../models\";\nimport { type IAlgorithm } from \"./IAlgorithm\";\n\n/**\n * Sorts rooms according to the browser's determination of alphabetic.\n */\nexport class AlphabeticAlgorithm implements IAlgorithm {\n    public sortRooms(rooms: Room[], tagId: TagID): Room[] {\n        const collator = new Intl.Collator();\n        return rooms.sort((a, b) => {\n            return collator.compare(a.name, b.name);\n        });\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { type TagID } from \"../../models\";\nimport { type IAlgorithm } from \"./IAlgorithm\";\n\n/**\n * Sorts rooms according to the tag's `order` property on the room.\n */\nexport class ManualAlgorithm implements IAlgorithm {\n    public sortRooms(rooms: Room[], tagId: TagID): Room[] {\n        const getOrderProp = (r: Room): number => r.tags[tagId].order || 0;\n        return rooms.sort((a, b) => {\n            return getOrderProp(a) - getOrderProp(b);\n        });\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { type RoomUpdateCause, type TagID } from \"../../models\";\nimport { SortAlgorithm } from \"../models\";\n\n/**\n * Represents a list ordering algorithm. Subclasses should populate the\n * `cachedOrderedRooms` field.\n */\nexport abstract class OrderingAlgorithm {\n    protected cachedOrderedRooms: Room[] = [];\n\n    // set by setSortAlgorithm() in ctor\n    protected sortingAlgorithm!: SortAlgorithm;\n\n    protected constructor(\n        protected tagId: TagID,\n        initialSortingAlgorithm: SortAlgorithm,\n    ) {\n        // noinspection JSIgnoredPromiseFromCall\n        this.setSortAlgorithm(initialSortingAlgorithm); // we use the setter for validation\n    }\n\n    /**\n     * The rooms as ordered by the algorithm.\n     */\n    public get orderedRooms(): Room[] {\n        return this.cachedOrderedRooms;\n    }\n\n    public get isMutedToBottom(): boolean {\n        return this.sortingAlgorithm === SortAlgorithm.Recent;\n    }\n\n    /**\n     * Sets the sorting algorithm to use within the list.\n     * @param newAlgorithm The new algorithm. Must be defined.\n     * @returns Resolves when complete.\n     */\n    public setSortAlgorithm(newAlgorithm: SortAlgorithm): void {\n        if (!newAlgorithm) throw new Error(\"A sorting algorithm must be defined\");\n        this.sortingAlgorithm = newAlgorithm;\n\n        // Force regeneration of the rooms\n        this.setRooms(this.orderedRooms);\n    }\n\n    /**\n     * Sets the rooms the algorithm should be handling, implying a reconstruction\n     * of the ordering.\n     * @param rooms The rooms to use going forward.\n     */\n    public abstract setRooms(rooms: Room[]): void;\n\n    /**\n     * Handle a room update. The Algorithm will only call this for causes which\n     * the list ordering algorithm can handle within the same tag. For example,\n     * tag changes will not be sent here.\n     * @param room The room where the update happened.\n     * @param cause The cause of the update.\n     * @returns True if the update requires the Algorithm to update the presentation layers.\n     */\n    public abstract handleRoomUpdate(room: Room, cause: RoomUpdateCause): boolean;\n\n    protected getRoomIndex(room: Room): number {\n        let roomIdx = this.cachedOrderedRooms.indexOf(room);\n        if (roomIdx === -1) {\n            // can only happen if the js-sdk's store goes sideways.\n            logger.warn(`Degrading performance to find missing room in \"${this.tagId}\": ${room.roomId}`);\n            roomIdx = this.cachedOrderedRooms.findIndex((r) => r.roomId === room.roomId);\n        }\n        return roomIdx;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2018, 2019 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { RoomUpdateCause, type TagID } from \"../../models\";\nimport { SortAlgorithm } from \"../models\";\nimport { sortRoomsWithAlgorithm } from \"../tag-sorting\";\nimport { OrderingAlgorithm } from \"./OrderingAlgorithm\";\nimport { NotificationLevel } from \"../../../notifications/NotificationLevel\";\nimport { RoomNotificationStateStore } from \"../../../notifications/RoomNotificationStateStore\";\n\ntype CategorizedRoomMap = {\n    [category in NotificationLevel]: Room[];\n};\n\ntype CategoryIndex = Partial<{\n    [category in NotificationLevel]: number; // integer\n}>;\n\n// Caution: changing this means you'll need to update a bunch of assumptions and\n// comments! Check the usage of Category carefully to figure out what needs changing\n// if you're going to change this array's order.\nconst CATEGORY_ORDER = [\n    NotificationLevel.Unsent,\n    NotificationLevel.Highlight,\n    NotificationLevel.Notification,\n    NotificationLevel.Activity,\n    NotificationLevel.None, // idle\n    NotificationLevel.Muted,\n];\n\n/**\n * An implementation of the \"importance\" algorithm for room list sorting. Where\n * the tag sorting algorithm does not interfere, rooms will be ordered into\n * categories of varying importance to the user. Alphabetical sorting does not\n * interfere with this algorithm, however manual ordering does.\n *\n * The importance of a room is defined by the kind of notifications, if any, are\n * present on the room. These are classified internally as Unsent, Red, Grey,\n * Bold, and Idle. 'Unsent' rooms have unsent messages, Red rooms have mentions,\n * grey have unread messages, bold is a less noisy version of grey, and idle\n * means all activity has been seen by the user.\n *\n * The algorithm works by monitoring all room changes, including new messages in\n * tracked rooms, to determine if it needs a new category or different placement\n * within the same category. For more information, see the comments contained\n * within the class.\n */\nexport class ImportanceAlgorithm extends OrderingAlgorithm {\n    // This tracks the category for the tag it represents by tracking the index of\n    // each category within the list, where zero is the top of the list. This then\n    // tracks when rooms change categories and splices the orderedRooms array as\n    // needed, preventing many ordering operations.\n\n    private indices: CategoryIndex = {};\n\n    public constructor(tagId: TagID, initialSortingAlgorithm: SortAlgorithm) {\n        super(tagId, initialSortingAlgorithm);\n    }\n\n    // noinspection JSMethodCanBeStatic\n    private categorizeRooms(rooms: Room[]): CategorizedRoomMap {\n        const map: CategorizedRoomMap = {\n            [NotificationLevel.Unsent]: [],\n            [NotificationLevel.Highlight]: [],\n            [NotificationLevel.Notification]: [],\n            [NotificationLevel.Activity]: [],\n            [NotificationLevel.None]: [],\n            [NotificationLevel.Muted]: [],\n        };\n        for (const room of rooms) {\n            const category = this.getRoomCategory(room);\n            map[category]?.push(room);\n        }\n        return map;\n    }\n\n    // noinspection JSMethodCanBeStatic\n    private getRoomCategory(room: Room): NotificationLevel {\n        // It's fine for us to call this a lot because it's cached, and we shouldn't be\n        // wasting anything by doing so as the store holds single references\n        const state = RoomNotificationStateStore.instance.getRoomState(room);\n        return this.isMutedToBottom && state.muted ? NotificationLevel.Muted : state.level;\n    }\n\n    public setRooms(rooms: Room[]): void {\n        if (this.sortingAlgorithm === SortAlgorithm.Manual) {\n            this.cachedOrderedRooms = sortRoomsWithAlgorithm(rooms, this.tagId, this.sortingAlgorithm);\n        } else {\n            // Every other sorting type affects the categories, not the whole tag.\n            const categorized = this.categorizeRooms(rooms);\n            for (const category of Object.keys(categorized)) {\n                const notificationColor = category as unknown as NotificationLevel;\n                const roomsToOrder = categorized[notificationColor];\n                categorized[notificationColor] = sortRoomsWithAlgorithm(\n                    roomsToOrder,\n                    this.tagId,\n                    this.sortingAlgorithm,\n                );\n            }\n\n            const newlyOrganized: Room[] = [];\n            const newIndices: CategoryIndex = {};\n\n            for (const category of CATEGORY_ORDER) {\n                newIndices[category] = newlyOrganized.length;\n                newlyOrganized.push(...categorized[category]);\n            }\n\n            this.indices = newIndices;\n            this.cachedOrderedRooms = newlyOrganized;\n        }\n    }\n\n    private getCategoryIndex(category: NotificationLevel): number {\n        const categoryIndex = this.indices[category];\n\n        if (categoryIndex === undefined) {\n            throw new Error(`Index of category ${category} not found`);\n        }\n\n        return categoryIndex;\n    }\n\n    private handleSplice(room: Room, cause: RoomUpdateCause): boolean {\n        if (cause === RoomUpdateCause.NewRoom) {\n            const category = this.getRoomCategory(room);\n            this.alterCategoryPositionBy(category, 1, this.indices);\n            this.cachedOrderedRooms.splice(this.getCategoryIndex(category), 0, room); // splice in the new room (pre-adjusted)\n            this.sortCategory(category);\n        } else if (cause === RoomUpdateCause.RoomRemoved) {\n            const roomIdx = this.getRoomIndex(room);\n            if (roomIdx === -1) {\n                logger.warn(`Tried to remove unknown room from ${this.tagId}: ${room.roomId}`);\n                return false; // no change\n            }\n            const oldCategory = this.getCategoryFromIndices(roomIdx, this.indices);\n            this.alterCategoryPositionBy(oldCategory, -1, this.indices);\n            this.cachedOrderedRooms.splice(roomIdx, 1); // remove the room\n        } else {\n            throw new Error(`Unhandled splice: ${cause}`);\n        }\n\n        // changes have been made if we made it here, so say so\n        return true;\n    }\n\n    public handleRoomUpdate(room: Room, cause: RoomUpdateCause): boolean {\n        if (cause === RoomUpdateCause.NewRoom || cause === RoomUpdateCause.RoomRemoved) {\n            return this.handleSplice(room, cause);\n        }\n\n        if (\n            cause !== RoomUpdateCause.Timeline &&\n            cause !== RoomUpdateCause.ReadReceipt &&\n            cause !== RoomUpdateCause.PossibleMuteChange\n        ) {\n            throw new Error(`Unsupported update cause: ${cause}`);\n        }\n\n        // don't react to mute changes when we are not sorting by mute\n        if (cause === RoomUpdateCause.PossibleMuteChange && !this.isMutedToBottom) {\n            return false;\n        }\n\n        if (this.sortingAlgorithm === SortAlgorithm.Manual) {\n            return false; // Nothing to do here.\n        }\n\n        const category = this.getRoomCategory(room);\n\n        const roomIdx = this.getRoomIndex(room);\n        if (roomIdx === -1) {\n            throw new Error(`Room ${room.roomId} has no index in ${this.tagId}`);\n        }\n\n        // Try to avoid doing array operations if we don't have to: only move rooms within\n        // the categories if we're jumping categories\n        const oldCategory = this.getCategoryFromIndices(roomIdx, this.indices);\n        if (oldCategory !== category) {\n            // Move the room and update the indices\n            this.moveRoomIndexes(1, oldCategory, category, this.indices);\n            this.cachedOrderedRooms.splice(roomIdx, 1); // splice out the old index (fixed position)\n            this.cachedOrderedRooms.splice(this.getCategoryIndex(category), 0, room); // splice in the new room (pre-adjusted)\n            // Note: if moveRoomIndexes() is called after the splice then the insert operation\n            // will happen in the wrong place. Because we would have already adjusted the index\n            // for the category, we don't need to determine how the room is moving in the list.\n            // If we instead tried to insert before updating the indices, we'd have to determine\n            // whether the room was moving later (towards IDLE) or earlier (towards RED) from its\n            // current position, as it'll affect the category's start index after we remove the\n            // room from the array.\n        }\n\n        // Sort the category now that we've dumped the room in\n        this.sortCategory(category);\n\n        return true; // change made\n    }\n\n    private sortCategory(category: NotificationLevel): void {\n        // This should be relatively quick because the room is usually inserted at the top of the\n        // category, and most popular sorting algorithms will deal with trying to keep the active\n        // room at the top/start of the category. For the few algorithms that will have to move the\n        // thing quite far (alphabetic with a Z room for example), the list should already be sorted\n        // well enough that it can rip through the array and slot the changed room in quickly.\n        const nextCategoryStartIdx =\n            category === CATEGORY_ORDER[CATEGORY_ORDER.length - 1]\n                ? Number.MAX_SAFE_INTEGER\n                : this.getCategoryIndex(CATEGORY_ORDER[CATEGORY_ORDER.indexOf(category) + 1]);\n        const startIdx = this.getCategoryIndex(category);\n        const numSort = nextCategoryStartIdx - startIdx; // splice() returns up to the max, so MAX_SAFE_INT is fine\n        const unsortedSlice = this.cachedOrderedRooms.splice(startIdx, numSort);\n        const sorted = sortRoomsWithAlgorithm(unsortedSlice, this.tagId, this.sortingAlgorithm);\n        this.cachedOrderedRooms.splice(startIdx, 0, ...sorted);\n    }\n\n    // noinspection JSMethodCanBeStatic\n    private getCategoryFromIndices(index: number, indices: CategoryIndex): NotificationLevel {\n        for (let i = 0; i < CATEGORY_ORDER.length; i++) {\n            const category = CATEGORY_ORDER[i];\n            const isLast = i === CATEGORY_ORDER.length - 1;\n            const startIdx = indices[category];\n            const endIdx = isLast ? Number.MAX_SAFE_INTEGER : indices[CATEGORY_ORDER[i + 1]];\n\n            if (startIdx === undefined || endIdx === undefined) continue;\n\n            if (index >= startIdx && index < endIdx) {\n                return category;\n            }\n        }\n\n        // \"Should never happen\" disclaimer goes here\n        throw new Error(\"Programming error: somehow you've ended up with an index that isn't in a category\");\n    }\n\n    // noinspection JSMethodCanBeStatic\n    private moveRoomIndexes(\n        nRooms: number,\n        fromCategory: NotificationLevel,\n        toCategory: NotificationLevel,\n        indices: CategoryIndex,\n    ): void {\n        // We have to update the index of the category *after* the from/toCategory variables\n        // in order to update the indices correctly. Because the room is moving from/to those\n        // categories, the next category's index will change - not the category we're modifying.\n        // We also need to update subsequent categories as they'll all shift by nRooms, so we\n        // loop over the order to achieve that.\n\n        this.alterCategoryPositionBy(fromCategory, -nRooms, indices);\n        this.alterCategoryPositionBy(toCategory, +nRooms, indices);\n    }\n\n    private alterCategoryPositionBy(category: NotificationLevel, n: number, indices: CategoryIndex): void {\n        // Note: when we alter a category's index, we actually have to modify the ones following\n        // the target and not the target itself.\n\n        // XXX: If this ever actually gets more than one room passed to it, it'll need more index\n        // handling. For instance, if 45 rooms are removed from the middle of a 50 room list, the\n        // index for the categories will be way off.\n\n        const nextOrderIndex = CATEGORY_ORDER.indexOf(category) + 1;\n\n        if (n > 0) {\n            for (let i = nextOrderIndex; i < CATEGORY_ORDER.length; i++) {\n                const nextCategory = CATEGORY_ORDER[i];\n\n                if (indices[nextCategory] === undefined) {\n                    throw new Error(`Index of category ${category} not found`);\n                }\n\n                indices[nextCategory]! += Math.abs(n);\n            }\n        } else if (n < 0) {\n            for (let i = nextOrderIndex; i < CATEGORY_ORDER.length; i++) {\n                const nextCategory = CATEGORY_ORDER[i];\n\n                if (indices[nextCategory] === undefined) {\n                    throw new Error(`Index of category ${category} not found`);\n                }\n\n                indices[nextCategory]! -= Math.abs(n);\n            }\n        }\n\n        // Do a quick check to see if we've completely broken the index\n        for (let i = 1; i < CATEGORY_ORDER.length; i++) {\n            const lastCat = CATEGORY_ORDER[i - 1];\n            const lastCatIndex = indices[lastCat];\n            const thisCat = CATEGORY_ORDER[i];\n            const thisCatIndex = indices[thisCat];\n\n            if (lastCatIndex === undefined || thisCatIndex === undefined || lastCatIndex > thisCatIndex) {\n                // \"should never happen\" disclaimer goes here\n                logger.warn(\n                    `!! Room list index corruption: ${lastCat} (i:${indices[lastCat]}) is greater ` +\n                        `than ${thisCat} (i:${indices[thisCat]}) - category indices are likely desynced from reality`,\n                );\n\n                // TODO: Regenerate index when this happens: https://github.com/vector-im/element-web/issues/14234\n            }\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { type SortAlgorithm } from \"../models\";\nimport { sortRoomsWithAlgorithm } from \"../tag-sorting\";\nimport { OrderingAlgorithm } from \"./OrderingAlgorithm\";\nimport { RoomUpdateCause, type TagID } from \"../../models\";\nimport { RoomNotificationStateStore } from \"../../../notifications/RoomNotificationStateStore\";\n\ntype NaturalCategorizedRoomMap = {\n    defaultRooms: Room[];\n    mutedRooms: Room[];\n};\n\n/**\n * Uses the natural tag sorting algorithm order to determine tag ordering. No\n * additional behavioural changes are present.\n */\nexport class NaturalAlgorithm extends OrderingAlgorithm {\n    private cachedCategorizedOrderedRooms: NaturalCategorizedRoomMap = {\n        defaultRooms: [],\n        mutedRooms: [],\n    };\n    public constructor(tagId: TagID, initialSortingAlgorithm: SortAlgorithm) {\n        super(tagId, initialSortingAlgorithm);\n    }\n\n    public setRooms(rooms: Room[]): void {\n        const { defaultRooms, mutedRooms } = this.categorizeRooms(rooms);\n\n        this.cachedCategorizedOrderedRooms = {\n            defaultRooms: sortRoomsWithAlgorithm(defaultRooms, this.tagId, this.sortingAlgorithm),\n            mutedRooms: sortRoomsWithAlgorithm(mutedRooms, this.tagId, this.sortingAlgorithm),\n        };\n        this.buildCachedOrderedRooms();\n    }\n\n    public handleRoomUpdate(room: Room, cause: RoomUpdateCause): boolean {\n        const isSplice = cause === RoomUpdateCause.NewRoom || cause === RoomUpdateCause.RoomRemoved;\n        const isInPlace =\n            cause === RoomUpdateCause.Timeline ||\n            cause === RoomUpdateCause.ReadReceipt ||\n            cause === RoomUpdateCause.PossibleMuteChange;\n        const isMuted = this.isMutedToBottom && this.getRoomIsMuted(room);\n\n        if (!isSplice && !isInPlace) {\n            throw new Error(`Unsupported update cause: ${cause}`);\n        }\n\n        if (cause === RoomUpdateCause.NewRoom) {\n            if (isMuted) {\n                this.cachedCategorizedOrderedRooms.mutedRooms = sortRoomsWithAlgorithm(\n                    [...this.cachedCategorizedOrderedRooms.mutedRooms, room],\n                    this.tagId,\n                    this.sortingAlgorithm,\n                );\n            } else {\n                this.cachedCategorizedOrderedRooms.defaultRooms = sortRoomsWithAlgorithm(\n                    [...this.cachedCategorizedOrderedRooms.defaultRooms, room],\n                    this.tagId,\n                    this.sortingAlgorithm,\n                );\n            }\n            this.buildCachedOrderedRooms();\n            return true;\n        } else if (cause === RoomUpdateCause.RoomRemoved) {\n            return this.removeRoom(room);\n        } else if (cause === RoomUpdateCause.PossibleMuteChange) {\n            if (this.isMutedToBottom) {\n                return this.onPossibleMuteChange(room);\n            } else {\n                return false;\n            }\n        }\n\n        // TODO: Optimize this to avoid useless operations: https://github.com/vector-im/element-web/issues/14457\n        // For example, we can skip updates to alphabetic (sometimes) and manually ordered tags\n        if (isMuted) {\n            this.cachedCategorizedOrderedRooms.mutedRooms = sortRoomsWithAlgorithm(\n                this.cachedCategorizedOrderedRooms.mutedRooms,\n                this.tagId,\n                this.sortingAlgorithm,\n            );\n        } else {\n            this.cachedCategorizedOrderedRooms.defaultRooms = sortRoomsWithAlgorithm(\n                this.cachedCategorizedOrderedRooms.defaultRooms,\n                this.tagId,\n                this.sortingAlgorithm,\n            );\n        }\n        this.buildCachedOrderedRooms();\n        return true;\n    }\n\n    /**\n     * Remove a room from the cached room list\n     * @param room Room to remove\n     * @returns {boolean} true when room list should update as result\n     */\n    private removeRoom(room: Room): boolean {\n        const defaultIndex = this.cachedCategorizedOrderedRooms.defaultRooms.findIndex((r) => r.roomId === room.roomId);\n        if (defaultIndex > -1) {\n            this.cachedCategorizedOrderedRooms.defaultRooms.splice(defaultIndex, 1);\n            this.buildCachedOrderedRooms();\n            return true;\n        }\n        const mutedIndex = this.cachedCategorizedOrderedRooms.mutedRooms.findIndex((r) => r.roomId === room.roomId);\n        if (mutedIndex > -1) {\n            this.cachedCategorizedOrderedRooms.mutedRooms.splice(mutedIndex, 1);\n            this.buildCachedOrderedRooms();\n            return true;\n        }\n\n        logger.warn(`Tried to remove unknown room from ${this.tagId}: ${room.roomId}`);\n        // room was not in cached lists, no update\n        return false;\n    }\n\n    /**\n     * Sets cachedOrderedRooms from cachedCategorizedOrderedRooms\n     */\n    private buildCachedOrderedRooms(): void {\n        this.cachedOrderedRooms = [\n            ...this.cachedCategorizedOrderedRooms.defaultRooms,\n            ...this.cachedCategorizedOrderedRooms.mutedRooms,\n        ];\n    }\n\n    private getRoomIsMuted(room: Room): boolean {\n        // It's fine for us to call this a lot because it's cached, and we shouldn't be\n        // wasting anything by doing so as the store holds single references\n        const state = RoomNotificationStateStore.instance.getRoomState(room);\n        return state.muted;\n    }\n\n    private categorizeRooms(rooms: Room[]): NaturalCategorizedRoomMap {\n        if (!this.isMutedToBottom) {\n            return { defaultRooms: rooms, mutedRooms: [] };\n        }\n        return rooms.reduce<NaturalCategorizedRoomMap>(\n            (acc, room: Room) => {\n                if (this.getRoomIsMuted(room)) {\n                    acc.mutedRooms.push(room);\n                } else {\n                    acc.defaultRooms.push(room);\n                }\n                return acc;\n            },\n            { defaultRooms: [], mutedRooms: [] } as NaturalCategorizedRoomMap,\n        );\n    }\n\n    private onPossibleMuteChange(room: Room): boolean {\n        const isMuted = this.getRoomIsMuted(room);\n        if (isMuted) {\n            const defaultIndex = this.cachedCategorizedOrderedRooms.defaultRooms.findIndex(\n                (r) => r.roomId === room.roomId,\n            );\n\n            // room has been muted\n            if (defaultIndex > -1) {\n                // remove from the default list\n                this.cachedCategorizedOrderedRooms.defaultRooms.splice(defaultIndex, 1);\n                // add to muted list and reorder\n                this.cachedCategorizedOrderedRooms.mutedRooms = sortRoomsWithAlgorithm(\n                    [...this.cachedCategorizedOrderedRooms.mutedRooms, room],\n                    this.tagId,\n                    this.sortingAlgorithm,\n                );\n                // rebuild\n                this.buildCachedOrderedRooms();\n                return true;\n            }\n        } else {\n            const mutedIndex = this.cachedCategorizedOrderedRooms.mutedRooms.findIndex((r) => r.roomId === room.roomId);\n\n            // room has been unmuted\n            if (mutedIndex > -1) {\n                // remove from the muted list\n                this.cachedCategorizedOrderedRooms.mutedRooms.splice(mutedIndex, 1);\n                // add to default list and reorder\n                this.cachedCategorizedOrderedRooms.defaultRooms = sortRoomsWithAlgorithm(\n                    [...this.cachedCategorizedOrderedRooms.defaultRooms, room],\n                    this.tagId,\n                    this.sortingAlgorithm,\n                );\n                // rebuild\n                this.buildCachedOrderedRooms();\n                return true;\n            }\n        }\n\n        return false;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { ImportanceAlgorithm } from \"./ImportanceAlgorithm\";\nimport { ListAlgorithm, type SortAlgorithm } from \"../models\";\nimport { NaturalAlgorithm } from \"./NaturalAlgorithm\";\nimport { type TagID } from \"../../models\";\nimport { type OrderingAlgorithm } from \"./OrderingAlgorithm\";\n\ninterface AlgorithmFactory {\n    (tagId: TagID, initialSortingAlgorithm: SortAlgorithm): OrderingAlgorithm;\n}\n\nconst ALGORITHM_FACTORIES: { [algorithm in ListAlgorithm]: AlgorithmFactory } = {\n    [ListAlgorithm.Natural]: (tagId, initSort) => new NaturalAlgorithm(tagId, initSort),\n    [ListAlgorithm.Importance]: (tagId, initSort) => new ImportanceAlgorithm(tagId, initSort),\n};\n\n/**\n * Gets an instance of the defined algorithm\n * @param {ListAlgorithm} algorithm The algorithm to get an instance of.\n * @param {TagID} tagId The tag the algorithm is for.\n * @param {SortAlgorithm} initSort The initial sorting algorithm for the ordering algorithm.\n * @returns {Algorithm} The algorithm instance.\n */\nexport function getListAlgorithmInstance(\n    algorithm: ListAlgorithm,\n    tagId: TagID,\n    initSort: SortAlgorithm,\n): OrderingAlgorithm {\n    if (!ALGORITHM_FACTORIES[algorithm]) {\n        throw new Error(`${algorithm} is not a known algorithm`);\n    }\n\n    return ALGORITHM_FACTORIES[algorithm](tagId, initSort);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { JoinRule, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { isNullOrUndefined } from \"matrix-js-sdk/src/utils\";\nimport { EventEmitter } from \"events\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport DMRoomMap from \"../../../utils/DMRoomMap\";\nimport { arrayDiff, arrayHasDiff } from \"../../../utils/arrays\";\nimport { DefaultTagID, RoomUpdateCause, type TagID } from \"../models\";\nimport {\n    type IListOrderingMap,\n    type IOrderingAlgorithmMap,\n    type ITagMap,\n    type ITagSortingMap,\n    type ListAlgorithm,\n    type SortAlgorithm,\n} from \"./models\";\nimport {\n    EffectiveMembership,\n    getEffectiveMembership,\n    getEffectiveMembershipTag,\n    splitRoomsByMembership,\n} from \"../../../utils/membership\";\nimport { type OrderingAlgorithm } from \"./list-ordering/OrderingAlgorithm\";\nimport { getListAlgorithmInstance } from \"./list-ordering\";\nimport { VisibilityProvider } from \"../filters/VisibilityProvider\";\nimport { CallStore, CallStoreEvent } from \"../../CallStore\";\n\n/**\n * Fired when the Algorithm has determined a list has been updated.\n */\nexport const LIST_UPDATED_EVENT = \"list_updated_event\";\n\n// These are the causes which require a room to be known in order for us to handle them. If\n// a cause in this list is raised and we don't know about the room, we don't handle the update.\n//\n// Note: these typically happen when a new room is coming in, such as the user creating or\n// joining the room. For these cases, we need to know about the room prior to handling it otherwise\n// we'll make bad assumptions.\nconst CAUSES_REQUIRING_ROOM = [RoomUpdateCause.Timeline, RoomUpdateCause.ReadReceipt];\n\ninterface IStickyRoom {\n    room: Room;\n    position: number;\n    tag: TagID;\n}\n\n/**\n * Represents a list ordering algorithm. This class will take care of tag\n * management (which rooms go in which tags) and ask the implementation to\n * deal with ordering mechanics.\n */\nexport class Algorithm extends EventEmitter {\n    private _cachedRooms: ITagMap = {};\n    private _cachedStickyRooms: ITagMap | null = {}; // a clone of the _cachedRooms, with the sticky room\n    private _stickyRoom: IStickyRoom | null = null;\n    private _lastStickyRoom: IStickyRoom | null = null; // only not-null when changing the sticky room\n    private sortAlgorithms: ITagSortingMap | null = null;\n    private listAlgorithms: IListOrderingMap | null = null;\n    private algorithms: IOrderingAlgorithmMap | null = null;\n    private rooms: Room[] = [];\n    private roomIdsToTags: {\n        [roomId: string]: TagID[];\n    } = {};\n\n    /**\n     * Set to true to suspend emissions of algorithm updates.\n     */\n    public updatesInhibited = false;\n\n    public start(): void {\n        CallStore.instance.on(CallStoreEvent.ConnectedCalls, this.onConnectedCalls);\n    }\n\n    public stop(): void {\n        CallStore.instance.off(CallStoreEvent.ConnectedCalls, this.onConnectedCalls);\n    }\n\n    public get stickyRoom(): Room | null {\n        return this._stickyRoom ? this._stickyRoom.room : null;\n    }\n\n    public get hasTagSortingMap(): boolean {\n        return !!this.sortAlgorithms;\n    }\n\n    protected set cachedRooms(val: ITagMap) {\n        this._cachedRooms = val;\n        this.recalculateStickyRoom();\n        this.recalculateActiveCallRooms();\n    }\n\n    protected get cachedRooms(): ITagMap {\n        // 🐉 Here be dragons.\n        // Note: this is used by the underlying algorithm classes, so don't make it return\n        // the sticky room cache. If it ends up returning the sticky room cache, we end up\n        // corrupting our caches and confusing them.\n        return this._cachedRooms;\n    }\n\n    /**\n     * Awaitable version of the sticky room setter.\n     * @param val The new room to sticky.\n     */\n    public setStickyRoom(val: Room | null): void {\n        try {\n            this.updateStickyRoom(val);\n        } catch (e) {\n            logger.warn(\"Failed to update sticky room\", e);\n        }\n    }\n\n    public getTagSorting(tagId: TagID): SortAlgorithm | null {\n        if (!this.sortAlgorithms) return null;\n        return this.sortAlgorithms[tagId];\n    }\n\n    public setTagSorting(tagId: TagID, sort: SortAlgorithm): void {\n        if (!tagId) throw new Error(\"Tag ID must be defined\");\n        if (!sort) throw new Error(\"Algorithm must be defined\");\n        if (!this.sortAlgorithms) throw new Error(\"this.sortAlgorithms must be defined before calling setTagSorting\");\n        if (!this.algorithms) throw new Error(\"this.algorithms must be defined before calling setTagSorting\");\n        this.sortAlgorithms[tagId] = sort;\n\n        const algorithm: OrderingAlgorithm = this.algorithms[tagId];\n        algorithm.setSortAlgorithm(sort);\n        this._cachedRooms[tagId] = algorithm.orderedRooms;\n        this.recalculateStickyRoom(tagId); // update sticky room to make sure it appears if needed\n        this.recalculateActiveCallRooms(tagId);\n    }\n\n    public getListOrdering(tagId: TagID): ListAlgorithm | null {\n        if (!this.listAlgorithms) return null;\n        return this.listAlgorithms[tagId];\n    }\n\n    public setListOrdering(tagId: TagID, order: ListAlgorithm): void {\n        if (!tagId) throw new Error(\"Tag ID must be defined\");\n        if (!order) throw new Error(\"Algorithm must be defined\");\n        if (!this.sortAlgorithms) throw new Error(\"this.sortAlgorithms must be defined before calling setListOrdering\");\n        if (!this.listAlgorithms) throw new Error(\"this.listAlgorithms must be defined before calling setListOrdering\");\n        if (!this.algorithms) throw new Error(\"this.algorithms must be defined before calling setListOrdering\");\n        this.listAlgorithms[tagId] = order;\n\n        const algorithm = getListAlgorithmInstance(order, tagId, this.sortAlgorithms[tagId]);\n        this.algorithms[tagId] = algorithm;\n\n        algorithm.setRooms(this._cachedRooms[tagId]);\n        this._cachedRooms[tagId] = algorithm.orderedRooms;\n        this.recalculateStickyRoom(tagId); // update sticky room to make sure it appears if needed\n        this.recalculateActiveCallRooms(tagId);\n    }\n\n    private updateStickyRoom(val: Room | null): void {\n        this.doUpdateStickyRoom(val);\n        this._lastStickyRoom = null; // clear to indicate we're done changing\n    }\n\n    private doUpdateStickyRoom(val: Room | null): void {\n        if (val?.isSpaceRoom() && val.getMyMembership() !== KnownMembership.Invite) {\n            // no-op sticky rooms for spaces - they're effectively virtual rooms\n            val = null;\n        }\n\n        if (val && !VisibilityProvider.instance.isRoomVisible(val)) {\n            val = null; // the room isn't visible - lie to the rest of this function\n        }\n\n        // Set the last sticky room to indicate that we're in a change. The code throughout the\n        // class can safely handle a null room, so this should be safe to do as a backup.\n        this._lastStickyRoom = this._stickyRoom || <IStickyRoom>{};\n\n        // It's possible to have no selected room. In that case, clear the sticky room\n        if (!val) {\n            if (this._stickyRoom) {\n                const stickyRoom = this._stickyRoom.room;\n                this._stickyRoom = null; // clear before we go to update the algorithm\n\n                // Lie to the algorithm and re-add the room to the algorithm\n                this.handleRoomUpdate(stickyRoom, RoomUpdateCause.NewRoom);\n                return;\n            }\n            return;\n        }\n\n        // When we do have a room though, we expect to be able to find it\n        let tag = this.roomIdsToTags[val.roomId]?.[0];\n        if (!tag) throw new Error(`${val.roomId} does not belong to a tag and cannot be sticky`);\n\n        // We specifically do NOT use the ordered rooms set as it contains the sticky room, which\n        // means we'll be off by 1 when the user is switching rooms. This leads to visual jumping\n        // when the user is moving south in the list (not north, because of math).\n        const tagList = this.getOrderedRoomsWithoutSticky()[tag] || []; // can be null if filtering\n        let position = tagList.indexOf(val);\n\n        // We do want to see if a tag change happened though - if this did happen then we'll want\n        // to force the position to zero (top) to ensure we can properly handle it.\n        const wasSticky = this._lastStickyRoom.room ? this._lastStickyRoom.room.roomId === val.roomId : false;\n        if (this._lastStickyRoom.tag && tag !== this._lastStickyRoom.tag && wasSticky && position < 0) {\n            logger.warn(`Sticky room ${val.roomId} changed tags during sticky room handling`);\n            position = 0;\n        }\n\n        // Sanity check the position to make sure the room is qualified for being sticky\n        if (position < 0) throw new Error(`${val.roomId} does not appear to be known and cannot be sticky`);\n\n        // 🐉 Here be dragons.\n        // Before we can go through with lying to the underlying algorithm about a room\n        // we need to ensure that when we do we're ready for the inevitable sticky room\n        // update we'll receive. To prepare for that, we first remove the sticky room and\n        // recalculate the state ourselves so that when the underlying algorithm calls for\n        // the same thing it no-ops. After we're done calling the algorithm, we'll issue\n        // a new update for ourselves.\n        const lastStickyRoom = this._stickyRoom;\n        this._stickyRoom = null; // clear before we update the algorithm\n        this.recalculateStickyRoom();\n\n        // When we do have the room, re-add the old room (if needed) to the algorithm\n        // and remove the sticky room from the algorithm. This is so the underlying\n        // algorithm doesn't try and confuse itself with the sticky room concept.\n        // We don't add the new room if the sticky room isn't changing because that's\n        // an easy way to cause duplication. We have to do room ID checks instead of\n        // referential checks as the references can differ through the lifecycle.\n        if (lastStickyRoom && lastStickyRoom.room && lastStickyRoom.room.roomId !== val.roomId) {\n            // Lie to the algorithm and re-add the room to the algorithm\n            this.handleRoomUpdate(lastStickyRoom.room, RoomUpdateCause.NewRoom);\n        }\n        // Lie to the algorithm and remove the room from it's field of view\n        this.handleRoomUpdate(val, RoomUpdateCause.RoomRemoved);\n\n        // handleRoomUpdate may have modified this._stickyRoom. Convince the\n        // compiler of this fact.\n        this._stickyRoom = this.stickyRoomMightBeModified();\n\n        // Check for tag & position changes while we're here. We also check the room to ensure\n        // it is still the same room.\n        if (this._stickyRoom) {\n            if (this._stickyRoom.room !== val) {\n                // Check the room IDs just in case\n                if (this._stickyRoom.room.roomId === val.roomId) {\n                    logger.warn(\"Sticky room changed references\");\n                } else {\n                    throw new Error(\"Sticky room changed while the sticky room was changing\");\n                }\n            }\n\n            logger.warn(\n                `Sticky room changed tag & position from ${tag} / ${position} ` +\n                    `to ${this._stickyRoom.tag} / ${this._stickyRoom.position}`,\n            );\n\n            tag = this._stickyRoom.tag;\n            position = this._stickyRoom.position;\n        }\n\n        // Now that we're done lying to the algorithm, we need to update our position\n        // marker only if the user is moving further down the same list. If they're switching\n        // lists, or moving upwards, the position marker will splice in just fine but if\n        // they went downwards in the same list we'll be off by 1 due to the shifting rooms.\n        if (lastStickyRoom && lastStickyRoom.tag === tag && lastStickyRoom.position <= position) {\n            position++;\n        }\n\n        this._stickyRoom = {\n            room: val,\n            position: position,\n            tag: tag,\n        };\n\n        // We update the filtered rooms just in case, as otherwise users will end up visiting\n        // a room while filtering and it'll disappear. We don't update the filter earlier in\n        // this function simply because we don't have to.\n        this.recalculateStickyRoom();\n        this.recalculateActiveCallRooms(tag);\n        if (lastStickyRoom && lastStickyRoom.tag !== tag) this.recalculateActiveCallRooms(lastStickyRoom.tag);\n\n        // Finally, trigger an update\n        if (this.updatesInhibited) return;\n        this.emit(LIST_UPDATED_EVENT);\n    }\n\n    /**\n     * Hack to prevent Typescript claiming this._stickyRoom is always null.\n     */\n    private stickyRoomMightBeModified(): IStickyRoom | null {\n        return this._stickyRoom;\n    }\n\n    private onConnectedCalls = (): void => {\n        // In case we're unsticking a room, sort it back into natural order\n        this.recalculateStickyRoom();\n\n        // Update the stickiness of rooms with calls\n        this.recalculateActiveCallRooms();\n\n        if (this.updatesInhibited) return;\n        // This isn't in response to any particular RoomListStore update,\n        // so notify the store that it needs to force-update\n        this.emit(LIST_UPDATED_EVENT, true);\n    };\n\n    private initCachedStickyRooms(): void {\n        this._cachedStickyRooms = {};\n        for (const tagId of Object.keys(this.cachedRooms)) {\n            this._cachedStickyRooms[tagId] = [...this.cachedRooms[tagId]]; // shallow clone\n        }\n    }\n\n    /**\n     * Recalculate the sticky room position. If this is being called in relation to\n     * a specific tag being updated, it should be given to this function to optimize\n     * the call.\n     * @param updatedTag The tag that was updated, if possible.\n     */\n    protected recalculateStickyRoom(updatedTag: TagID | null = null): void {\n        // 🐉 Here be dragons.\n        // This function does far too much for what it should, and is called by many places.\n        // Not only is this responsible for ensuring the sticky room is held in place at all\n        // times, it is also responsible for ensuring our clone of the cachedRooms is up to\n        // date. If either of these desyncs, we see weird behaviour like duplicated rooms,\n        // outdated lists, and other nonsensical issues that aren't necessarily obvious.\n\n        if (!this._stickyRoom) {\n            // If there's no sticky room, just do nothing useful.\n            if (!!this._cachedStickyRooms) {\n                // Clear the cache if we won't be needing it\n                this._cachedStickyRooms = null;\n                if (this.updatesInhibited) return;\n                this.emit(LIST_UPDATED_EVENT);\n            }\n            return;\n        }\n\n        if (!this._cachedStickyRooms || !updatedTag) {\n            this.initCachedStickyRooms();\n        }\n\n        if (updatedTag) {\n            // Update the tag indicated by the caller, if possible. This is mostly to ensure\n            // our cache is up to date.\n            if (this._cachedStickyRooms) {\n                this._cachedStickyRooms[updatedTag] = [...this.cachedRooms[updatedTag]]; // shallow clone\n            }\n        }\n\n        // Now try to insert the sticky room, if we need to.\n        // We need to if there's no updated tag (we regenned the whole cache) or if the tag\n        // we might have updated from the cache is also our sticky room.\n        const sticky = this._stickyRoom;\n        if (sticky && (!updatedTag || updatedTag === sticky.tag) && this._cachedStickyRooms) {\n            this._cachedStickyRooms[sticky.tag].splice(sticky.position, 0, sticky.room);\n        }\n\n        // Finally, trigger an update\n        if (this.updatesInhibited) return;\n        this.emit(LIST_UPDATED_EVENT);\n    }\n\n    /**\n     * Recalculate the position of any rooms with calls. If this is being called in\n     * relation to a specific tag being updated, it should be given to this function to\n     * optimize the call.\n     *\n     * This expects to be called *after* the sticky rooms are updated, and sticks the\n     * room with the currently active call to the top of its tag.\n     *\n     * @param updatedTag The tag that was updated, if possible.\n     */\n    protected recalculateActiveCallRooms(updatedTag: TagID | null = null): void {\n        if (!updatedTag) {\n            // Assume all tags need updating\n            // We're not modifying the map here, so can safely rely on the cached values\n            // rather than the explicitly sticky map.\n            for (const tagId of Object.keys(this.cachedRooms)) {\n                if (!tagId) {\n                    throw new Error(\"Unexpected recursion: falsy tag\");\n                }\n                this.recalculateActiveCallRooms(tagId);\n            }\n            return;\n        }\n\n        if (CallStore.instance.connectedCalls.size) {\n            // We operate on the sticky rooms map\n            if (!this._cachedStickyRooms) this.initCachedStickyRooms();\n            const rooms = this._cachedStickyRooms![updatedTag];\n\n            const activeRoomIds = new Set([...CallStore.instance.connectedCalls].map((call) => call.roomId));\n            const activeRooms: Room[] = [];\n            const inactiveRooms: Room[] = [];\n\n            for (const room of rooms) {\n                (activeRoomIds.has(room.roomId) ? activeRooms : inactiveRooms).push(room);\n            }\n\n            // Stick rooms with active calls to the top\n            this._cachedStickyRooms![updatedTag] = [...activeRooms, ...inactiveRooms];\n        }\n    }\n\n    /**\n     * Asks the Algorithm to regenerate all lists, using the tags given\n     * as reference for which lists to generate and which way to generate\n     * them.\n     * @param {ITagSortingMap} tagSortingMap The tags to generate.\n     * @param {IListOrderingMap} listOrderingMap The ordering of those tags.\n     */\n    public populateTags(tagSortingMap: ITagSortingMap, listOrderingMap: IListOrderingMap): void {\n        if (!tagSortingMap) throw new Error(`Sorting map cannot be null or empty`);\n        if (!listOrderingMap) throw new Error(`Ordering ma cannot be null or empty`);\n        if (arrayHasDiff(Object.keys(tagSortingMap), Object.keys(listOrderingMap))) {\n            throw new Error(`Both maps must contain the exact same tags`);\n        }\n        this.sortAlgorithms = tagSortingMap;\n        this.listAlgorithms = listOrderingMap;\n        this.algorithms = {};\n        for (const tag of Object.keys(tagSortingMap)) {\n            this.algorithms[tag] = getListAlgorithmInstance(this.listAlgorithms[tag], tag, this.sortAlgorithms[tag]);\n        }\n        return this.setKnownRooms(this.rooms);\n    }\n\n    /**\n     * Gets an ordered set of rooms for the all known tags.\n     * @returns {ITagMap} The cached list of rooms, ordered,\n     * for each tag. May be empty, but never null/undefined.\n     */\n    public getOrderedRooms(): ITagMap {\n        return this._cachedStickyRooms || this.cachedRooms;\n    }\n\n    /**\n     * This returns the same as getOrderedRooms(), but without the sticky room\n     * map as it causes issues for sticky room handling (see sticky room handling\n     * for more information).\n     * @returns {ITagMap} The cached list of rooms, ordered,\n     * for each tag. May be empty, but never null/undefined.\n     */\n    private getOrderedRoomsWithoutSticky(): ITagMap {\n        return this.cachedRooms;\n    }\n\n    /**\n     * Seeds the Algorithm with a set of rooms. The algorithm will discard all\n     * previously known information and instead use these rooms instead.\n     * @param {Room[]} rooms The rooms to force the algorithm to use.\n     */\n    public setKnownRooms(rooms: Room[]): void {\n        if (isNullOrUndefined(rooms)) throw new Error(`Array of rooms cannot be null`);\n        if (!this.sortAlgorithms) throw new Error(`Cannot set known rooms without a tag sorting map`);\n\n        if (!this.updatesInhibited) {\n            // We only log this if we're expecting to be publishing updates, which means that\n            // this could be an unexpected invocation. If we're inhibited, then this is probably\n            // an intentional invocation.\n            logger.warn(\"Resetting known rooms, initiating regeneration\");\n        }\n\n        // Before we go any further we need to clear (but remember) the sticky room to\n        // avoid accidentally duplicating it in the list.\n        const oldStickyRoom = this._stickyRoom;\n        if (oldStickyRoom) this.updateStickyRoom(null);\n\n        this.rooms = rooms;\n\n        const newTags: ITagMap = {};\n        for (const tagId in this.sortAlgorithms) {\n            // noinspection JSUnfilteredForInLoop\n            newTags[tagId] = [];\n        }\n\n        // If we can avoid doing work, do so.\n        if (!rooms.length) {\n            this.generateFreshTags(newTags); // just in case it wants to do something\n            this.cachedRooms = newTags;\n            return;\n        }\n\n        // Split out the easy rooms first (leave and invite)\n        const memberships = splitRoomsByMembership(rooms);\n\n        for (const room of memberships[EffectiveMembership.Invite]) {\n            newTags[DefaultTagID.Invite].push(room);\n        }\n        for (const room of memberships[EffectiveMembership.Leave]) {\n            // We may not have had an archived section previously, so make sure its there.\n            if (newTags[DefaultTagID.Archived] === undefined) newTags[DefaultTagID.Archived] = [];\n            newTags[DefaultTagID.Archived].push(room);\n        }\n\n        // Now process all the joined rooms. This is a bit more complicated\n        for (const room of memberships[EffectiveMembership.Join]) {\n            const tags = this.getTagsOfJoinedRoom(room);\n\n            let inTag = false;\n            if (tags.length > 0) {\n                for (const tag of tags) {\n                    if (!isNullOrUndefined(newTags[tag])) {\n                        newTags[tag].push(room);\n                        inTag = true;\n                    }\n                }\n            }\n\n            if (!inTag) {\n                if (DMRoomMap.shared().getUserIdForRoomId(room.roomId)) {\n                    newTags[DefaultTagID.DM].push(room);\n                } else {\n                    newTags[DefaultTagID.Untagged].push(room);\n                }\n            }\n        }\n\n        this.generateFreshTags(newTags);\n\n        this.cachedRooms = newTags; // this recalculates the filtered rooms for us\n        this.updateTagsFromCache();\n\n        // Now that we've finished generation, we need to update the sticky room to what\n        // it was. It's entirely possible that it changed lists though, so if it did then\n        // we also have to update the position of it.\n        if (oldStickyRoom && oldStickyRoom.room) {\n            this.updateStickyRoom(oldStickyRoom.room);\n            if (this._stickyRoom && this._stickyRoom.room) {\n                // just in case the update doesn't go according to plan\n                if (this._stickyRoom.tag !== oldStickyRoom.tag) {\n                    // We put the sticky room at the top of the list to treat it as an obvious tag change.\n                    this._stickyRoom.position = 0;\n                    this.recalculateStickyRoom(this._stickyRoom.tag);\n                }\n            }\n        }\n    }\n\n    public getTagsForRoom(room: Room): TagID[] {\n        const tags: TagID[] = [];\n\n        if (!getEffectiveMembership(room.getMyMembership())) return []; // peeked room has no tags\n\n        const membership = getEffectiveMembershipTag(room);\n\n        if (membership === EffectiveMembership.Invite) {\n            tags.push(DefaultTagID.Invite);\n        } else if (membership === EffectiveMembership.Leave) {\n            tags.push(DefaultTagID.Archived);\n        } else {\n            tags.push(...this.getTagsOfJoinedRoom(room));\n        }\n\n        if (!tags.length) tags.push(DefaultTagID.Untagged);\n\n        return tags;\n    }\n\n    private getTagsOfJoinedRoom(room: Room): TagID[] {\n        let tags = Object.keys(room.tags || {});\n\n        if (tags.length === 0) {\n            // Check to see if it's a DM if it isn't anything else\n            if (DMRoomMap.shared().getUserIdForRoomId(room.roomId)) {\n                tags = [DefaultTagID.DM];\n            }\n        }\n        if (room.isCallRoom() && (room.getJoinRule() === JoinRule.Public || room.getJoinRule() === JoinRule.Knock)) {\n            tags.push(DefaultTagID.Conference);\n        }\n\n        return tags;\n    }\n\n    /**\n     * Updates the roomsToTags map\n     */\n    private updateTagsFromCache(): void {\n        const newMap: Algorithm[\"roomIdsToTags\"] = {};\n\n        const tags = Object.keys(this.cachedRooms);\n        for (const tagId of tags) {\n            const rooms = this.cachedRooms[tagId];\n            for (const room of rooms) {\n                if (!newMap[room.roomId]) newMap[room.roomId] = [];\n                newMap[room.roomId].push(tagId);\n            }\n        }\n\n        this.roomIdsToTags = newMap;\n    }\n\n    /**\n     * Called when the Algorithm believes a complete regeneration of the existing\n     * lists is needed.\n     * @param {ITagMap} updatedTagMap The tag map which needs populating. Each tag\n     * will already have the rooms which belong to it - they just need ordering. Must\n     * be mutated in place.\n     */\n    private generateFreshTags(updatedTagMap: ITagMap): void {\n        if (!this.algorithms) throw new Error(\"Not ready: no algorithms to determine tags from\");\n\n        for (const tag of Object.keys(updatedTagMap)) {\n            const algorithm: OrderingAlgorithm = this.algorithms[tag];\n            if (!algorithm) throw new Error(`No algorithm for ${tag}`);\n\n            algorithm.setRooms(updatedTagMap[tag]);\n            updatedTagMap[tag] = algorithm.orderedRooms;\n        }\n    }\n\n    /**\n     * Asks the Algorithm to update its knowledge of a room. For example, when\n     * a user tags a room, joins/creates a room, or leaves a room the Algorithm\n     * should be told that the room's info might have changed. The Algorithm\n     * may no-op this request if no changes are required.\n     * @param {Room} room The room which might have affected sorting.\n     * @param {RoomUpdateCause} cause The reason for the update being triggered.\n     * @returns {Promise<boolean>} A boolean of whether or not getOrderedRooms()\n     * should be called after processing.\n     */\n    public handleRoomUpdate(room: Room, cause: RoomUpdateCause): boolean {\n        if (!this.algorithms) throw new Error(\"Not ready: no algorithms to determine tags from\");\n\n        // Note: check the isSticky against the room ID just in case the reference is wrong\n        const isSticky = this._stickyRoom?.room?.roomId === room.roomId;\n        if (cause === RoomUpdateCause.NewRoom) {\n            const isForLastSticky = this._lastStickyRoom?.room === room;\n            const roomTags = this.roomIdsToTags[room.roomId];\n            const hasTags = roomTags && roomTags.length > 0;\n\n            // Don't change the cause if the last sticky room is being re-added. If we fail to\n            // pass the cause through as NewRoom, we'll fail to lie to the algorithm and thus\n            // lose the room.\n            if (hasTags && !isForLastSticky) {\n                logger.warn(`${room.roomId} is reportedly new but is already known - assuming TagChange instead`);\n                cause = RoomUpdateCause.PossibleTagChange;\n            }\n\n            // Check to see if the room is known first\n            let knownRoomRef = this.rooms.includes(room);\n            if (hasTags && !knownRoomRef) {\n                logger.warn(`${room.roomId} might be a reference change - attempting to update reference`);\n                this.rooms = this.rooms.map((r) => (r.roomId === room.roomId ? room : r));\n                knownRoomRef = this.rooms.includes(room);\n                if (!knownRoomRef) {\n                    logger.warn(`${room.roomId} is still not referenced. It may be sticky.`);\n                }\n            }\n\n            // If we have tags for a room and don't have the room referenced, something went horribly\n            // wrong - the reference should have been updated above.\n            if (hasTags && !knownRoomRef && !isSticky) {\n                throw new Error(`${room.roomId} is missing from room array but is known - trying to find duplicate`);\n            }\n\n            // Like above, update the reference to the sticky room if we need to\n            if (hasTags && isSticky && this._stickyRoom) {\n                // Go directly in and set the sticky room's new reference, being careful not\n                // to trigger a sticky room update ourselves.\n                this._stickyRoom.room = room;\n            }\n\n            // If after all that we're still a NewRoom update, add the room if applicable.\n            // We don't do this for the sticky room (because it causes duplication issues)\n            // or if we know about the reference (as it should be replaced).\n            if (cause === RoomUpdateCause.NewRoom && !isSticky && !knownRoomRef) {\n                this.rooms.push(room);\n            }\n        }\n\n        let didTagChange = false;\n        if (cause === RoomUpdateCause.PossibleTagChange) {\n            const oldTags = this.roomIdsToTags[room.roomId] || [];\n            const newTags = this.getTagsForRoom(room);\n            const diff = arrayDiff(oldTags, newTags);\n            if (diff.removed.length > 0 || diff.added.length > 0) {\n                for (const rmTag of diff.removed) {\n                    const algorithm: OrderingAlgorithm = this.algorithms[rmTag];\n                    if (!algorithm) throw new Error(`No algorithm for ${rmTag}`);\n                    algorithm.handleRoomUpdate(room, RoomUpdateCause.RoomRemoved);\n                    this._cachedRooms[rmTag] = algorithm.orderedRooms;\n                    this.recalculateStickyRoom(rmTag); // update sticky room to make sure it moves if needed\n                    this.recalculateActiveCallRooms(rmTag);\n                }\n                for (const addTag of diff.added) {\n                    const algorithm: OrderingAlgorithm = this.algorithms[addTag];\n                    if (!algorithm) throw new Error(`No algorithm for ${addTag}`);\n                    algorithm.handleRoomUpdate(room, RoomUpdateCause.NewRoom);\n                    this._cachedRooms[addTag] = algorithm.orderedRooms;\n                }\n\n                // Update the tag map so we don't regen it in a moment\n                this.roomIdsToTags[room.roomId] = newTags;\n\n                cause = RoomUpdateCause.Timeline;\n                didTagChange = true;\n            } else {\n                // This is a tag change update and no tags were changed, nothing to do!\n                return false;\n            }\n\n            if (didTagChange && isSticky) {\n                // Manually update the tag for the sticky room without triggering a sticky room\n                // update. The update will be handled implicitly by the sticky room handling and\n                // requires no changes on our part, if we're in the middle of a sticky room change.\n                if (this._lastStickyRoom) {\n                    this._stickyRoom = {\n                        room,\n                        tag: this.roomIdsToTags[room.roomId][0],\n                        position: 0, // right at the top as it changed tags\n                    };\n                } else {\n                    // We have to clear the lock as the sticky room change will trigger updates.\n                    this.setStickyRoom(room);\n                }\n            }\n        }\n\n        // If the update is for a room change which might be the sticky room, prevent it. We\n        // need to make sure that the causes (NewRoom and RoomRemoved) are still triggered though\n        // as the sticky room relies on this.\n        if (cause !== RoomUpdateCause.NewRoom && cause !== RoomUpdateCause.RoomRemoved) {\n            if (this.stickyRoom === room) {\n                return false;\n            }\n        }\n\n        if (!this.roomIdsToTags[room.roomId]) {\n            if (CAUSES_REQUIRING_ROOM.includes(cause)) {\n                return false;\n            }\n\n            // Get the tags for the room and populate the cache\n            const roomTags = this.getTagsForRoom(room).filter((t) => !isNullOrUndefined(this.cachedRooms[t]));\n\n            // \"This should never happen\" condition - we specify DefaultTagID.Untagged in getTagsForRoom(),\n            // which means we should *always* have a tag to go off of.\n            if (!roomTags.length) throw new Error(`Tags cannot be determined for ${room.roomId}`);\n\n            this.roomIdsToTags[room.roomId] = roomTags;\n        }\n\n        const tags = this.roomIdsToTags[room.roomId];\n        if (!tags) {\n            logger.warn(`No tags known for \"${room.name}\" (${room.roomId})`);\n            return false;\n        }\n\n        let changed = didTagChange;\n        for (const tag of tags) {\n            const algorithm: OrderingAlgorithm = this.algorithms[tag];\n            if (!algorithm) throw new Error(`No algorithm for ${tag}`);\n\n            algorithm.handleRoomUpdate(room, cause);\n            this._cachedRooms[tag] = algorithm.orderedRooms;\n\n            // Flag that we've done something\n            this.recalculateStickyRoom(tag); // update sticky room to make sure it appears if needed\n            this.recalculateActiveCallRooms(tag);\n            changed = true;\n        }\n\n        return changed;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EventEmitter } from \"events\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { FILTER_CHANGED, type IFilterCondition } from \"./IFilterCondition\";\nimport { type IDestroyable } from \"../../../utils/IDestroyable\";\nimport SpaceStore from \"../../spaces/SpaceStore\";\nimport { isMetaSpace, MetaSpace, type SpaceKey } from \"../../spaces\";\nimport { setHasDiff } from \"../../../utils/sets\";\nimport SettingsStore from \"../../../settings/SettingsStore\";\n\n/**\n * A filter condition for the room list which reveals rooms which\n * are a member of a given space or if no space is selected shows:\n *  + Orphaned rooms (ones not in any space you are a part of)\n *  + All DMs\n */\nexport class SpaceFilterCondition extends EventEmitter implements IFilterCondition, IDestroyable {\n    private roomIds = new Set<string>();\n    private userIds = new Set<string>();\n    private showPeopleInSpace = true;\n    private space: SpaceKey = MetaSpace.Home;\n\n    public isVisible(room: Room): boolean {\n        return SpaceStore.instance.isRoomInSpace(this.space, room.roomId);\n    }\n\n    private onStoreUpdate = async (forceUpdate = false): Promise<void> => {\n        const beforeRoomIds = this.roomIds;\n        // clone the set as it may be mutated by the space store internally\n        this.roomIds = new Set(SpaceStore.instance.getSpaceFilteredRoomIds(this.space));\n\n        const beforeUserIds = this.userIds;\n        // clone the set as it may be mutated by the space store internally\n        this.userIds = new Set(SpaceStore.instance.getSpaceFilteredUserIds(this.space));\n\n        const beforeShowPeopleInSpace = this.showPeopleInSpace;\n        this.showPeopleInSpace =\n            isMetaSpace(this.space[0]) || SettingsStore.getValue(\"Spaces.showPeopleInSpace\", this.space);\n\n        if (\n            forceUpdate ||\n            beforeShowPeopleInSpace !== this.showPeopleInSpace ||\n            setHasDiff(beforeRoomIds, this.roomIds) ||\n            setHasDiff(beforeUserIds, this.userIds)\n        ) {\n            this.emit(FILTER_CHANGED);\n            // XXX: Room List Store has a bug where updates to the pre-filter during a local echo of a\n            // tags transition seem to be ignored, so refire in the next tick to work around it\n            setTimeout(() => {\n                this.emit(FILTER_CHANGED);\n            });\n        }\n    };\n\n    public updateSpace(space: SpaceKey): void {\n        SpaceStore.instance.off(this.space, this.onStoreUpdate);\n        SpaceStore.instance.on((this.space = space), this.onStoreUpdate);\n        this.onStoreUpdate(true); // initial update from the change to the space\n    }\n\n    public destroy(): void {\n        SpaceStore.instance.off(this.space, this.onStoreUpdate);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type RoomListStore as Interface } from \"./Interface\";\nimport { SpaceFilterCondition } from \"./filters/SpaceFilterCondition\";\nimport SpaceStore from \"../spaces/SpaceStore\";\nimport { MetaSpace, type SpaceKey, UPDATE_HOME_BEHAVIOUR, UPDATE_SELECTED_SPACE } from \"../spaces\";\n\n/**\n * Watches for changes in spaces to manage the filter on the provided RoomListStore\n */\nexport class SpaceWatcher {\n    private readonly filter = new SpaceFilterCondition();\n    // we track these separately to the SpaceStore as we need to observe transitions\n    private activeSpace: SpaceKey = SpaceStore.instance.activeSpace;\n    private allRoomsInHome: boolean = SpaceStore.instance.allRoomsInHome;\n\n    public constructor(private store: Interface) {\n        if (SpaceWatcher.needsFilter(this.activeSpace, this.allRoomsInHome)) {\n            this.updateFilter();\n            store.addFilter(this.filter);\n        }\n        SpaceStore.instance.on(UPDATE_SELECTED_SPACE, this.onSelectedSpaceUpdated);\n        SpaceStore.instance.on(UPDATE_HOME_BEHAVIOUR, this.onHomeBehaviourUpdated);\n    }\n\n    private static needsFilter(spaceKey: SpaceKey, allRoomsInHome: boolean): boolean {\n        return !(spaceKey === MetaSpace.Home && allRoomsInHome);\n    }\n\n    private onSelectedSpaceUpdated = (activeSpace: SpaceKey, allRoomsInHome = this.allRoomsInHome): void => {\n        if (activeSpace === this.activeSpace && allRoomsInHome === this.allRoomsInHome) return; // nop\n\n        const neededFilter = SpaceWatcher.needsFilter(this.activeSpace, this.allRoomsInHome);\n        const needsFilter = SpaceWatcher.needsFilter(activeSpace, allRoomsInHome);\n\n        this.activeSpace = activeSpace;\n        this.allRoomsInHome = allRoomsInHome;\n\n        if (needsFilter) {\n            this.updateFilter();\n        }\n\n        if (!neededFilter && needsFilter) {\n            this.store.addFilter(this.filter);\n        } else if (neededFilter && !needsFilter) {\n            this.store.removeFilter(this.filter);\n        }\n    };\n\n    private onHomeBehaviourUpdated = (allRoomsInHome: boolean): void => {\n        this.onSelectedSpaceUpdated(this.activeSpace, allRoomsInHome);\n    };\n\n    private updateFilter = (): void => {\n        this.filter.updateSpace(this.activeSpace);\n    };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type { Room } from \"matrix-js-sdk/src/matrix\";\nimport type { EventEmitter } from \"events\";\nimport { type ITagMap, type ListAlgorithm, type SortAlgorithm } from \"./algorithms/models\";\nimport { type RoomUpdateCause, type TagID } from \"./models\";\nimport { type IFilterCondition } from \"./filters/IFilterCondition\";\n\nexport enum RoomListStoreEvent {\n    // The event/channel which is called when the room lists have been changed.\n    ListsUpdate = \"lists_update\",\n    // The event which is called when the room list is loading.\n    // Called with the (tagId, bool) which is true when the list is loading, else false.\n    ListsLoading = \"lists_loading\",\n}\n\nexport interface RoomListStore extends EventEmitter {\n    /**\n     * Gets an ordered set of rooms for the all known tags.\n     * @returns {ITagMap} The cached list of rooms, ordered,\n     * for each tag. May be empty, but never null/undefined.\n     */\n    get orderedLists(): ITagMap;\n\n    /**\n     * Return the total number of rooms in this list. Prefer this method to\n     * RoomListStore.orderedLists[tagId].length because the client may not\n     * be aware of all the rooms in this list (e.g in Sliding Sync).\n     * @param tagId the tag to get the room count for.\n     * @returns the number of rooms in this list, or 0 if the list is unknown.\n     */\n    getCount(tagId: TagID): number;\n\n    /**\n     * Set the sort algorithm for the specified tag.\n     * @param tagId the tag to set the algorithm for\n     * @param sort the sort algorithm to set to\n     */\n    setTagSorting(tagId: TagID, sort: SortAlgorithm): void;\n\n    /**\n     * Get the sort algorithm for the specified tag.\n     * @param tagId tag to get the sort algorithm for\n     * @returns the sort algorithm\n     */\n    getTagSorting(tagId: TagID): SortAlgorithm | null;\n\n    /**\n     * Set the list algorithm for the specified tag.\n     * @param tagId the tag to set the algorithm for\n     * @param order the list algorithm to set to\n     */\n    setListOrder(tagId: TagID, order: ListAlgorithm): void;\n\n    /**\n     * Get the list algorithm for the specified tag.\n     * @param tagId tag to get the list algorithm for\n     * @returns the list algorithm\n     */\n    getListOrder(tagId: TagID): ListAlgorithm | null;\n\n    /**\n     * Regenerates the room whole room list, discarding any previous results.\n     *\n     * Note: This is only exposed externally for the tests. Do not call this from within\n     * the app.\n     * @param params.trigger Set to false to prevent a list update from being sent. Should only\n     * be used if the calling code will manually trigger the update.\n     */\n    regenerateAllLists(params: { trigger: boolean }): void;\n\n    /**\n     * Adds a filter condition to the room list store. Filters may be applied async,\n     * and thus might not cause an update to the store immediately.\n     * @param {IFilterCondition} filter The filter condition to add.\n     */\n    addFilter(filter: IFilterCondition): Promise<void>;\n\n    /**\n     * Removes a filter condition from the room list store. If the filter was\n     * not previously added to the room list store, this will no-op. The effects\n     * of removing a filter may be applied async and therefore might not cause\n     * an update right away.\n     * @param {IFilterCondition} filter The filter condition to remove.\n     */\n    removeFilter(filter: IFilterCondition): void;\n\n    /**\n     * Gets the tags for a room identified by the store. The returned set\n     * should never be empty, and will contain DefaultTagID.Untagged if\n     * the store is not aware of any tags.\n     * @param room The room to get the tags for.\n     * @returns The tags for the room.\n     */\n    getTagsForRoom(room: Room): TagID[];\n\n    /**\n     * Manually update a room with a given cause. This should only be used if the\n     * room list store would otherwise be incapable of doing the update itself. Note\n     * that this may race with the room list's regular operation.\n     * @param {Room} room The room to update.\n     * @param {RoomUpdateCause} cause The cause to update for.\n     */\n    manualRoomUpdate(room: Room, cause: RoomUpdateCause): Promise<void>;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient, type Room, EventType, type EmptyObject } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport SettingsStore from \"../../settings/SettingsStore\";\nimport { DefaultTagID, OrderedDefaultTagIDs, RoomUpdateCause, type TagID } from \"./models\";\nimport {\n    type IListOrderingMap,\n    type ITagMap,\n    type ITagSortingMap,\n    ListAlgorithm,\n    SortAlgorithm,\n} from \"./algorithms/models\";\nimport { type ActionPayload } from \"../../dispatcher/payloads\";\nimport defaultDispatcher, { type MatrixDispatcher } from \"../../dispatcher/dispatcher\";\nimport { readReceiptChangeIsFor } from \"../../utils/read-receipts\";\nimport { FILTER_CHANGED, type IFilterCondition } from \"./filters/IFilterCondition\";\nimport { Algorithm, LIST_UPDATED_EVENT } from \"./algorithms/Algorithm\";\nimport { EffectiveMembership, getEffectiveMembership, getEffectiveMembershipTag } from \"../../utils/membership\";\nimport RoomListLayoutStore from \"./RoomListLayoutStore\";\nimport { MarkedExecution } from \"../../utils/MarkedExecution\";\nimport { AsyncStoreWithClient } from \"../AsyncStoreWithClient\";\nimport { RoomNotificationStateStore } from \"../notifications/RoomNotificationStateStore\";\nimport { VisibilityProvider } from \"./filters/VisibilityProvider\";\nimport { SpaceWatcher } from \"./SpaceWatcher\";\nimport { type IRoomTimelineActionPayload } from \"../../actions/MatrixActionCreators\";\nimport { type RoomListStore as Interface, RoomListStoreEvent } from \"./Interface\";\nimport { UPDATE_EVENT } from \"../AsyncStore\";\nimport { SdkContextClass } from \"../../contexts/SDKContext\";\nimport { getChangedOverrideRoomMutePushRules } from \"./utils/roomMute\";\n\nexport const LISTS_UPDATE_EVENT = RoomListStoreEvent.ListsUpdate;\nexport const LISTS_LOADING_EVENT = RoomListStoreEvent.ListsLoading; // unused; used by SlidingRoomListStore\n\nexport class RoomListStoreClass extends AsyncStoreWithClient<EmptyObject> implements Interface {\n    /**\n     * Set to true if you're running tests on the store. Should not be touched in\n     * any other environment.\n     */\n    public static TEST_MODE = false;\n\n    private initialListsGenerated = false;\n    private msc3946ProcessDynamicPredecessor: boolean;\n    private msc3946SettingWatcherRef: string;\n    private algorithm = new Algorithm();\n    private prefilterConditions: IFilterCondition[] = [];\n    private updateFn = new MarkedExecution(() => {\n        for (const tagId of Object.keys(this.orderedLists)) {\n            RoomNotificationStateStore.instance.getListState(tagId).setRooms(this.orderedLists[tagId]);\n        }\n        this.emit(LISTS_UPDATE_EVENT);\n    });\n\n    public constructor(dis: MatrixDispatcher) {\n        super(dis);\n        this.setMaxListeners(20); // RoomList + LeftPanel + 8xRoomSubList + spares\n        this.algorithm.start();\n\n        this.msc3946ProcessDynamicPredecessor = SettingsStore.getValue(\"feature_dynamic_room_predecessors\");\n        this.msc3946SettingWatcherRef = SettingsStore.watchSetting(\n            \"feature_dynamic_room_predecessors\",\n            null,\n            (_settingName, _roomId, _level, _newValAtLevel, newVal) => {\n                this.msc3946ProcessDynamicPredecessor = newVal;\n                this.regenerateAllLists({ trigger: true });\n            },\n        );\n    }\n\n    public componentWillUnmount(): void {\n        SettingsStore.unwatchSetting(this.msc3946SettingWatcherRef);\n    }\n\n    private setupWatchers(): void {\n        // TODO: Maybe destroy this if this class supports destruction\n        new SpaceWatcher(this);\n    }\n\n    public get orderedLists(): ITagMap {\n        if (!this.algorithm) return {}; // No tags yet.\n        return this.algorithm.getOrderedRooms();\n    }\n\n    // Intended for test usage\n    public async resetStore(): Promise<void> {\n        await this.reset();\n        this.prefilterConditions = [];\n        this.initialListsGenerated = false;\n\n        this.algorithm.off(LIST_UPDATED_EVENT, this.onAlgorithmListUpdated);\n        this.algorithm.off(FILTER_CHANGED, this.onAlgorithmListUpdated);\n        this.algorithm.stop();\n        this.algorithm = new Algorithm();\n        this.algorithm.on(LIST_UPDATED_EVENT, this.onAlgorithmListUpdated);\n        this.algorithm.on(FILTER_CHANGED, this.onAlgorithmListUpdated);\n\n        // Reset state without causing updates as the client will have been destroyed\n        // and downstream code will throw NPE errors.\n        await this.reset(null, true);\n    }\n\n    // Public for test usage. Do not call this.\n    public async makeReady(forcedClient?: MatrixClient): Promise<void> {\n        if (forcedClient) {\n            this.readyStore.useUnitTestClient(forcedClient);\n        }\n\n        SdkContextClass.instance.roomViewStore.addListener(UPDATE_EVENT, () => this.handleRVSUpdate({}));\n        this.algorithm.on(LIST_UPDATED_EVENT, this.onAlgorithmListUpdated);\n        this.algorithm.on(FILTER_CHANGED, this.onAlgorithmFilterUpdated);\n        this.setupWatchers();\n\n        // Update any settings here, as some may have happened before we were logically ready.\n        logger.log(\"Regenerating room lists: Startup\");\n        this.updateAlgorithmInstances();\n        this.regenerateAllLists({ trigger: false });\n        this.handleRVSUpdate({ trigger: false }); // fake an RVS update to adjust sticky room, if needed\n\n        this.updateFn.mark(); // we almost certainly want to trigger an update.\n        this.updateFn.trigger();\n    }\n\n    /**\n     * Handles suspected RoomViewStore changes.\n     * @param trigger Set to false to prevent a list update from being sent. Should only\n     * be used if the calling code will manually trigger the update.\n     */\n    private handleRVSUpdate({ trigger = true }): void {\n        if (!this.matrixClient) return; // We assume there won't be RVS updates without a client\n\n        const activeRoomId = SdkContextClass.instance.roomViewStore.getRoomId();\n        if (!activeRoomId && this.algorithm.stickyRoom) {\n            this.algorithm.setStickyRoom(null);\n        } else if (activeRoomId) {\n            const activeRoom = this.matrixClient.getRoom(activeRoomId);\n            if (!activeRoom) {\n                logger.warn(`${activeRoomId} is current in RVS but missing from client - clearing sticky room`);\n                this.algorithm.setStickyRoom(null);\n            } else if (activeRoom !== this.algorithm.stickyRoom) {\n                this.algorithm.setStickyRoom(activeRoom);\n            }\n        }\n\n        if (trigger) this.updateFn.trigger();\n    }\n\n    protected async onReady(): Promise<any> {\n        await this.makeReady();\n    }\n\n    protected async onNotReady(): Promise<any> {\n        await this.resetStore();\n    }\n\n    protected async onAction(payload: ActionPayload): Promise<void> {\n        // If we're not remotely ready, don't even bother scheduling the dispatch handling.\n        // This is repeated in the handler just in case things change between a decision here and\n        // when the timer fires.\n        const logicallyReady = this.matrixClient && this.initialListsGenerated;\n        if (!logicallyReady) return;\n\n        // When we're running tests we can't reliably use setImmediate out of timing concerns.\n        // As such, we use a more synchronous model.\n        if (RoomListStoreClass.TEST_MODE) {\n            await this.onDispatchAsync(payload);\n            return;\n        }\n\n        // We do this to intentionally break out of the current event loop task, allowing\n        // us to instead wait for a more convenient time to run our updates.\n        setTimeout(() => this.onDispatchAsync(payload));\n    }\n\n    protected async onDispatchAsync(payload: ActionPayload): Promise<void> {\n        // Everything here requires a MatrixClient or some sort of logical readiness.\n        if (!this.matrixClient || !this.initialListsGenerated) return;\n\n        if (!this.algorithm) {\n            // This shouldn't happen because `initialListsGenerated` implies we have an algorithm.\n            throw new Error(\"Room list store has no algorithm to process dispatcher update with\");\n        }\n\n        if (payload.action === \"MatrixActions.Room.receipt\") {\n            // First see if the receipt event is for our own user. If it was, trigger\n            // a room update (we probably read the room on a different device).\n            if (readReceiptChangeIsFor(payload.event, this.matrixClient)) {\n                const room = payload.room;\n                if (!room) {\n                    logger.warn(`Own read receipt was in unknown room ${room.roomId}`);\n                    return;\n                }\n                await this.handleRoomUpdate(room, RoomUpdateCause.ReadReceipt);\n                this.updateFn.trigger();\n                return;\n            }\n        } else if (payload.action === \"MatrixActions.Room.tags\") {\n            const roomPayload = <any>payload; // TODO: Type out the dispatcher types\n            await this.handleRoomUpdate(roomPayload.room, RoomUpdateCause.PossibleTagChange);\n            this.updateFn.trigger();\n        } else if (payload.action === \"MatrixActions.Room.timeline\") {\n            const eventPayload = <IRoomTimelineActionPayload>payload;\n\n            // Ignore non-live events (backfill) and notification timeline set events (without a room)\n            if (!eventPayload.isLiveEvent || !eventPayload.isLiveUnfilteredRoomTimelineEvent || !eventPayload.room) {\n                return;\n            }\n\n            const roomId = eventPayload.event.getRoomId();\n            const room = this.matrixClient.getRoom(roomId);\n            const tryUpdate = async (updatedRoom: Room): Promise<void> => {\n                if (\n                    eventPayload.event.getType() === EventType.RoomTombstone &&\n                    eventPayload.event.getStateKey() === \"\"\n                ) {\n                    const newRoom = this.matrixClient?.getRoom(eventPayload.event.getContent()[\"replacement_room\"]);\n                    if (newRoom) {\n                        // If we have the new room, then the new room check will have seen the predecessor\n                        // and did the required updates, so do nothing here.\n                        return;\n                    }\n                }\n                // If the join rule changes we need to update the tags for the room.\n                // A conference tag is determined by the room public join rule.\n                if (eventPayload.event.getType() === EventType.RoomJoinRules)\n                    await this.handleRoomUpdate(updatedRoom, RoomUpdateCause.PossibleTagChange);\n                else await this.handleRoomUpdate(updatedRoom, RoomUpdateCause.Timeline);\n\n                this.updateFn.trigger();\n            };\n            if (!room) {\n                logger.warn(`Live timeline event ${eventPayload.event.getId()} received without associated room`);\n                logger.warn(`Queuing failed room update for retry as a result.`);\n                window.setTimeout(async (): Promise<void> => {\n                    const updatedRoom = this.matrixClient?.getRoom(roomId);\n\n                    if (updatedRoom) {\n                        await tryUpdate(updatedRoom);\n                    }\n                }, 100); // 100ms should be enough for the room to show up\n                return;\n            } else {\n                await tryUpdate(room);\n            }\n        } else if (payload.action === \"MatrixActions.Event.decrypted\") {\n            const eventPayload = <any>payload; // TODO: Type out the dispatcher types\n            const roomId = eventPayload.event.getRoomId();\n            if (!roomId) {\n                return;\n            }\n            const room = this.matrixClient.getRoom(roomId);\n            if (!room) {\n                logger.warn(`Event ${eventPayload.event.getId()} was decrypted in an unknown room ${roomId}`);\n                return;\n            }\n            await this.handleRoomUpdate(room, RoomUpdateCause.Timeline);\n            this.updateFn.trigger();\n        } else if (payload.action === \"MatrixActions.accountData\" && payload.event_type === EventType.Direct) {\n            const eventPayload = <any>payload; // TODO: Type out the dispatcher types\n            const dmMap = eventPayload.event.getContent();\n            for (const userId of Object.keys(dmMap)) {\n                const roomIds = dmMap[userId];\n                for (const roomId of roomIds) {\n                    const room = this.matrixClient.getRoom(roomId);\n                    if (!room) {\n                        logger.warn(`${roomId} was found in DMs but the room is not in the store`);\n                        continue;\n                    }\n\n                    // We expect this RoomUpdateCause to no-op if there's no change, and we don't expect\n                    // the user to have hundreds of rooms to update in one event. As such, we just hammer\n                    // away at updates until the problem is solved. If we were expecting more than a couple\n                    // of rooms to be updated at once, we would consider batching the rooms up.\n                    await this.handleRoomUpdate(room, RoomUpdateCause.PossibleTagChange);\n                }\n            }\n            this.updateFn.trigger();\n        } else if (payload.action === \"MatrixActions.Room.myMembership\") {\n            this.onDispatchMyMembership(<any>payload);\n            return;\n        }\n\n        const possibleMuteChangeRoomIds = getChangedOverrideRoomMutePushRules(payload);\n        if (possibleMuteChangeRoomIds) {\n            for (const roomId of possibleMuteChangeRoomIds) {\n                const room = roomId && this.matrixClient.getRoom(roomId);\n                if (room) {\n                    await this.handleRoomUpdate(room, RoomUpdateCause.PossibleMuteChange);\n                }\n            }\n            this.updateFn.trigger();\n        }\n    }\n\n    /**\n     * Handle a MatrixActions.Room.myMembership event from the dispatcher.\n     *\n     * Public for test.\n     */\n    public async onDispatchMyMembership(membershipPayload: any): Promise<void> {\n        // TODO: Type out the dispatcher types so membershipPayload is not any\n        const oldMembership = getEffectiveMembership(membershipPayload.oldMembership);\n        const newMembership = getEffectiveMembershipTag(membershipPayload.room, membershipPayload.membership);\n        if (oldMembership !== EffectiveMembership.Join && newMembership === EffectiveMembership.Join) {\n            // If we're joining an upgraded room, we'll want to make sure we don't proliferate the dead room in the list.\n            const room: Room = membershipPayload.room;\n            const roomUpgradeHistory = room.client.getRoomUpgradeHistory(\n                room.roomId,\n                true,\n                this.msc3946ProcessDynamicPredecessor,\n            );\n            const predecessors = roomUpgradeHistory.slice(0, roomUpgradeHistory.indexOf(room));\n            for (const predecessor of predecessors) {\n                const isSticky = this.algorithm.stickyRoom === predecessor;\n                if (isSticky) {\n                    this.algorithm.setStickyRoom(null);\n                }\n                // Note: we hit the algorithm instead of our handleRoomUpdate() function to\n                // avoid redundant updates.\n                this.algorithm.handleRoomUpdate(predecessor, RoomUpdateCause.RoomRemoved);\n            }\n\n            await this.handleRoomUpdate(membershipPayload.room, RoomUpdateCause.NewRoom);\n            this.updateFn.trigger();\n            return;\n        }\n\n        if (oldMembership !== EffectiveMembership.Invite && newMembership === EffectiveMembership.Invite) {\n            await this.handleRoomUpdate(membershipPayload.room, RoomUpdateCause.NewRoom);\n            this.updateFn.trigger();\n            return;\n        }\n\n        // If it's not a join, it's transitioning into a different list (possibly historical)\n        if (oldMembership !== newMembership) {\n            await this.handleRoomUpdate(membershipPayload.room, RoomUpdateCause.PossibleTagChange);\n            this.updateFn.trigger();\n            return;\n        }\n    }\n\n    private async handleRoomUpdate(room: Room, cause: RoomUpdateCause): Promise<any> {\n        if (!VisibilityProvider.instance.isRoomVisible(room)) {\n            return; // don't do anything on rooms that aren't visible\n        }\n\n        if (\n            (cause === RoomUpdateCause.NewRoom || cause === RoomUpdateCause.PossibleTagChange) &&\n            !this.prefilterConditions.every((c) => c.isVisible(room))\n        ) {\n            return; // don't do anything on new/moved rooms which ought not to be shown\n        }\n\n        const shouldUpdate = this.algorithm.handleRoomUpdate(room, cause);\n        if (shouldUpdate) {\n            this.updateFn.mark();\n        }\n    }\n\n    private async recalculatePrefiltering(): Promise<void> {\n        if (!this.algorithm) return;\n        if (!this.algorithm.hasTagSortingMap) return; // we're still loading\n\n        // Inhibit updates because we're about to lie heavily to the algorithm\n        this.algorithm.updatesInhibited = true;\n\n        // Figure out which rooms are about to be valid, and the state of affairs\n        const rooms = this.getPlausibleRooms();\n        const currentSticky = this.algorithm.stickyRoom;\n        const stickyIsStillPresent = currentSticky && rooms.includes(currentSticky);\n\n        // Reset the sticky room before resetting the known rooms so the algorithm\n        // doesn't freak out.\n        this.algorithm.setStickyRoom(null);\n        this.algorithm.setKnownRooms(rooms);\n\n        // Set the sticky room back, if needed, now that we have updated the store.\n        // This will use relative stickyness to the new room set.\n        if (stickyIsStillPresent) {\n            this.algorithm.setStickyRoom(currentSticky);\n        }\n\n        // Finally, mark an update and resume updates from the algorithm\n        this.updateFn.mark();\n        this.algorithm.updatesInhibited = false;\n    }\n\n    public setTagSorting(tagId: TagID, sort: SortAlgorithm): void {\n        this.setAndPersistTagSorting(tagId, sort);\n        // We'll always need an update after changing the sort order, so mark for update and trigger\n        // immediately.\n        this.updateFn.mark();\n        this.updateFn.trigger();\n    }\n\n    private setAndPersistTagSorting(tagId: TagID, sort: SortAlgorithm): void {\n        this.algorithm.setTagSorting(tagId, sort);\n        // TODO: Per-account? https://github.com/vector-im/element-web/issues/14114\n        localStorage.setItem(`mx_tagSort_${tagId}`, sort);\n    }\n\n    public getTagSorting(tagId: TagID): SortAlgorithm | null {\n        return this.algorithm.getTagSorting(tagId);\n    }\n\n    // noinspection JSMethodCanBeStatic\n    private getStoredTagSorting(tagId: TagID): SortAlgorithm {\n        // TODO: Per-account? https://github.com/vector-im/element-web/issues/14114\n        return <SortAlgorithm>localStorage.getItem(`mx_tagSort_${tagId}`);\n    }\n\n    // logic must match calculateListOrder\n    private calculateTagSorting(tagId: TagID): SortAlgorithm {\n        const definedSort = this.getTagSorting(tagId);\n        const storedSort = this.getStoredTagSorting(tagId);\n\n        // We use the following order to determine which of the 4 flags to use:\n        // Stored > Settings > Defined > Default\n\n        let tagSort = SortAlgorithm.Recent;\n        if (storedSort) {\n            tagSort = storedSort;\n        } else if (definedSort) {\n            tagSort = definedSort;\n        } // else default (already set)\n\n        return tagSort;\n    }\n\n    public setListOrder(tagId: TagID, order: ListAlgorithm): void {\n        this.setAndPersistListOrder(tagId, order);\n        this.updateFn.trigger();\n    }\n\n    private setAndPersistListOrder(tagId: TagID, order: ListAlgorithm): void {\n        this.algorithm.setListOrdering(tagId, order);\n        // TODO: Per-account? https://github.com/vector-im/element-web/issues/14114\n        localStorage.setItem(`mx_listOrder_${tagId}`, order);\n    }\n\n    public getListOrder(tagId: TagID): ListAlgorithm | null {\n        return this.algorithm.getListOrdering(tagId);\n    }\n\n    // noinspection JSMethodCanBeStatic\n    private getStoredListOrder(tagId: TagID): ListAlgorithm {\n        // TODO: Per-account? https://github.com/vector-im/element-web/issues/14114\n        return <ListAlgorithm>localStorage.getItem(`mx_listOrder_${tagId}`);\n    }\n\n    // logic must match calculateTagSorting\n    private calculateListOrder(tagId: TagID): ListAlgorithm {\n        const defaultOrder = ListAlgorithm.Natural;\n        const definedOrder = this.getListOrder(tagId);\n        const storedOrder = this.getStoredListOrder(tagId);\n\n        // We use the following order to determine which of the 4 flags to use:\n        // Stored > Settings > Defined > Default\n\n        let listOrder = defaultOrder;\n        if (storedOrder) {\n            listOrder = storedOrder;\n        } else if (definedOrder) {\n            listOrder = definedOrder;\n        } // else default (already set)\n\n        return listOrder;\n    }\n\n    private updateAlgorithmInstances(): void {\n        // We'll require an update, so mark for one. Marking now also prevents the calls\n        // to setTagSorting and setListOrder from causing triggers.\n        this.updateFn.mark();\n\n        for (const tag of Object.keys(this.orderedLists)) {\n            const definedSort = this.getTagSorting(tag);\n            const definedOrder = this.getListOrder(tag);\n\n            const tagSort = this.calculateTagSorting(tag);\n            const listOrder = this.calculateListOrder(tag);\n\n            if (tagSort !== definedSort) {\n                this.setAndPersistTagSorting(tag, tagSort);\n            }\n            if (listOrder !== definedOrder) {\n                this.setAndPersistListOrder(tag, listOrder);\n            }\n        }\n    }\n\n    private onAlgorithmListUpdated = (forceUpdate: boolean): void => {\n        this.updateFn.mark();\n        if (forceUpdate) this.updateFn.trigger();\n    };\n\n    private onAlgorithmFilterUpdated = (): void => {\n        // The filter can happen off-cycle, so trigger an update. The filter will have\n        // already caused a mark.\n        this.updateFn.trigger();\n    };\n\n    private onPrefilterUpdated = async (): Promise<void> => {\n        await this.recalculatePrefiltering();\n        this.updateFn.trigger();\n    };\n\n    private getPlausibleRooms(): Room[] {\n        if (!this.matrixClient) return [];\n\n        let rooms = this.matrixClient.getVisibleRooms(this.msc3946ProcessDynamicPredecessor);\n        rooms = rooms.filter((r) => VisibilityProvider.instance.isRoomVisible(r));\n\n        if (this.prefilterConditions.length > 0) {\n            rooms = rooms.filter((r) => {\n                for (const filter of this.prefilterConditions) {\n                    if (!filter.isVisible(r)) {\n                        return false;\n                    }\n                }\n                return true;\n            });\n        }\n\n        return rooms;\n    }\n\n    /**\n     * Regenerates the room whole room list, discarding any previous results.\n     *\n     * Note: This is only exposed externally for the tests. Do not call this from within\n     * the app.\n     * @param trigger Set to false to prevent a list update from being sent. Should only\n     * be used if the calling code will manually trigger the update.\n     */\n    public regenerateAllLists({ trigger = true }): void {\n        logger.warn(\"Regenerating all room lists\");\n\n        const rooms = this.getPlausibleRooms();\n\n        const sorts: ITagSortingMap = {};\n        const orders: IListOrderingMap = {};\n        const allTags = [...OrderedDefaultTagIDs];\n        for (const tagId of allTags) {\n            sorts[tagId] = this.calculateTagSorting(tagId);\n            orders[tagId] = this.calculateListOrder(tagId);\n\n            RoomListLayoutStore.instance.ensureLayoutExists(tagId);\n        }\n\n        this.algorithm.populateTags(sorts, orders);\n        this.algorithm.setKnownRooms(rooms);\n\n        this.initialListsGenerated = true;\n\n        if (trigger) this.updateFn.trigger();\n    }\n\n    /**\n     * Adds a filter condition to the room list store. Filters may be applied async,\n     * and thus might not cause an update to the store immediately.\n     * @param {IFilterCondition} filter The filter condition to add.\n     */\n    public async addFilter(filter: IFilterCondition): Promise<void> {\n        filter.on(FILTER_CHANGED, this.onPrefilterUpdated);\n        this.prefilterConditions.push(filter);\n        const promise = this.recalculatePrefiltering();\n        promise.then(() => this.updateFn.trigger());\n    }\n\n    /**\n     * Removes a filter condition from the room list store. If the filter was\n     * not previously added to the room list store, this will no-op. The effects\n     * of removing a filter may be applied async and therefore might not cause\n     * an update right away.\n     * @param {IFilterCondition} filter The filter condition to remove.\n     */\n    public removeFilter(filter: IFilterCondition): void {\n        let promise = Promise.resolve();\n        let removed = false;\n        const idx = this.prefilterConditions.indexOf(filter);\n        if (idx >= 0) {\n            filter.off(FILTER_CHANGED, this.onPrefilterUpdated);\n            this.prefilterConditions.splice(idx, 1);\n            promise = this.recalculatePrefiltering();\n            removed = true;\n        }\n\n        if (removed) {\n            promise.then(() => this.updateFn.trigger());\n        }\n    }\n\n    /**\n     * Gets the tags for a room identified by the store. The returned set\n     * should never be empty, and will contain DefaultTagID.Untagged if\n     * the store is not aware of any tags.\n     * @param room The room to get the tags for.\n     * @returns The tags for the room.\n     */\n    public getTagsForRoom(room: Room): TagID[] {\n        const algorithmTags = this.algorithm.getTagsForRoom(room);\n        if (!algorithmTags) return [DefaultTagID.Untagged];\n        return algorithmTags;\n    }\n\n    public getCount(tagId: TagID): number {\n        // The room list store knows about all the rooms, so just return the length.\n        return this.orderedLists[tagId].length || 0;\n    }\n\n    /**\n     * Manually update a room with a given cause. This should only be used if the\n     * room list store would otherwise be incapable of doing the update itself. Note\n     * that this may race with the room list's regular operation.\n     * @param {Room} room The room to update.\n     * @param {RoomUpdateCause} cause The cause to update for.\n     */\n    public async manualRoomUpdate(room: Room, cause: RoomUpdateCause): Promise<void> {\n        await this.handleRoomUpdate(room, cause);\n        this.updateFn.trigger();\n    }\n}\n\nexport default class RoomListStore {\n    private static internalInstance: Interface;\n\n    public static get instance(): Interface {\n        if (!RoomListStore.internalInstance) {\n            const instance = new RoomListStoreClass(defaultDispatcher);\n            instance.start();\n            RoomListStore.internalInstance = instance;\n        }\n\n        return this.internalInstance;\n    }\n}\n\nwindow.mxRoomListStore = RoomListStore.instance;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { type TagID } from \"../models\";\nimport { type OrderingAlgorithm } from \"./list-ordering/OrderingAlgorithm\";\n\nexport enum SortAlgorithm {\n    Manual = \"MANUAL\",\n    Alphabetic = \"ALPHABETIC\",\n    Recent = \"RECENT\",\n}\n\nexport enum ListAlgorithm {\n    // Orders Red > Grey > Bold > Idle\n    Importance = \"IMPORTANCE\",\n\n    // Orders however the SortAlgorithm decides\n    Natural = \"NATURAL\",\n}\n\nexport interface ITagSortingMap {\n    // @ts-ignore - TypeScript really wants this to be [tagId: string] but we know better.\n    [tagId: TagID]: SortAlgorithm;\n}\n\nexport interface IListOrderingMap {\n    // @ts-ignore - TypeScript really wants this to be [tagId: string] but we know better.\n    [tagId: TagID]: ListAlgorithm;\n}\n\nexport interface IOrderingAlgorithmMap {\n    // @ts-ignore - TypeScript really wants this to be [tagId: string] but we know better.\n    [tagId: TagID]: OrderingAlgorithm;\n}\n\nexport interface ITagMap {\n    // @ts-ignore - TypeScript really wants this to be [tagId: string] but we know better.\n    [tagId: TagID]: Room[];\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room, type MatrixEvent, EventType } from \"matrix-js-sdk/src/matrix\";\n\nimport { type TagID } from \"../../models\";\nimport { type IAlgorithm } from \"./IAlgorithm\";\nimport { MatrixClientPeg } from \"../../../../MatrixClientPeg\";\nimport * as Unread from \"../../../../Unread\";\nimport { EffectiveMembership, getEffectiveMembership } from \"../../../../utils/membership\";\n\nexport function shouldCauseReorder(event: MatrixEvent): boolean {\n    const type = event.getType();\n    const content = event.getContent();\n    const prevContent = event.getPrevContent();\n\n    // Never ignore membership changes\n    if (type === EventType.RoomMember && prevContent.membership !== content.membership) return true;\n\n    // Ignore display name changes\n    if (type === EventType.RoomMember && prevContent.displayname !== content.displayname) return false;\n    // Ignore avatar changes\n    if (type === EventType.RoomMember && prevContent.avatar_url !== content.avatar_url) return false;\n\n    return true;\n}\n\nexport const sortRooms = (rooms: Room[]): Room[] => {\n    // We cache the timestamp lookup to avoid iterating forever on the timeline\n    // of events. This cache only survives a single sort though.\n    // We wouldn't need this if `.sort()` didn't constantly try and compare all\n    // of the rooms to each other.\n\n    // TODO: We could probably improve the sorting algorithm here by finding changes.\n    // See https://github.com/vector-im/element-web/issues/14459\n    // For example, if we spent a little bit of time to determine which elements have\n    // actually changed (probably needs to be done higher up?) then we could do an\n    // insertion sort or similar on the limited set of changes.\n\n    // TODO: Don't assume we're using the same client as the peg\n    // See https://github.com/vector-im/element-web/issues/14458\n    let myUserId = \"\";\n    if (MatrixClientPeg.get()) {\n        myUserId = MatrixClientPeg.get()!.getSafeUserId();\n    }\n\n    const tsCache: { [roomId: string]: number } = {};\n\n    return rooms.sort((a, b) => {\n        const roomALastTs = tsCache[a.roomId] ?? getLastTs(a, myUserId);\n        const roomBLastTs = tsCache[b.roomId] ?? getLastTs(b, myUserId);\n\n        tsCache[a.roomId] = roomALastTs;\n        tsCache[b.roomId] = roomBLastTs;\n\n        return roomBLastTs - roomALastTs;\n    });\n};\n\nexport const getLastTs = (r: Room, userId: string): number => {\n    const mainTimelineLastTs = ((): number => {\n        // Apparently we can have rooms without timelines, at least under testing\n        // environments. Just return MAX_INT when this happens.\n        if (!r?.timeline) {\n            return Number.MAX_SAFE_INTEGER;\n        }\n        // MSC4186: Simplified Sliding Sync sets this.\n        // If it's present, sort by it.\n        const bumpStamp = r.getBumpStamp();\n        if (bumpStamp) {\n            return bumpStamp;\n        }\n\n        // If the room hasn't been joined yet, it probably won't have a timeline to\n        // parse. We'll still fall back to the timeline if this fails, but chances\n        // are we'll at least have our own membership event to go off of.\n        const effectiveMembership = getEffectiveMembership(r.getMyMembership());\n        if (effectiveMembership !== EffectiveMembership.Join) {\n            const membershipEvent = r.currentState.getStateEvents(EventType.RoomMember, userId);\n            if (membershipEvent && !Array.isArray(membershipEvent)) {\n                return membershipEvent.getTs();\n            }\n        }\n\n        for (let i = r.timeline.length - 1; i >= 0; --i) {\n            const ev = r.timeline[i];\n            if (!ev.getTs()) continue; // skip events that don't have timestamps (tests only?)\n\n            if (\n                (ev.getSender() === userId && shouldCauseReorder(ev)) ||\n                Unread.eventTriggersUnreadCount(r.client, ev)\n            ) {\n                return ev.getTs();\n            }\n        }\n\n        // we might only have events that don't trigger the unread indicator,\n        // in which case use the oldest event even if normally it wouldn't count.\n        // This is better than just assuming the last event was forever ago.\n        return r.timeline[0]?.getTs() ?? Number.MAX_SAFE_INTEGER;\n    })();\n\n    const threadLastEventTimestamps = r.getThreads().map((thread) => {\n        const event = thread.replyToEvent ?? thread.rootEvent;\n        return event?.getTs() ?? 0;\n    });\n\n    return Math.max(mainTimelineLastTs, ...threadLastEventTimestamps);\n};\n\n/**\n * Sorts rooms according to the last event's timestamp in each room that seems\n * useful to the user.\n */\nexport class RecentAlgorithm implements IAlgorithm {\n    public sortRooms(rooms: Room[], tagId: TagID): Room[] {\n        return sortRooms(rooms);\n    }\n\n    public getLastTs(room: Room, userId: string): number {\n        return getLastTs(room, userId);\n    }\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2020 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { RoomListCustomisations } from \"../../../customisations/RoomList\";\nimport { isLocalRoom } from \"../../../utils/localRoom/isLocalRoom\";\n\nexport class VisibilityProvider {\n    private static internalInstance: VisibilityProvider;\n\n    private constructor() {}\n\n    public static get instance(): VisibilityProvider {\n        if (!VisibilityProvider.internalInstance) {\n            VisibilityProvider.internalInstance = new VisibilityProvider();\n        }\n        return VisibilityProvider.internalInstance;\n    }\n\n    public isRoomVisible(room?: Room): boolean {\n        if (!room) {\n            return false;\n        }\n\n        // hide space rooms as they'll be shown in the SpacePanel\n        if (room.isSpaceRoom()) {\n            return false;\n        }\n\n        if (isLocalRoom(room)) {\n            // local rooms shouldn't show up anywhere\n            return false;\n        }\n\n        const isVisibleFn = RoomListCustomisations.isRoomVisible;\n        if (isVisibleFn) {\n            return isVisibleFn(room);\n        }\n\n        return true; // default\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport enum DefaultTagID {\n    Invite = \"im.vector.fake.invite\",\n    Untagged = \"im.vector.fake.recent\", // legacy: used to just be 'recent rooms' but now it's all untagged rooms\n    Archived = \"im.vector.fake.archived\",\n    LowPriority = \"m.lowpriority\",\n    Favourite = \"m.favourite\",\n    DM = \"im.vector.fake.direct\",\n    Conference = \"im.vector.fake.conferences\",\n    ServerNotice = \"m.server_notice\",\n    Suggested = \"im.vector.fake.suggested\",\n}\n\nexport const OrderedDefaultTagIDs = [\n    DefaultTagID.Invite,\n    DefaultTagID.Favourite,\n    DefaultTagID.DM,\n    DefaultTagID.Conference,\n    DefaultTagID.Untagged,\n    DefaultTagID.LowPriority,\n    DefaultTagID.ServerNotice,\n    DefaultTagID.Suggested,\n    DefaultTagID.Archived,\n];\n\nexport type TagID = string | DefaultTagID;\n\nexport enum RoomUpdateCause {\n    Timeline = \"TIMELINE\",\n    PossibleTagChange = \"POSSIBLE_TAG_CHANGE\",\n    PossibleMuteChange = \"POSSIBLE_MUTE_CHANGE\",\n    ReadReceipt = \"READ_RECEIPT\",\n    NewRoom = \"NEW_ROOM\",\n    RoomRemoved = \"ROOM_REMOVED\",\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, EventType, type IPushRules } from \"matrix-js-sdk/src/matrix\";\n\nimport { type ActionPayload } from \"../../../dispatcher/payloads\";\nimport { isRuleMaybeRoomMuteRule } from \"../../../RoomNotifs\";\nimport { arrayDiff } from \"../../../utils/arrays\";\n\n/**\n * Gets any changed push rules that are room specific overrides\n * that mute notifications\n * @param actionPayload\n * @returns {string[]} ruleIds of added or removed rules\n */\nexport const getChangedOverrideRoomMutePushRules = (actionPayload: ActionPayload): string[] | undefined => {\n    if (\n        actionPayload.action !== \"MatrixActions.accountData\" ||\n        actionPayload.event?.getType() !== EventType.PushRules\n    ) {\n        return undefined;\n    }\n    const event = actionPayload.event as MatrixEvent;\n    const prevEvent = actionPayload.previousEvent as MatrixEvent | undefined;\n\n    if (!event || !prevEvent) {\n        return undefined;\n    }\n\n    const roomPushRules = (event.getContent() as IPushRules)?.global?.override?.filter(isRuleMaybeRoomMuteRule);\n    const prevRoomPushRules = (prevEvent?.getContent() as IPushRules)?.global?.override?.filter(\n        isRuleMaybeRoomMuteRule,\n    );\n\n    const { added, removed } = arrayDiff(\n        prevRoomPushRules?.map((rule) => rule.rule_id) || [],\n        roomPushRules?.map((rule) => rule.rule_id) || [],\n    );\n\n    return [...added, ...removed];\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021, 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { throttle } from \"lodash\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { NotificationLevel } from \"./NotificationLevel\";\nimport { arrayDiff } from \"../../utils/arrays\";\nimport { type RoomNotificationState } from \"./RoomNotificationState\";\nimport { NotificationState, NotificationStateEvents } from \"./NotificationState\";\nimport { DefaultTagID } from \"../room-list/models\";\nimport RoomListStore from \"../room-list/RoomListStore\";\nimport { RoomNotificationStateStore } from \"./RoomNotificationStateStore\";\n\nexport class SpaceNotificationState extends NotificationState {\n    public rooms: Room[] = []; // exposed only for tests\n    private states: { [spaceId: string]: RoomNotificationState } = {};\n\n    public constructor() {\n        super();\n    }\n\n    public get symbol(): string | null {\n        return this._level === NotificationLevel.Unsent ? \"!\" : null;\n    }\n\n    public setRooms(rooms: Room[]): void {\n        const oldRooms = this.rooms;\n        const diff = arrayDiff(oldRooms, rooms);\n        this.rooms = rooms;\n        for (const oldRoom of diff.removed) {\n            const state = this.states[oldRoom.roomId];\n            if (!state) continue; // We likely just didn't have a badge (race condition)\n            delete this.states[oldRoom.roomId];\n            state.off(NotificationStateEvents.Update, this.onRoomNotificationStateUpdate);\n        }\n        for (const newRoom of diff.added) {\n            const state = RoomNotificationStateStore.instance.getRoomState(newRoom);\n            state.on(NotificationStateEvents.Update, this.onRoomNotificationStateUpdate);\n            this.states[newRoom.roomId] = state;\n        }\n\n        this.calculateTotalState();\n    }\n\n    public getFirstRoomWithNotifications(): string | undefined {\n        return Object.values(this.states).find((state) => state.level >= this.level)?.room.roomId;\n    }\n\n    public destroy(): void {\n        super.destroy();\n        for (const state of Object.values(this.states)) {\n            state.off(NotificationStateEvents.Update, this.onRoomNotificationStateUpdate);\n        }\n        this.states = {};\n    }\n\n    private onRoomNotificationStateUpdate = (): void => {\n        this.calculateTotalState();\n    };\n\n    private calculateTotalState = throttle(\n        (): void => {\n            const snapshot = this.snapshot();\n\n            this._count = 0;\n            this._level = NotificationLevel.None;\n            for (const [roomId, state] of Object.entries(this.states)) {\n                const room = this.rooms.find((r) => r.roomId === roomId);\n                const roomTags = room ? RoomListStore.instance.getTagsForRoom(room) : [];\n\n                // We ignore unreads in LowPriority rooms, see https://github.com/vector-im/element-web/issues/16836\n                if (roomTags.includes(DefaultTagID.LowPriority) && state.level === NotificationLevel.Activity) continue;\n\n                this._count += state.count;\n                this._level = Math.max(this.level, state.level);\n            }\n\n            // finally, publish an update if needed\n            this.emitIfUpdated(snapshot);\n        },\n        100,\n        { leading: false, trailing: true },\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { alphabetPad, baseToString, stringToBase, DEFAULT_ALPHABET } from \"matrix-js-sdk/src/utils\";\n\nimport { moveElement } from \"./arrays\";\n\nexport function midPointsBetweenStrings(\n    a: string,\n    b: string,\n    count: number,\n    maxLen: number,\n    alphabet = DEFAULT_ALPHABET,\n): string[] {\n    const padN = Math.min(Math.max(a.length, b.length), maxLen);\n    const padA = alphabetPad(a, padN, alphabet);\n    const padB = alphabetPad(b, padN, alphabet);\n    const baseA = stringToBase(padA, alphabet);\n    const baseB = stringToBase(padB, alphabet);\n\n    if (baseB - baseA - BigInt(1) < count) {\n        if (padN < maxLen) {\n            // this recurses once at most due to the new limit of n+1\n            return midPointsBetweenStrings(\n                alphabetPad(padA, padN + 1, alphabet),\n                alphabetPad(padB, padN + 1, alphabet),\n                count,\n                padN + 1,\n                alphabet,\n            );\n        }\n        return [];\n    }\n\n    const step = (baseB - baseA) / BigInt(count + 1);\n    const start = BigInt(baseA + step);\n    return Array(count)\n        .fill(undefined)\n        .map((_, i) => baseToString(start + BigInt(i) * step, alphabet));\n}\n\ninterface IEntry {\n    index: number;\n    order?: string;\n}\n\nexport const reorderLexicographically = (\n    orders: Array<string | undefined>,\n    fromIndex: number,\n    toIndex: number,\n    maxLen = 50,\n): Required<IEntry>[] => {\n    // sanity check inputs\n    if (fromIndex < 0 || toIndex < 0 || fromIndex > orders.length || toIndex > orders.length || fromIndex === toIndex) {\n        return [];\n    }\n\n    // zip orders with their indices to simplify later index wrangling\n    const ordersWithIndices: IEntry[] = orders.map((order, index) => ({ index, order }));\n    // apply the fundamental order update to the zipped array\n    const newOrder = moveElement(ordersWithIndices, fromIndex, toIndex);\n\n    // check if we have to fill undefined orders to complete placement\n    const orderToLeftUndefined = newOrder[toIndex - 1]?.order === undefined;\n\n    let leftBoundIdx = toIndex;\n    let rightBoundIdx = toIndex;\n\n    let canMoveLeft = true;\n    const nextBase =\n        newOrder[toIndex + 1]?.order !== undefined\n            ? stringToBase(newOrder[toIndex + 1].order!)\n            : BigInt(Number.MAX_VALUE);\n\n    // check how far left we would have to mutate to fit in that direction\n    for (let i = toIndex - 1, j = 1; i >= 0; i--, j++) {\n        if (newOrder[i]?.order !== undefined && nextBase - stringToBase(newOrder[i].order!) > j) break;\n        leftBoundIdx = i;\n    }\n\n    // verify the left move would be sufficient\n    const firstOrderBase = newOrder[0].order === undefined ? undefined : stringToBase(newOrder[0].order);\n    const bigToIndex = BigInt(toIndex);\n    if (\n        leftBoundIdx === 0 &&\n        firstOrderBase !== undefined &&\n        nextBase - firstOrderBase <= bigToIndex &&\n        firstOrderBase <= bigToIndex\n    ) {\n        canMoveLeft = false;\n    }\n\n    const canDisplaceRight = !orderToLeftUndefined;\n    let canMoveRight = canDisplaceRight;\n    if (canDisplaceRight) {\n        const prevBase =\n            newOrder[toIndex - 1]?.order !== undefined\n                ? stringToBase(newOrder[toIndex - 1].order!)\n                : BigInt(Number.MIN_VALUE);\n\n        // check how far right we would have to mutate to fit in that direction\n        for (let i = toIndex + 1, j = 1; i < newOrder.length; i++, j++) {\n            if (newOrder[i]?.order === undefined || stringToBase(newOrder[i].order!) - prevBase > j) break;\n            rightBoundIdx = i;\n        }\n\n        // verify the right move would be sufficient\n        if (\n            rightBoundIdx === newOrder.length - 1 &&\n            (newOrder[rightBoundIdx]?.order ? stringToBase(newOrder[rightBoundIdx].order!) : BigInt(Number.MAX_VALUE)) -\n                prevBase <=\n                rightBoundIdx - toIndex\n        ) {\n            canMoveRight = false;\n        }\n    }\n\n    // pick the cheaper direction\n    const leftDiff = canMoveLeft ? toIndex - leftBoundIdx : Number.MAX_SAFE_INTEGER;\n    const rightDiff = canMoveRight ? rightBoundIdx - toIndex : Number.MAX_SAFE_INTEGER;\n    if (orderToLeftUndefined || leftDiff < rightDiff) {\n        rightBoundIdx = toIndex;\n    } else {\n        leftBoundIdx = toIndex;\n    }\n\n    const prevOrder = newOrder[leftBoundIdx - 1]?.order ?? \"\";\n    const nextOrder =\n        newOrder[rightBoundIdx + 1]?.order ??\n        DEFAULT_ALPHABET.charAt(DEFAULT_ALPHABET.length - 1).repeat(prevOrder.length || 1);\n\n    const changes = midPointsBetweenStrings(prevOrder, nextOrder, 1 + rightBoundIdx - leftBoundIdx, maxLen);\n\n    return changes.map((order, i) => ({\n        index: newOrder[leftBoundIdx + i].index,\n        order,\n    }));\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type SpaceKey } from \".\";\n\nexport type SpaceEntityMap = Map<SpaceKey, Set<string>>;\nexport type SpaceDescendantMap = Map<SpaceKey, Set<SpaceKey>>;\n\nconst traverseSpaceDescendants = (\n    spaceDescendantMap: SpaceDescendantMap,\n    spaceId: SpaceKey,\n    flatSpace = new Set<SpaceKey>(),\n): Set<SpaceKey> => {\n    flatSpace.add(spaceId);\n    const descendentSpaces = spaceDescendantMap.get(spaceId);\n    descendentSpaces?.forEach((descendantSpaceId) => {\n        if (!flatSpace.has(descendantSpaceId)) {\n            traverseSpaceDescendants(spaceDescendantMap, descendantSpaceId, flatSpace);\n        }\n    });\n\n    return flatSpace;\n};\n\n/**\n * Helper function to traverse space hierarchy and flatten\n * @param spaceEntityMap ie map of rooms or dm userIds\n * @param spaceDescendantMap map of spaces and their children\n * @returns set of all rooms\n */\nexport const flattenSpaceHierarchy = (\n    spaceEntityMap: SpaceEntityMap,\n    spaceDescendantMap: SpaceDescendantMap,\n    spaceId: SpaceKey,\n): Set<string> => {\n    const flattenedSpaceIds = traverseSpaceDescendants(spaceDescendantMap, spaceId);\n    const flattenedRooms = new Set<string>();\n\n    flattenedSpaceIds.forEach((id) => {\n        const roomIds = spaceEntityMap.get(id);\n        roomIds?.forEach(flattenedRooms.add, flattenedRooms);\n    });\n\n    return flattenedRooms;\n};\n\nexport const flattenSpaceHierarchyWithCache =\n    (cache: SpaceEntityMap) =>\n    (\n        spaceEntityMap: SpaceEntityMap,\n        spaceDescendantMap: SpaceDescendantMap,\n        spaceId: SpaceKey,\n        useCache = true,\n    ): Set<string> => {\n        if (useCache && cache.has(spaceId)) {\n            return cache.get(spaceId)!;\n        }\n        const result = flattenSpaceHierarchy(spaceEntityMap, spaceDescendantMap, spaceId);\n        cache.set(spaceId, result);\n\n        return result;\n    };\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021, 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ListIteratee, type Many, sortBy } from \"lodash\";\nimport {\n    EventType,\n    RoomType,\n    type Room,\n    RoomEvent,\n    type RoomMember,\n    RoomStateEvent,\n    type MatrixEvent,\n    ClientEvent,\n    type ISendEventResponse,\n    type EmptyObject,\n} from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { AsyncStoreWithClient } from \"../AsyncStoreWithClient\";\nimport defaultDispatcher from \"../../dispatcher/dispatcher\";\nimport RoomListStore from \"../room-list/RoomListStore\";\nimport SettingsStore from \"../../settings/SettingsStore\";\nimport DMRoomMap from \"../../utils/DMRoomMap\";\nimport { SpaceNotificationState } from \"../notifications/SpaceNotificationState\";\nimport { RoomNotificationStateStore } from \"../notifications/RoomNotificationStateStore\";\nimport { DefaultTagID } from \"../room-list/models\";\nimport { EnhancedMap, mapDiff } from \"../../utils/maps\";\nimport { setDiff, setHasDiff } from \"../../utils/sets\";\nimport { Action } from \"../../dispatcher/actions\";\nimport { arrayHasDiff, arrayHasOrderChange, filterBoolean } from \"../../utils/arrays\";\nimport { reorderLexicographically } from \"../../utils/stringOrderField\";\nimport { TAG_ORDER } from \"../../components/views/rooms/LegacyRoomList\";\nimport { type SettingUpdatedPayload } from \"../../dispatcher/payloads/SettingUpdatedPayload\";\nimport {\n    isMetaSpace,\n    type ISuggestedRoom,\n    MetaSpace,\n    type SpaceKey,\n    UPDATE_HOME_BEHAVIOUR,\n    UPDATE_INVITED_SPACES,\n    UPDATE_SELECTED_SPACE,\n    UPDATE_SUGGESTED_ROOMS,\n    UPDATE_TOP_LEVEL_SPACES,\n} from \".\";\nimport { getCachedRoomIdForAlias } from \"../../RoomAliasCache\";\nimport { EffectiveMembership, getEffectiveMembership } from \"../../utils/membership\";\nimport {\n    flattenSpaceHierarchyWithCache,\n    type SpaceEntityMap,\n    type SpaceDescendantMap,\n    flattenSpaceHierarchy,\n} from \"./flattenSpaceHierarchy\";\nimport { PosthogAnalytics } from \"../../PosthogAnalytics\";\nimport { type ViewRoomPayload } from \"../../dispatcher/payloads/ViewRoomPayload\";\nimport { type ViewHomePagePayload } from \"../../dispatcher/payloads/ViewHomePagePayload\";\nimport { type SwitchSpacePayload } from \"../../dispatcher/payloads/SwitchSpacePayload\";\nimport { type AfterLeaveRoomPayload } from \"../../dispatcher/payloads/AfterLeaveRoomPayload\";\nimport { SdkContextClass } from \"../../contexts/SDKContext\";\nimport { ModuleApi } from \"../../modules/Api.ts\";\n\nconst ACTIVE_SPACE_LS_KEY = \"mx_active_space\";\n\nconst metaSpaceOrder: MetaSpace[] = [\n    MetaSpace.Home,\n    MetaSpace.Favourites,\n    MetaSpace.People,\n    MetaSpace.Orphans,\n    MetaSpace.VideoRooms,\n];\n\nconst MAX_SUGGESTED_ROOMS = 20;\n\nconst getSpaceContextKey = (space: SpaceKey): string => `mx_space_context_${space}`;\n\nconst partitionSpacesAndRooms = (arr: Room[]): [Room[], Room[]] => {\n    // [spaces, rooms]\n    return arr.reduce<[Room[], Room[]]>(\n        (result, room: Room) => {\n            result[room.isSpaceRoom() ? 0 : 1].push(room);\n            return result;\n        },\n        [[], []],\n    );\n};\n\nconst validOrder = (order?: string): string | undefined => {\n    if (\n        typeof order === \"string\" &&\n        order.length <= 50 &&\n        Array.from(order).every((c: string) => {\n            const charCode = c.charCodeAt(0);\n            return charCode >= 0x20 && charCode <= 0x7e;\n        })\n    ) {\n        return order;\n    }\n};\n\n// For sorting space children using a validated `order`, `origin_server_ts`, `room_id`\nexport const getChildOrder = (\n    order: string | undefined,\n    ts: number,\n    roomId: string,\n): Array<Many<ListIteratee<unknown>>> => {\n    return [validOrder(order) ?? NaN, ts, roomId]; // NaN has lodash sort it at the end in asc\n};\n\ntype SpaceStoreActions =\n    | SettingUpdatedPayload\n    | ViewRoomPayload\n    | ViewHomePagePayload\n    | SwitchSpacePayload\n    | AfterLeaveRoomPayload;\n\nexport class SpaceStoreClass extends AsyncStoreWithClient<EmptyObject> {\n    // The spaces representing the roots of the various tree-like hierarchies\n    private rootSpaces: Room[] = [];\n    // Map from room/space ID to set of spaces which list it as a child\n    private parentMap = new EnhancedMap<string, Set<string>>();\n    // Map from SpaceKey to SpaceNotificationState instance representing that space\n    private notificationStateMap = new Map<SpaceKey, SpaceNotificationState>();\n    // Map from SpaceKey to Set of room IDs that are direct descendants of that space\n    private roomIdsBySpace: SpaceEntityMap = new Map<SpaceKey, Set<string>>(); // won't contain MetaSpace.People\n    // Map from space id to Set of space keys that are direct descendants of that space\n    // meta spaces do not have descendants\n    private childSpacesBySpace: SpaceDescendantMap = new Map<Room[\"roomId\"], Set<Room[\"roomId\"]>>();\n    // Map from space id to Set of user IDs that are direct descendants of that space\n    private userIdsBySpace: SpaceEntityMap = new Map<Room[\"roomId\"], Set<string>>();\n    // cache that stores the aggregated lists of roomIdsBySpace and userIdsBySpace\n    // cleared on changes\n    private _aggregatedSpaceCache = {\n        roomIdsBySpace: new Map<SpaceKey, Set<string>>(),\n        userIdsBySpace: new Map<Room[\"roomId\"], Set<string>>(),\n    };\n    // The space currently selected in the Space Panel\n    private _activeSpace: SpaceKey = MetaSpace.Home; // set properly by onReady\n    private _suggestedRooms: ISuggestedRoom[] = [];\n    private _invitedSpaces = new Set<Room>();\n    private spaceOrderLocalEchoMap = new Map<string, string | undefined>();\n    // The following properties are set by onReady as they live in account_data\n    private _allRoomsInHome = false;\n    private _enabledMetaSpaces: MetaSpace[] = [];\n    /** Whether the feature flag is set for MSC3946 */\n    private _msc3946ProcessDynamicPredecessor: boolean = SettingsStore.getValue(\"feature_dynamic_room_predecessors\");\n    private _storeReadyDeferred = Promise.withResolvers<void>();\n\n    public constructor() {\n        super(defaultDispatcher, {});\n\n        SettingsStore.monitorSetting(\"Spaces.allRoomsInHome\", null);\n        SettingsStore.monitorSetting(\"Spaces.enabledMetaSpaces\", null);\n        SettingsStore.monitorSetting(\"Spaces.showPeopleInSpace\", null);\n        SettingsStore.monitorSetting(\"feature_dynamic_room_predecessors\", null);\n    }\n\n    /**\n     * A promise that resolves when the space store is ready.\n     * This happens after an initial hierarchy of spaces and rooms has been computed.\n     */\n    public get storeReadyPromise(): Promise<void> {\n        return this._storeReadyDeferred.promise;\n    }\n\n    /**\n     * Get the order of meta spaces to display in the space panel.\n     *\n     * This accessor should be removed when the \"feature_new_room_list\" labs flag is removed.\n     * \"People\" and \"Favourites\" will be removed from the \"metaSpaceOrder\" array and this filter will no longer be needed.\n     * @private\n     */\n    private get metaSpaceOrder(): MetaSpace[] {\n        if (!SettingsStore.getValue(\"feature_new_room_list\")) return metaSpaceOrder;\n\n        // People and Favourites are not shown when the new room list is enabled\n        return metaSpaceOrder.filter((space) => space !== MetaSpace.People && space !== MetaSpace.Favourites);\n    }\n\n    public get invitedSpaces(): Room[] {\n        return Array.from(this._invitedSpaces);\n    }\n\n    public get enabledMetaSpaces(): MetaSpace[] {\n        return this._enabledMetaSpaces;\n    }\n\n    public get spacePanelSpaces(): Room[] {\n        return this.rootSpaces;\n    }\n\n    public get activeSpace(): SpaceKey {\n        return this._activeSpace;\n    }\n\n    public get activeSpaceRoom(): Room | null {\n        if (isMetaSpace(this._activeSpace)) return null;\n        return this.matrixClient?.getRoom(this._activeSpace) ?? null;\n    }\n\n    public get suggestedRooms(): ISuggestedRoom[] {\n        return this._suggestedRooms;\n    }\n\n    public get allRoomsInHome(): boolean {\n        return this._allRoomsInHome;\n    }\n\n    public setActiveRoomInSpace(space: SpaceKey): void {\n        if (!isMetaSpace(space) && !this.matrixClient?.getRoom(space)?.isSpaceRoom()) return;\n        if (space !== this.activeSpace) this.setActiveSpace(space, false);\n\n        let roomId: string | undefined;\n        if (space === MetaSpace.Home && this.allRoomsInHome) {\n            const hasMentions = RoomNotificationStateStore.instance.globalState.hasMentions;\n            const lists = RoomListStore.instance.orderedLists;\n            tagLoop: for (let i = 0; i < TAG_ORDER.length; i++) {\n                const t = TAG_ORDER[i];\n                if (!lists[t]) continue;\n                for (const room of lists[t]) {\n                    const state = RoomNotificationStateStore.instance.getRoomState(room);\n                    if (hasMentions ? state.hasMentions : state.isUnread) {\n                        roomId = room.roomId;\n                        break tagLoop;\n                    }\n                }\n            }\n        } else {\n            roomId = this.getNotificationState(space).getFirstRoomWithNotifications();\n        }\n\n        if (!!roomId) {\n            defaultDispatcher.dispatch<ViewRoomPayload>({\n                action: Action.ViewRoom,\n                room_id: roomId,\n                context_switch: true,\n                metricsTrigger: \"WebSpacePanelNotificationBadge\",\n            });\n        }\n    }\n\n    /**\n     * Sets the active space, updates room list filters,\n     * optionally switches the user's room back to where they were when they last viewed that space.\n     * @param space which space to switch to.\n     * @param contextSwitch whether to switch the user's context,\n     * should not be done when the space switch is done implicitly due to another event like switching room.\n     */\n    public setActiveSpace(space: SpaceKey, contextSwitch = true): void {\n        if (!space || !this.matrixClient || space === this.activeSpace) return;\n\n        let cliSpace: Room | null = null;\n        if (ModuleApi.instance.extras.spacePanelItems.has(space)) {\n            // it's a \"space\" provided by a module: that's good enough\n        } else if (!isMetaSpace(space)) {\n            cliSpace = this.matrixClient.getRoom(space);\n            if (!cliSpace?.isSpaceRoom()) return;\n        } else if (!this.enabledMetaSpaces.includes(space)) {\n            return;\n        }\n\n        window.localStorage.setItem(ACTIVE_SPACE_LS_KEY, (this._activeSpace = space)); // Update & persist selected space\n\n        if (contextSwitch) {\n            // view last selected room from space\n            const roomId = this.getLastSelectedRoomIdForSpace(space);\n\n            // if the space being selected is an invite then always view that invite\n            // else if the last viewed room in this space is joined then view that\n            // else view space home or home depending on what is being clicked on\n            if (\n                roomId &&\n                cliSpace?.getMyMembership() !== KnownMembership.Invite &&\n                this.matrixClient.getRoom(roomId)?.getMyMembership() === KnownMembership.Join &&\n                this.isRoomInSpace(space, roomId)\n            ) {\n                defaultDispatcher.dispatch<ViewRoomPayload>({\n                    action: Action.ViewRoom,\n                    room_id: roomId,\n                    context_switch: true,\n                    metricsTrigger: \"WebSpaceContextSwitch\",\n                });\n            } else if (cliSpace) {\n                defaultDispatcher.dispatch<ViewRoomPayload>({\n                    action: Action.ViewRoom,\n                    room_id: space,\n                    context_switch: true,\n                    metricsTrigger: \"WebSpaceContextSwitch\",\n                });\n            } else if (ModuleApi.instance.extras.spacePanelItems.has(space)) {\n                // module will handle this\n            } else {\n                defaultDispatcher.dispatch<ViewHomePagePayload>({\n                    action: Action.ViewHomePage,\n                    context_switch: true,\n                });\n            }\n        }\n\n        this.emit(UPDATE_SELECTED_SPACE, this.activeSpace);\n        this.emit(UPDATE_SUGGESTED_ROOMS, (this._suggestedRooms = []));\n\n        if (cliSpace) {\n            this.loadSuggestedRooms(cliSpace);\n\n            // Load all members for the selected space and its subspaces,\n            // so we can correctly show DMs we have with members of this space.\n            SpaceStore.instance.traverseSpace(\n                space,\n                (roomId) => {\n                    this.matrixClient?.getRoom(roomId)?.loadMembersIfNeeded();\n                },\n                false,\n            );\n        }\n    }\n\n    /**\n     * Returns the room-id of the last active room in a given space.\n     * This is the room that would be opened when you switch to a given space.\n     * @param space The space you're interested in.\n     * @returns room-id of the room or null if there's no last active room.\n     */\n    public getLastSelectedRoomIdForSpace(space: SpaceKey): string | null {\n        const roomId = window.localStorage.getItem(getSpaceContextKey(space));\n        return roomId;\n    }\n\n    private async loadSuggestedRooms(space: Room): Promise<void> {\n        const suggestedRooms = await this.fetchSuggestedRooms(space);\n        if (this._activeSpace === space.roomId) {\n            this._suggestedRooms = suggestedRooms;\n            this.emit(UPDATE_SUGGESTED_ROOMS, this._suggestedRooms);\n        }\n    }\n\n    public fetchSuggestedRooms = async (space: Room, limit = MAX_SUGGESTED_ROOMS): Promise<ISuggestedRoom[]> => {\n        try {\n            const { rooms } = await this.matrixClient!.getRoomHierarchy(space.roomId, limit, 1, true);\n\n            const viaMap = new EnhancedMap<string, Set<string>>();\n            rooms.forEach((room) => {\n                room.children_state.forEach((ev) => {\n                    if (ev.type === EventType.SpaceChild && ev.content.via?.length) {\n                        ev.content.via.forEach((via) => {\n                            viaMap.getOrCreate(ev.state_key, new Set()).add(via);\n                        });\n                    }\n                });\n            });\n\n            return rooms\n                .filter((roomInfo) => {\n                    return (\n                        roomInfo.room_type !== RoomType.Space &&\n                        this.matrixClient?.getRoom(roomInfo.room_id)?.getMyMembership() !== KnownMembership.Join\n                    );\n                })\n                .map((roomInfo) => ({\n                    ...roomInfo,\n                    viaServers: Array.from(viaMap.get(roomInfo.room_id) || []),\n                }));\n        } catch (e) {\n            logger.error(e);\n        }\n        return [];\n    };\n\n    public addRoomToSpace(space: Room, roomId: string, via: string[], suggested = false): Promise<ISendEventResponse> {\n        return this.matrixClient!.sendStateEvent(\n            space.roomId,\n            EventType.SpaceChild,\n            {\n                via,\n                suggested,\n            },\n            roomId,\n        );\n    }\n\n    public getChildren(spaceId: string): Room[] {\n        const room = this.matrixClient?.getRoom(spaceId);\n        const childEvents = room?.currentState\n            .getStateEvents(EventType.SpaceChild)\n            .filter((ev) => ev.getContent()?.via);\n        return (\n            sortBy(childEvents, (ev) => {\n                return getChildOrder(ev.getContent().order, ev.getTs(), ev.getStateKey()!);\n            })\n                .map((ev) => {\n                    const history = this.matrixClient!.getRoomUpgradeHistory(\n                        ev.getStateKey()!,\n                        true,\n                        this._msc3946ProcessDynamicPredecessor,\n                    );\n                    return history[history.length - 1];\n                })\n                .filter((room) => {\n                    return (\n                        room?.getMyMembership() === KnownMembership.Join ||\n                        room?.getMyMembership() === KnownMembership.Invite\n                    );\n                }) || []\n        );\n    }\n\n    public getChildRooms(spaceId: string): Room[] {\n        return this.getChildren(spaceId).filter((r) => !r.isSpaceRoom());\n    }\n\n    public getChildSpaces(spaceId: string): Room[] {\n        // don't show invited subspaces as they surface at the top level for better visibility\n        return this.getChildren(spaceId).filter((r) => r.isSpaceRoom() && r.getMyMembership() === KnownMembership.Join);\n    }\n\n    public getParents(roomId: string, canonicalOnly = false): Room[] {\n        if (!this.matrixClient) return [];\n        const userId = this.matrixClient.getSafeUserId();\n        const room = this.matrixClient.getRoom(roomId);\n        const events = room?.currentState.getStateEvents(EventType.SpaceParent) ?? [];\n        return filterBoolean(\n            events.map((ev) => {\n                const content = ev.getContent();\n                if (!Array.isArray(content.via) || (canonicalOnly && !content.canonical)) {\n                    return; // skip\n                }\n\n                // only respect the relationship if the sender has sufficient permissions in the parent to set\n                // child relations, as per MSC1772.\n                // https://github.com/matrix-org/matrix-doc/blob/main/proposals/1772-groups-as-rooms.md#relationship-between-rooms-and-spaces\n                const parent = this.matrixClient?.getRoom(ev.getStateKey());\n                const relation = parent?.currentState.getStateEvents(EventType.SpaceChild, roomId);\n                if (\n                    !parent?.currentState.maySendStateEvent(EventType.SpaceChild, userId) ||\n                    // also skip this relation if the parent had this child added but then since removed it\n                    (relation && !Array.isArray(relation.getContent().via))\n                ) {\n                    return; // skip\n                }\n\n                return parent;\n            }),\n        );\n    }\n\n    public getCanonicalParent(roomId: string): Room | null {\n        const parents = this.getParents(roomId, true);\n        return sortBy(parents, (r) => r.roomId)?.[0] || null;\n    }\n\n    public getKnownParents(roomId: string, includeAncestors?: boolean): Set<string> {\n        if (includeAncestors) {\n            return flattenSpaceHierarchy(this.parentMap, this.parentMap, roomId);\n        }\n        return this.parentMap.get(roomId) || new Set();\n    }\n\n    public isRoomInSpace(space: SpaceKey, roomId: string, includeDescendantSpaces = true): boolean {\n        if (space === MetaSpace.Home && this.allRoomsInHome) {\n            return true;\n        }\n        if (space === MetaSpace.VideoRooms) {\n            return !!this.matrixClient?.getRoom(roomId)?.isCallRoom();\n        }\n        if (this.getSpaceFilteredRoomIds(space, includeDescendantSpaces)?.has(roomId)) {\n            return true;\n        }\n\n        const dmPartner = DMRoomMap.shared().getUserIdForRoomId(roomId);\n        if (!dmPartner) {\n            return false;\n        }\n        // beyond this point we know this is a DM\n\n        if (space === MetaSpace.Home || space === MetaSpace.People) {\n            // these spaces contain all DMs\n            return true;\n        }\n\n        if (\n            !isMetaSpace(space) &&\n            this.getSpaceFilteredUserIds(space, includeDescendantSpaces)?.has(dmPartner) &&\n            SettingsStore.getValue(\"Spaces.showPeopleInSpace\", space)\n        ) {\n            return true;\n        }\n\n        return false;\n    }\n\n    // get all rooms in a space\n    // including descendant spaces\n    public getSpaceFilteredRoomIds = (\n        space: SpaceKey,\n        includeDescendantSpaces = true,\n        useCache = true,\n    ): Set<string> => {\n        if (space === MetaSpace.Home && this.allRoomsInHome) {\n            return new Set(\n                this.matrixClient!.getVisibleRooms(this._msc3946ProcessDynamicPredecessor).map((r) => r.roomId),\n            );\n        }\n\n        // meta spaces never have descendants\n        // and the aggregate cache is not managed for meta spaces\n        if (!includeDescendantSpaces || isMetaSpace(space)) {\n            return this.roomIdsBySpace.get(space) || new Set();\n        }\n\n        return this.getAggregatedRoomIdsBySpace(this.roomIdsBySpace, this.childSpacesBySpace, space, useCache);\n    };\n\n    public getSpaceFilteredUserIds = (\n        space: SpaceKey,\n        includeDescendantSpaces = true,\n        useCache = true,\n    ): Set<string> | undefined => {\n        if (space === MetaSpace.Home && this.allRoomsInHome) {\n            return undefined;\n        }\n        if (isMetaSpace(space)) {\n            return undefined;\n        }\n\n        // meta spaces never have descendants\n        // and the aggregate cache is not managed for meta spaces\n        if (!includeDescendantSpaces || isMetaSpace(space)) {\n            return this.userIdsBySpace.get(space) || new Set();\n        }\n\n        return this.getAggregatedUserIdsBySpace(this.userIdsBySpace, this.childSpacesBySpace, space, useCache);\n    };\n\n    private getAggregatedRoomIdsBySpace = flattenSpaceHierarchyWithCache(this._aggregatedSpaceCache.roomIdsBySpace);\n    private getAggregatedUserIdsBySpace = flattenSpaceHierarchyWithCache(this._aggregatedSpaceCache.userIdsBySpace);\n\n    private markTreeChildren = (rootSpace: Room, unseen: Set<Room>): void => {\n        const stack = [rootSpace];\n        while (stack.length) {\n            const space = stack.pop()!;\n            unseen.delete(space);\n            this.getChildSpaces(space.roomId).forEach((space) => {\n                if (unseen.has(space)) {\n                    stack.push(space);\n                }\n            });\n        }\n    };\n\n    private findRootSpaces = (joinedSpaces: Room[]): Room[] => {\n        // exclude invited spaces from unseenChildren as they will be forcibly shown at the top level of the treeview\n        const unseenSpaces = new Set(joinedSpaces);\n\n        joinedSpaces.forEach((space) => {\n            this.getChildSpaces(space.roomId).forEach((subspace) => {\n                unseenSpaces.delete(subspace);\n            });\n        });\n\n        // Consider any spaces remaining in unseenSpaces as root,\n        // given they are not children of any known spaces.\n        // The hierarchy from these roots may not yet be exhaustive due to the possibility of full-cycles.\n        const rootSpaces = Array.from(unseenSpaces);\n\n        // Next we need to determine the roots of any remaining full-cycles.\n        // We sort spaces by room ID to force the cycle breaking to be deterministic.\n        const detachedNodes = new Set<Room>(sortBy(joinedSpaces, (space) => space.roomId));\n\n        // Mark any nodes which are children of our existing root spaces as attached.\n        rootSpaces.forEach((rootSpace) => {\n            this.markTreeChildren(rootSpace, detachedNodes);\n        });\n\n        // Handle spaces forming fully cyclical relationships.\n        // In order, assume each remaining detachedNode is a root unless it has already\n        // been claimed as the child of prior detached node.\n        // Work from a copy of the detachedNodes set as it will be mutated as part of this operation.\n        // TODO consider sorting by number of in-refs to favour nodes with fewer parents.\n        Array.from(detachedNodes).forEach((detachedNode) => {\n            if (!detachedNodes.has(detachedNode)) return; // already claimed, skip\n            // declare this detached node a new root, find its children, without ever looping back to it\n            rootSpaces.push(detachedNode); // consider this node a new root space\n            this.markTreeChildren(detachedNode, detachedNodes); // declare this node and its children attached\n        });\n\n        return rootSpaces;\n    };\n\n    private rebuildSpaceHierarchy = (): void => {\n        if (!this.matrixClient) return;\n        const visibleSpaces = this.matrixClient\n            .getVisibleRooms(this._msc3946ProcessDynamicPredecessor)\n            .filter((r) => r.isSpaceRoom());\n        const [joinedSpaces, invitedSpaces] = visibleSpaces.reduce(\n            ([joined, invited], s) => {\n                switch (getEffectiveMembership(s.getMyMembership())) {\n                    case EffectiveMembership.Join:\n                        joined.push(s);\n                        break;\n                    case EffectiveMembership.Invite:\n                        invited.push(s);\n                        break;\n                }\n                return [joined, invited];\n            },\n            [[], []] as [Room[], Room[]],\n        );\n\n        const rootSpaces = this.findRootSpaces(joinedSpaces);\n        const oldRootSpaces = this.rootSpaces;\n        this.rootSpaces = this.sortRootSpaces(rootSpaces);\n\n        this.onRoomsUpdate();\n\n        if (arrayHasOrderChange(oldRootSpaces, this.rootSpaces)) {\n            this.emit(UPDATE_TOP_LEVEL_SPACES, this.spacePanelSpaces, this.enabledMetaSpaces);\n        }\n\n        const oldInvitedSpaces = this._invitedSpaces;\n        this._invitedSpaces = new Set(this.sortRootSpaces(invitedSpaces));\n        if (setHasDiff(oldInvitedSpaces, this._invitedSpaces)) {\n            this.emit(UPDATE_INVITED_SPACES, this.invitedSpaces);\n        }\n    };\n\n    private rebuildParentMap = (): void => {\n        if (!this.matrixClient) return;\n        const joinedSpaces = this.matrixClient.getVisibleRooms(this._msc3946ProcessDynamicPredecessor).filter((r) => {\n            return r.isSpaceRoom() && r.getMyMembership() === KnownMembership.Join;\n        });\n\n        this.parentMap = new EnhancedMap<string, Set<string>>();\n        joinedSpaces.forEach((space) => {\n            const children = this.getChildren(space.roomId);\n            children.forEach((child) => {\n                this.parentMap.getOrCreate(child.roomId, new Set()).add(space.roomId);\n            });\n        });\n\n        PosthogAnalytics.instance.setProperty(\"numSpaces\", joinedSpaces.length);\n    };\n\n    private rebuildHomeSpace = (): void => {\n        if (this.allRoomsInHome) {\n            // this is a special-case to not have to maintain a set of all rooms\n            this.roomIdsBySpace.delete(MetaSpace.Home);\n        } else {\n            const rooms = new Set(\n                this.matrixClient!.getVisibleRooms(this._msc3946ProcessDynamicPredecessor)\n                    .filter(this.showInHomeSpace)\n                    .map((r) => r.roomId),\n            );\n            this.roomIdsBySpace.set(MetaSpace.Home, rooms);\n        }\n\n        if (this.activeSpace === MetaSpace.Home) {\n            this.switchSpaceIfNeeded();\n        }\n    };\n\n    private rebuildMetaSpaces = (): void => {\n        if (!this.matrixClient) return;\n        const enabledMetaSpaces = new Set(this.enabledMetaSpaces);\n        const visibleRooms = this.matrixClient.getVisibleRooms(this._msc3946ProcessDynamicPredecessor);\n\n        if (enabledMetaSpaces.has(MetaSpace.Home)) {\n            this.rebuildHomeSpace();\n        } else {\n            this.roomIdsBySpace.delete(MetaSpace.Home);\n        }\n\n        if (enabledMetaSpaces.has(MetaSpace.Favourites)) {\n            const favourites = visibleRooms.filter((r) => r.tags[DefaultTagID.Favourite]);\n            this.roomIdsBySpace.set(MetaSpace.Favourites, new Set(favourites.map((r) => r.roomId)));\n        } else {\n            this.roomIdsBySpace.delete(MetaSpace.Favourites);\n        }\n\n        // The People metaspace doesn't need maintaining\n\n        // Populate the orphans space if the Home space is enabled as it is a superset of it.\n        // Home is effectively a super set of People + Orphans with the addition of having all invites too.\n        if (enabledMetaSpaces.has(MetaSpace.Orphans) || enabledMetaSpaces.has(MetaSpace.Home)) {\n            const orphans = visibleRooms.filter((r) => {\n                // filter out DMs and rooms with >0 parents\n                return !this.parentMap.get(r.roomId)?.size && !DMRoomMap.shared().getUserIdForRoomId(r.roomId);\n            });\n            this.roomIdsBySpace.set(MetaSpace.Orphans, new Set(orphans.map((r) => r.roomId)));\n        }\n\n        if (isMetaSpace(this.activeSpace)) {\n            this.switchSpaceIfNeeded();\n        }\n    };\n\n    private updateNotificationStates = (spaces?: SpaceKey[]): void => {\n        if (!this.matrixClient) return;\n        const enabledMetaSpaces = new Set(this.enabledMetaSpaces);\n        const visibleRooms = this.matrixClient.getVisibleRooms(this._msc3946ProcessDynamicPredecessor);\n\n        let dmBadgeSpace: MetaSpace | undefined;\n        // only show badges on dms on the most relevant space if such exists\n        if (enabledMetaSpaces.has(MetaSpace.People)) {\n            dmBadgeSpace = MetaSpace.People;\n        } else if (enabledMetaSpaces.has(MetaSpace.Home)) {\n            dmBadgeSpace = MetaSpace.Home;\n        }\n\n        if (!spaces) {\n            spaces = [...this.roomIdsBySpace.keys()];\n            if (dmBadgeSpace === MetaSpace.People) {\n                spaces.push(MetaSpace.People);\n            }\n            if (enabledMetaSpaces.has(MetaSpace.Home) && !this.allRoomsInHome) {\n                spaces.push(MetaSpace.Home);\n            }\n        }\n\n        spaces.forEach((s) => {\n            if (this.allRoomsInHome && s === MetaSpace.Home) return; // we'll be using the global notification state, skip\n\n            const flattenedRoomsForSpace = this.getSpaceFilteredRoomIds(s, true);\n\n            // Update NotificationStates\n            this.getNotificationState(s).setRooms(\n                visibleRooms.filter((room) => {\n                    if (s === MetaSpace.People) {\n                        return this.isRoomInSpace(MetaSpace.People, room.roomId);\n                    }\n\n                    if (room.isSpaceRoom() || !flattenedRoomsForSpace.has(room.roomId)) return false;\n\n                    if (dmBadgeSpace && DMRoomMap.shared().getUserIdForRoomId(room.roomId)) {\n                        return s === dmBadgeSpace;\n                    }\n\n                    return true;\n                }),\n            );\n        });\n\n        if (dmBadgeSpace !== MetaSpace.People) {\n            this.notificationStateMap.delete(MetaSpace.People);\n        }\n    };\n\n    private showInHomeSpace = (room: Room): boolean => {\n        if (this.allRoomsInHome) return true;\n        if (room.isSpaceRoom()) return false;\n        return (\n            !this.parentMap.get(room.roomId)?.size || // put all orphaned rooms in the Home Space\n            !!DMRoomMap.shared().getUserIdForRoomId(room.roomId) || // put all DMs in the Home Space\n            room.getMyMembership() === KnownMembership.Invite\n        ); // put all invites in the Home Space\n    };\n\n    private static isInSpace(member?: RoomMember | null): boolean {\n        return member?.membership === KnownMembership.Join || member?.membership === KnownMembership.Invite;\n    }\n\n    // Method for resolving the impact of a single user's membership change in the given Space and its hierarchy\n    private onMemberUpdate = (space: Room, userId: string): void => {\n        const inSpace = SpaceStoreClass.isInSpace(space.getMember(userId));\n\n        if (inSpace) {\n            this.userIdsBySpace.get(space.roomId)?.add(userId);\n        } else {\n            this.userIdsBySpace.get(space.roomId)?.delete(userId);\n        }\n\n        // bust cache\n        this._aggregatedSpaceCache.userIdsBySpace.clear();\n\n        const affectedParentSpaceIds = this.getKnownParents(space.roomId, true);\n        this.emit(space.roomId);\n        affectedParentSpaceIds.forEach((spaceId) => this.emit(spaceId));\n\n        if (!inSpace) {\n            // switch space if the DM is no longer considered part of the space\n            this.switchSpaceIfNeeded();\n        }\n    };\n\n    private onRoomsUpdate = (): void => {\n        if (!this.matrixClient) return;\n        const visibleRooms = this.matrixClient.getVisibleRooms(this._msc3946ProcessDynamicPredecessor);\n\n        const prevRoomsBySpace = this.roomIdsBySpace;\n        const prevUsersBySpace = this.userIdsBySpace;\n        const prevChildSpacesBySpace = this.childSpacesBySpace;\n\n        this.roomIdsBySpace = new Map();\n        this.userIdsBySpace = new Map();\n        this.childSpacesBySpace = new Map();\n\n        this.rebuildParentMap();\n        // mutates this.roomIdsBySpace\n        this.rebuildMetaSpaces();\n\n        const hiddenChildren = new EnhancedMap<string, Set<string>>();\n        visibleRooms.forEach((room) => {\n            if (!([KnownMembership.Join, KnownMembership.Invite] as Array<string>).includes(room.getMyMembership()))\n                return;\n            this.getParents(room.roomId).forEach((parent) => {\n                hiddenChildren.getOrCreate(parent.roomId, new Set()).add(room.roomId);\n            });\n        });\n\n        this.rootSpaces.forEach((s) => {\n            // traverse each space tree in DFS to build up the supersets as you go up,\n            // reusing results from like subtrees.\n            const traverseSpace = (\n                spaceId: string,\n                parentPath: Set<string>,\n            ): [Set<string>, Set<string>] | undefined => {\n                if (parentPath.has(spaceId)) return; // prevent cycles\n                // reuse existing results if multiple similar branches exist\n                if (this.roomIdsBySpace.has(spaceId) && this.userIdsBySpace.has(spaceId)) {\n                    return [this.roomIdsBySpace.get(spaceId)!, this.userIdsBySpace.get(spaceId)!];\n                }\n\n                const [childSpaces, childRooms] = partitionSpacesAndRooms(this.getChildren(spaceId));\n\n                this.childSpacesBySpace.set(spaceId, new Set(childSpaces.map((space) => space.roomId)));\n\n                const roomIds = new Set(childRooms.map((r) => r.roomId));\n\n                const space = this.matrixClient?.getRoom(spaceId);\n                const userIds = new Set(\n                    space\n                        ?.getMembers()\n                        .filter((m) => {\n                            return m.membership === KnownMembership.Join || m.membership === KnownMembership.Invite;\n                        })\n                        .map((m) => m.userId),\n                );\n\n                const newPath = new Set(parentPath).add(spaceId);\n\n                childSpaces.forEach((childSpace) => {\n                    traverseSpace(childSpace.roomId, newPath);\n                });\n                hiddenChildren.get(spaceId)?.forEach((roomId) => {\n                    roomIds.add(roomId);\n                });\n\n                // Expand room IDs to all known versions of the given rooms\n                const expandedRoomIds = new Set(\n                    Array.from(roomIds).flatMap((roomId) => {\n                        return this.matrixClient!.getRoomUpgradeHistory(\n                            roomId,\n                            true,\n                            this._msc3946ProcessDynamicPredecessor,\n                        ).map((r) => r.roomId);\n                    }),\n                );\n\n                this.roomIdsBySpace.set(spaceId, expandedRoomIds);\n\n                this.userIdsBySpace.set(spaceId, userIds);\n                return [expandedRoomIds, userIds];\n            };\n\n            traverseSpace(s.roomId, new Set());\n        });\n\n        const roomDiff = mapDiff(prevRoomsBySpace, this.roomIdsBySpace);\n        const userDiff = mapDiff(prevUsersBySpace, this.userIdsBySpace);\n        const spaceDiff = mapDiff(prevChildSpacesBySpace, this.childSpacesBySpace);\n        // filter out keys which changed by reference only by checking whether the sets differ\n        const roomsChanged = roomDiff.changed.filter((k) => {\n            return setHasDiff(prevRoomsBySpace.get(k)!, this.roomIdsBySpace.get(k)!);\n        });\n        const usersChanged = userDiff.changed.filter((k) => {\n            return setHasDiff(prevUsersBySpace.get(k)!, this.userIdsBySpace.get(k)!);\n        });\n        const spacesChanged = spaceDiff.changed.filter((k) => {\n            return setHasDiff(prevChildSpacesBySpace.get(k)!, this.childSpacesBySpace.get(k)!);\n        });\n\n        const changeSet = new Set([\n            ...roomDiff.added,\n            ...userDiff.added,\n            ...spaceDiff.added,\n            ...roomDiff.removed,\n            ...userDiff.removed,\n            ...spaceDiff.removed,\n            ...roomsChanged,\n            ...usersChanged,\n            ...spacesChanged,\n        ]);\n\n        const affectedParents = Array.from(changeSet).flatMap((changedId) => [\n            ...this.getKnownParents(changedId, true),\n        ]);\n        affectedParents.forEach((parentId) => changeSet.add(parentId));\n        // bust aggregate cache\n        this._aggregatedSpaceCache.roomIdsBySpace.clear();\n        this._aggregatedSpaceCache.userIdsBySpace.clear();\n\n        changeSet.forEach((k) => {\n            this.emit(k);\n        });\n\n        if (changeSet.has(this.activeSpace)) {\n            this.switchSpaceIfNeeded();\n        }\n\n        const notificationStatesToUpdate = [...changeSet];\n        // We update the People metaspace even if we didn't detect any changes\n        // as roomIdsBySpace does not pre-calculate it so we have to assume it could have changed\n        if (this.enabledMetaSpaces.includes(MetaSpace.People)) {\n            notificationStatesToUpdate.push(MetaSpace.People);\n        }\n        this.updateNotificationStates(notificationStatesToUpdate);\n    };\n\n    private switchSpaceIfNeeded = (roomId = SdkContextClass.instance.roomViewStore.getRoomId()): void => {\n        if (!roomId) return;\n        if (!this.isRoomInSpace(this.activeSpace, roomId) && !this.matrixClient?.getRoom(roomId)?.isSpaceRoom()) {\n            this.switchToRelatedSpace(roomId);\n        }\n    };\n\n    private switchToRelatedSpace = (roomId: string): void => {\n        if (this.suggestedRooms.find((r) => r.room_id === roomId)) return;\n\n        // try to find the canonical parent first\n        let parent: SpaceKey | undefined = this.getCanonicalParent(roomId)?.roomId;\n\n        // otherwise, try to find a root space which contains this room\n        if (!parent) {\n            parent = this.rootSpaces.find((s) => this.isRoomInSpace(s.roomId, roomId))?.roomId;\n        }\n\n        // otherwise, try to find a metaspace which contains this room\n        if (!parent) {\n            // search meta spaces in reverse as Home is the first and least specific one\n            parent = [...this.enabledMetaSpaces].reverse().find((s) => this.isRoomInSpace(s, roomId));\n        }\n\n        // don't trigger a context switch when we are switching a space to match the chosen room\n        if (parent) {\n            this.setActiveSpace(parent, false);\n        } else {\n            this.goToFirstSpace();\n        }\n    };\n\n    private onRoom = (room: Room, newMembership?: string, oldMembership?: string): void => {\n        const roomMembership = room.getMyMembership();\n        if (!roomMembership) {\n            // room is still being baked in the js-sdk, we'll process it at Room.myMembership instead\n            return;\n        }\n        const membership = newMembership || roomMembership;\n\n        if (!room.isSpaceRoom()) {\n            this.onRoomsUpdate();\n\n            if (membership === KnownMembership.Join) {\n                // the user just joined a room, remove it from the suggested list if it was there\n                const numSuggestedRooms = this._suggestedRooms.length;\n                this._suggestedRooms = this._suggestedRooms.filter((r) => r.room_id !== room.roomId);\n                if (numSuggestedRooms !== this._suggestedRooms.length) {\n                    this.emit(UPDATE_SUGGESTED_ROOMS, this._suggestedRooms);\n                    // If the suggested room was present in the list then we know we don't need to switch space\n                    return;\n                }\n\n                // if the room currently being viewed was just joined then switch to its related space\n                if (\n                    newMembership === KnownMembership.Join &&\n                    room.roomId === SdkContextClass.instance.roomViewStore.getRoomId()\n                ) {\n                    this.switchSpaceIfNeeded(room.roomId);\n                }\n            }\n            return;\n        }\n\n        // Space\n        if (membership === KnownMembership.Invite) {\n            const len = this._invitedSpaces.size;\n            this._invitedSpaces.add(room);\n            if (len !== this._invitedSpaces.size) {\n                this.emit(UPDATE_INVITED_SPACES, this.invitedSpaces);\n            }\n        } else if (oldMembership === KnownMembership.Invite && membership !== KnownMembership.Join) {\n            if (this._invitedSpaces.delete(room)) {\n                this.emit(UPDATE_INVITED_SPACES, this.invitedSpaces);\n            }\n        } else {\n            this.rebuildSpaceHierarchy();\n            // fire off updates to all parent listeners\n            this.parentMap.get(room.roomId)?.forEach((parentId) => {\n                this.emit(parentId);\n            });\n            this.emit(room.roomId);\n        }\n\n        if (membership === KnownMembership.Join && room.roomId === SdkContextClass.instance.roomViewStore.getRoomId()) {\n            // if the user was looking at the space and then joined: select that space\n            this.setActiveSpace(room.roomId, false);\n        } else if (membership === KnownMembership.Leave && room.roomId === this.activeSpace) {\n            // user's active space has gone away, go back to home\n            this.goToFirstSpace(true);\n        }\n    };\n\n    private notifyIfOrderChanged(): void {\n        const rootSpaces = this.sortRootSpaces(this.rootSpaces);\n        if (arrayHasOrderChange(this.rootSpaces, rootSpaces)) {\n            this.rootSpaces = rootSpaces;\n            this.emit(UPDATE_TOP_LEVEL_SPACES, this.spacePanelSpaces, this.enabledMetaSpaces);\n        }\n    }\n\n    private onRoomState = (ev: MatrixEvent): void => {\n        const room = this.matrixClient?.getRoom(ev.getRoomId());\n\n        if (!this.matrixClient || !room) return;\n\n        switch (ev.getType()) {\n            case EventType.SpaceChild: {\n                const target = this.matrixClient.getRoom(ev.getStateKey());\n\n                if (room.isSpaceRoom()) {\n                    if (target?.isSpaceRoom()) {\n                        this.rebuildSpaceHierarchy();\n                        this.emit(target.roomId);\n                    } else {\n                        this.onRoomsUpdate();\n                    }\n                    this.emit(room.roomId);\n                }\n\n                if (\n                    room.roomId === this.activeSpace && // current space\n                    target?.getMyMembership() !== KnownMembership.Join && // target not joined\n                    ev.getPrevContent().suggested !== ev.getContent().suggested // suggested flag changed\n                ) {\n                    this.loadSuggestedRooms(room);\n                }\n\n                break;\n            }\n\n            case EventType.SpaceParent:\n                // TODO rebuild the space parent and not the room - check permissions?\n                // TODO confirm this after implementing parenting behaviour\n                if (room.isSpaceRoom()) {\n                    this.rebuildSpaceHierarchy();\n                } else {\n                    this.onRoomsUpdate();\n                }\n                this.emit(room.roomId);\n                break;\n\n            case EventType.RoomPowerLevels:\n                if (room.isSpaceRoom()) {\n                    this.onRoomsUpdate();\n                }\n                break;\n            case EventType.RoomCreate:\n                // The room might become a video room. We need to tag it for that videoRooms space.\n                this.onRoomsUpdate();\n                break;\n        }\n    };\n\n    // listening for m.room.member events in onRoomState above doesn't work as the Member object isn't updated by then\n    private onRoomStateMembers = (ev: MatrixEvent): void => {\n        const room = this.matrixClient?.getRoom(ev.getRoomId());\n\n        const userId = ev.getStateKey()!;\n        if (\n            room?.isSpaceRoom() && // only consider space rooms\n            DMRoomMap.shared().getDMRoomsForUserId(userId).length > 0 && // only consider members we have a DM with\n            ev.getPrevContent().membership !== ev.getContent().membership // only consider when membership changes\n        ) {\n            this.onMemberUpdate(room, userId);\n        }\n    };\n\n    private onRoomAccountData = (ev: MatrixEvent, room: Room, lastEv?: MatrixEvent): void => {\n        if (room.isSpaceRoom() && ev.getType() === EventType.SpaceOrder) {\n            this.spaceOrderLocalEchoMap.delete(room.roomId); // clear any local echo\n            const order = ev.getContent()?.order;\n            const lastOrder = lastEv?.getContent()?.order;\n            if (order !== lastOrder) {\n                this.notifyIfOrderChanged();\n            }\n        } else if (ev.getType() === EventType.Tag) {\n            // If the room was in favourites and now isn't or the opposite then update its position in the trees\n            const oldTags = lastEv?.getContent()?.tags || {};\n            const newTags = ev.getContent()?.tags || {};\n            if (!!oldTags[DefaultTagID.Favourite] !== !!newTags[DefaultTagID.Favourite]) {\n                this.onRoomFavouriteChange(room);\n            }\n        }\n    };\n\n    private onRoomFavouriteChange(room: Room): void {\n        if (this.enabledMetaSpaces.includes(MetaSpace.Favourites)) {\n            if (room.tags[DefaultTagID.Favourite]) {\n                this.roomIdsBySpace.get(MetaSpace.Favourites)?.add(room.roomId);\n            } else {\n                this.roomIdsBySpace.get(MetaSpace.Favourites)?.delete(room.roomId);\n            }\n            this.emit(MetaSpace.Favourites);\n        }\n    }\n\n    private onRoomDmChange(room: Room, isDm: boolean): void {\n        const enabledMetaSpaces = new Set(this.enabledMetaSpaces);\n\n        if (!this.allRoomsInHome && enabledMetaSpaces.has(MetaSpace.Home)) {\n            const homeRooms = this.roomIdsBySpace.get(MetaSpace.Home);\n            if (this.showInHomeSpace(room)) {\n                homeRooms?.add(room.roomId);\n            } else if (!this.roomIdsBySpace.get(MetaSpace.Orphans)?.has(room.roomId)) {\n                this.roomIdsBySpace.get(MetaSpace.Home)?.delete(room.roomId);\n            }\n\n            this.emit(MetaSpace.Home);\n        }\n\n        if (enabledMetaSpaces.has(MetaSpace.People)) {\n            this.emit(MetaSpace.People);\n        }\n\n        if (enabledMetaSpaces.has(MetaSpace.Orphans) || enabledMetaSpaces.has(MetaSpace.Home)) {\n            if (isDm && this.roomIdsBySpace.get(MetaSpace.Orphans)?.delete(room.roomId)) {\n                this.emit(MetaSpace.Orphans);\n                this.emit(MetaSpace.Home);\n            }\n        }\n    }\n\n    private onAccountData = (ev: MatrixEvent, prevEv?: MatrixEvent): void => {\n        if (ev.getType() === EventType.Direct) {\n            const previousRooms = new Set(Object.values(prevEv?.getContent<Record<string, string[]>>() ?? {}).flat());\n            const currentRooms = new Set(Object.values(ev.getContent<Record<string, string[]>>()).flat());\n\n            const diff = setDiff(previousRooms, currentRooms);\n            [...diff.added, ...diff.removed].forEach((roomId) => {\n                const room = this.matrixClient?.getRoom(roomId);\n                if (room) {\n                    this.onRoomDmChange(room, currentRooms.has(roomId));\n                }\n            });\n\n            if (diff.removed.length > 0) {\n                this.switchSpaceIfNeeded();\n            }\n        }\n    };\n\n    protected async reset(): Promise<void> {\n        this.rootSpaces = [];\n        this.parentMap = new EnhancedMap();\n        this.notificationStateMap = new Map();\n        this.roomIdsBySpace = new Map();\n        this.userIdsBySpace = new Map();\n        this._aggregatedSpaceCache.roomIdsBySpace.clear();\n        this._aggregatedSpaceCache.userIdsBySpace.clear();\n        this._activeSpace = MetaSpace.Home; // set properly by onReady\n        this._suggestedRooms = [];\n        this._invitedSpaces = new Set();\n        this._enabledMetaSpaces = [];\n    }\n\n    protected async onNotReady(): Promise<void> {\n        if (this.matrixClient) {\n            this.matrixClient.removeListener(ClientEvent.Room, this.onRoom);\n            this.matrixClient.removeListener(RoomEvent.MyMembership, this.onRoom);\n            this.matrixClient.removeListener(RoomEvent.AccountData, this.onRoomAccountData);\n            this.matrixClient.removeListener(RoomStateEvent.Events, this.onRoomState);\n            this.matrixClient.removeListener(RoomStateEvent.Members, this.onRoomStateMembers);\n            this.matrixClient.removeListener(ClientEvent.AccountData, this.onAccountData);\n        }\n        await this.reset();\n    }\n\n    protected async onReady(): Promise<void> {\n        if (!this.matrixClient) return;\n        this.matrixClient.on(ClientEvent.Room, this.onRoom);\n        this.matrixClient.on(RoomEvent.MyMembership, this.onRoom);\n        this.matrixClient.on(RoomEvent.AccountData, this.onRoomAccountData);\n        this.matrixClient.on(RoomStateEvent.Events, this.onRoomState);\n        this.matrixClient.on(RoomStateEvent.Members, this.onRoomStateMembers);\n        this.matrixClient.on(ClientEvent.AccountData, this.onAccountData);\n\n        const oldMetaSpaces = this._enabledMetaSpaces;\n        const enabledMetaSpaces = SettingsStore.getValue(\"Spaces.enabledMetaSpaces\");\n        this._enabledMetaSpaces = this.metaSpaceOrder.filter((k) => enabledMetaSpaces[k]);\n\n        this._allRoomsInHome = SettingsStore.getValue(\"Spaces.allRoomsInHome\");\n        this.sendUserProperties();\n\n        this.rebuildSpaceHierarchy(); // trigger an initial update\n        // rebuildSpaceHierarchy will only send an update if the spaces have changed.\n        // If only the meta spaces have changed, we need to send an update ourselves.\n        if (arrayHasDiff(oldMetaSpaces, this._enabledMetaSpaces)) {\n            this.emit(UPDATE_TOP_LEVEL_SPACES, this.spacePanelSpaces, this.enabledMetaSpaces);\n        }\n\n        // restore selected state from last session if any and still valid\n        const lastSpaceId = window.localStorage.getItem(ACTIVE_SPACE_LS_KEY) as MetaSpace;\n        const valid =\n            lastSpaceId &&\n            (ModuleApi.instance.extras.spacePanelItems.has(lastSpaceId) ||\n                (!isMetaSpace(lastSpaceId) ? this.matrixClient.getRoom(lastSpaceId) : enabledMetaSpaces[lastSpaceId]));\n        if (valid) {\n            // don't context switch here as it may break permalinks\n            this.setActiveSpace(lastSpaceId, false);\n        } else {\n            this.switchSpaceIfNeeded();\n        }\n        this._storeReadyDeferred.resolve();\n    }\n\n    private sendUserProperties(): void {\n        const enabled = new Set(this.enabledMetaSpaces);\n        PosthogAnalytics.instance.setProperty(\"WebMetaSpaceHomeEnabled\", enabled.has(MetaSpace.Home));\n        PosthogAnalytics.instance.setProperty(\"WebMetaSpaceHomeAllRooms\", this.allRoomsInHome);\n        PosthogAnalytics.instance.setProperty(\"WebMetaSpacePeopleEnabled\", enabled.has(MetaSpace.People));\n        PosthogAnalytics.instance.setProperty(\"WebMetaSpaceFavouritesEnabled\", enabled.has(MetaSpace.Favourites));\n        PosthogAnalytics.instance.setProperty(\"WebMetaSpaceOrphansEnabled\", enabled.has(MetaSpace.Orphans));\n    }\n\n    private goToFirstSpace(contextSwitch = false): void {\n        this.setActiveSpace(this.enabledMetaSpaces[0] ?? this.spacePanelSpaces[0]?.roomId, contextSwitch);\n    }\n\n    protected async onAction(payload: SpaceStoreActions): Promise<void> {\n        if (!this.matrixClient) return;\n\n        switch (payload.action) {\n            case Action.ViewRoom: {\n                // Don't auto-switch rooms when reacting to a context-switch or for new rooms being created\n                // as this is not helpful and can create loops of rooms/space switching\n                const isSpace = payload.justCreatedOpts?.roomType === RoomType.Space;\n                if (payload.context_switch || (payload.justCreatedOpts && !isSpace)) break;\n                let roomId = payload.room_id;\n\n                if (payload.room_alias && !roomId) {\n                    const result = getCachedRoomIdForAlias(payload.room_alias);\n                    if (result) roomId = result.roomId;\n                }\n\n                if (!roomId) return; // we'll get re-fired with the room ID shortly\n\n                const room = this.matrixClient.getRoom(roomId);\n                if (room?.isSpaceRoom()) {\n                    // Don't context switch when navigating to the space room\n                    // as it will cause you to end up in the wrong room\n                    this.setActiveSpace(room.roomId, false);\n                } else {\n                    this.switchSpaceIfNeeded(roomId);\n                }\n\n                // Persist last viewed room from a space\n                // we don't await setActiveSpace above as we only care about this.activeSpace being up to date\n                // synchronously for the below code - everything else can and should be async.\n                window.localStorage.setItem(getSpaceContextKey(this.activeSpace), payload.room_id ?? \"\");\n                break;\n            }\n\n            case Action.ViewHomePage:\n                if (!payload.context_switch && this.enabledMetaSpaces.includes(MetaSpace.Home)) {\n                    this.setActiveSpace(MetaSpace.Home, false);\n                    window.localStorage.setItem(getSpaceContextKey(this.activeSpace), \"\");\n                }\n                break;\n\n            case Action.AfterLeaveRoom:\n                if (!isMetaSpace(this._activeSpace) && payload.room_id === this._activeSpace) {\n                    // User has left the current space, go to first space\n                    this.goToFirstSpace(true);\n                }\n                break;\n\n            case Action.SwitchSpace: {\n                // Metaspaces start at 1, Spaces follow\n                if (payload.num < 1 || payload.num > 9) break;\n                const numMetaSpaces = this.enabledMetaSpaces.length;\n                if (payload.num <= numMetaSpaces) {\n                    this.setActiveSpace(this.enabledMetaSpaces[payload.num - 1]);\n                } else if (this.spacePanelSpaces.length > payload.num - numMetaSpaces - 1) {\n                    this.setActiveSpace(this.spacePanelSpaces[payload.num - numMetaSpaces - 1].roomId);\n                }\n                break;\n            }\n\n            case Action.SettingUpdated: {\n                switch (payload.settingName) {\n                    case \"Spaces.allRoomsInHome\": {\n                        const newValue = SettingsStore.getValue(\"Spaces.allRoomsInHome\");\n                        if (this.allRoomsInHome !== newValue) {\n                            this._allRoomsInHome = newValue;\n                            if (this.enabledMetaSpaces.includes(MetaSpace.Home)) {\n                                this.rebuildHomeSpace();\n                            }\n                            this.sendUserProperties();\n                            this.emit(UPDATE_HOME_BEHAVIOUR, this.allRoomsInHome);\n                        }\n                        break;\n                    }\n\n                    case \"Spaces.enabledMetaSpaces\": {\n                        const newValue = SettingsStore.getValue(\"Spaces.enabledMetaSpaces\");\n                        const enabledMetaSpaces = this.metaSpaceOrder.filter((k) => newValue[k]);\n                        if (arrayHasDiff(this._enabledMetaSpaces, enabledMetaSpaces)) {\n                            const hadPeopleOrHomeEnabled = this.enabledMetaSpaces.some((s) => {\n                                return s === MetaSpace.Home || s === MetaSpace.People;\n                            });\n                            this._enabledMetaSpaces = enabledMetaSpaces;\n                            const hasPeopleOrHomeEnabled = this.enabledMetaSpaces.some((s) => {\n                                return s === MetaSpace.Home || s === MetaSpace.People;\n                            });\n\n                            // if a metaspace currently being viewed was removed, go to another one\n                            if (isMetaSpace(this.activeSpace) && !newValue[this.activeSpace]) {\n                                this.switchSpaceIfNeeded();\n                            }\n                            this.rebuildMetaSpaces();\n\n                            if (hadPeopleOrHomeEnabled !== hasPeopleOrHomeEnabled) {\n                                // in this case we have to rebuild everything as DM badges will move to/from real spaces\n                                this.updateNotificationStates();\n                            } else {\n                                this.updateNotificationStates(enabledMetaSpaces);\n                            }\n\n                            this.emit(UPDATE_TOP_LEVEL_SPACES, this.spacePanelSpaces, this.enabledMetaSpaces);\n                            this.sendUserProperties();\n                        }\n                        break;\n                    }\n\n                    case \"Spaces.showPeopleInSpace\":\n                        if (payload.roomId) {\n                            // getSpaceFilteredUserIds will return the appropriate value\n                            this.emit(payload.roomId);\n                            if (!this.enabledMetaSpaces.some((s) => s === MetaSpace.Home || s === MetaSpace.People)) {\n                                this.updateNotificationStates([payload.roomId]);\n                            }\n                        }\n                        break;\n\n                    case \"feature_dynamic_room_predecessors\":\n                        this._msc3946ProcessDynamicPredecessor = SettingsStore.getValue(\n                            \"feature_dynamic_room_predecessors\",\n                        );\n                        this.rebuildSpaceHierarchy();\n                        break;\n                }\n            }\n        }\n    }\n\n    public getNotificationState(key: SpaceKey): SpaceNotificationState {\n        if (this.notificationStateMap.has(key)) {\n            return this.notificationStateMap.get(key)!;\n        }\n\n        const state = new SpaceNotificationState();\n        this.notificationStateMap.set(key, state);\n        return state;\n    }\n\n    // traverse space tree with DFS calling fn on each space including the given root one,\n    // if includeRooms is true then fn will be called on each leaf room, if it is present in multiple sub-spaces\n    // then fn will be called with it multiple times.\n    public traverseSpace(\n        spaceId: string,\n        fn: (roomId: string) => void,\n        includeRooms = false,\n        parentPath?: Set<string>,\n    ): void {\n        if (parentPath && parentPath.has(spaceId)) return; // prevent cycles\n\n        fn(spaceId);\n\n        const newPath = new Set(parentPath).add(spaceId);\n        const [childSpaces, childRooms] = partitionSpacesAndRooms(this.getChildren(spaceId));\n\n        if (includeRooms) {\n            childRooms.forEach((r) => fn(r.roomId));\n        }\n        childSpaces.forEach((s) => this.traverseSpace(s.roomId, fn, includeRooms, newPath));\n    }\n\n    private getSpaceTagOrdering = (space: Room): string | undefined => {\n        if (this.spaceOrderLocalEchoMap.has(space.roomId)) return this.spaceOrderLocalEchoMap.get(space.roomId);\n        return validOrder(space.getAccountData(EventType.SpaceOrder)?.getContent()?.order);\n    };\n\n    private sortRootSpaces(spaces: Room[]): Room[] {\n        return sortBy(spaces, [this.getSpaceTagOrdering, \"roomId\"]);\n    }\n\n    private async setRootSpaceOrder(space: Room, order: string): Promise<void> {\n        this.spaceOrderLocalEchoMap.set(space.roomId, order);\n        try {\n            await this.matrixClient?.setRoomAccountData(space.roomId, EventType.SpaceOrder, { order });\n        } catch (e) {\n            logger.warn(\"Failed to set root space order\", e);\n            if (this.spaceOrderLocalEchoMap.get(space.roomId) === order) {\n                this.spaceOrderLocalEchoMap.delete(space.roomId);\n            }\n        }\n    }\n\n    public moveRootSpace(fromIndex: number, toIndex: number): void {\n        const currentOrders = this.rootSpaces.map(this.getSpaceTagOrdering);\n        const changes = reorderLexicographically(currentOrders, fromIndex, toIndex);\n\n        changes.forEach(({ index, order }) => {\n            this.setRootSpaceOrder(this.rootSpaces[index], order);\n        });\n\n        this.notifyIfOrderChanged();\n    }\n}\n\nexport default class SpaceStore {\n    private static readonly internalInstance = (() => {\n        const instance = new SpaceStoreClass();\n        instance.start();\n        return instance;\n    })();\n\n    public static get instance(): SpaceStoreClass {\n        return SpaceStore.internalInstance;\n    }\n\n    /**\n     * @internal for test only\n     */\n    public static testInstance(): SpaceStoreClass {\n        const store = new SpaceStoreClass();\n        store.start();\n        return store;\n    }\n}\n\nwindow.mxSpaceStore = SpaceStore.instance;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type HierarchyRoom } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../languageHandler\";\n\n// The consts & types are moved out here to prevent cyclical imports\n\nexport const UPDATE_TOP_LEVEL_SPACES = Symbol(\"top-level-spaces\");\nexport const UPDATE_INVITED_SPACES = Symbol(\"invited-spaces\");\nexport const UPDATE_SELECTED_SPACE = Symbol(\"selected-space\");\nexport const UPDATE_HOME_BEHAVIOUR = Symbol(\"home-behaviour\");\nexport const UPDATE_SUGGESTED_ROOMS = Symbol(\"suggested-rooms\");\n// Space Key will be emitted when a Space's children change\n\nexport enum MetaSpace {\n    Home = \"home-space\",\n    Favourites = \"favourites-space\",\n    People = \"people-space\",\n    Orphans = \"orphans-space\",\n    VideoRooms = \"video-rooms-space\",\n}\n\nexport const getMetaSpaceName = (spaceKey: MetaSpace, allRoomsInHome = false): string => {\n    switch (spaceKey) {\n        case MetaSpace.Home:\n            return allRoomsInHome ? _t(\"common|all_chats\") : _t(\"common|home\");\n        case MetaSpace.Favourites:\n            return _t(\"common|favourites\");\n        case MetaSpace.People:\n            return _t(\"common|people\");\n        case MetaSpace.Orphans:\n            return _t(\"common|orphan_rooms\");\n        case MetaSpace.VideoRooms:\n            return _t(\"voip|metaspace_video_rooms|conference_room_section\");\n    }\n};\n\n/**\n * This can be:\n *  - a MetaSpace\n *  - space ID (ie. a room ID)\n *  - A 'custom' space from a module\n * Unfortunately we can't type the last set as we don't know what modules will define,\n * so we can't do better than string here.\n */\nexport type SpaceKey = string;\n\nexport interface ISuggestedRoom extends HierarchyRoom {\n    viaServers: string[];\n}\n\nexport function isMetaSpace(spaceKey?: SpaceKey): spaceKey is MetaSpace {\n    return (\n        spaceKey === MetaSpace.Home ||\n        spaceKey === MetaSpace.Favourites ||\n        spaceKey === MetaSpace.People ||\n        spaceKey === MetaSpace.Orphans ||\n        spaceKey === MetaSpace.VideoRooms\n    );\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2020-2022 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type IWidgetApiRequest } from \"matrix-widget-api\";\n\nexport enum ElementWidgetActions {\n    // All of these actions are currently specific to Jitsi and Element Call\n    JoinCall = \"io.element.join\",\n    HangupCall = \"im.vector.hangup\",\n    Close = \"io.element.close\",\n    CallParticipants = \"io.element.participants\",\n    StartLiveStream = \"im.vector.start_live_stream\",\n\n    // Actions for switching layouts\n    TileLayout = \"io.element.tile_layout\",\n    SpotlightLayout = \"io.element.spotlight_layout\",\n\n    OpenIntegrationManager = \"integration_manager_open\",\n    /**\n     * @deprecated Use MSC2931 instead\n     */\n    ViewRoom = \"io.element.view_room\",\n\n    // This action type is used as a `fromWidget` and a `toWidget` action.\n    // fromWidget: updates the client about the current device mute state\n    // toWidget: the client requests a specific device mute configuration\n    //   The reply will always be the resulting configuration\n    //   It is possible to sent an empty configuration to retrieve the current values or\n    //   just one of the fields to update that particular value\n    //   An undefined field means that EC will keep the mute state as is.\n    //   -> this will allow the client to only get the current state\n    //\n    // The data of the widget action request and the response are:\n    // {\n    //   audio_enabled?: boolean,\n    //   video_enabled?: boolean\n    // }\n    // NOTE: this is currently unused. Its only here to make EW aware\n    // of this action so it does not throw errors.\n    DeviceMute = \"io.element.device_mute\",\n}\n\nexport interface IHangupCallApiRequest extends IWidgetApiRequest {\n    data: {\n        errorMessage?: string;\n    };\n}\n\n/**\n * @deprecated Use MSC2931 instead\n */\nexport interface IViewRoomApiRequest extends IWidgetApiRequest {\n    data: {\n        room_id: string; // eslint-disable-line camelcase\n    };\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2020 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nexport enum ElementWidgetCapabilities {\n    /**\n     * @deprecated Use MSC2931 instead.\n     */\n    CanChangeViewedRoom = \"io.element.view_room\",\n    /**\n     * Ask Element to not give the option to move the widget into a separate tab.\n     * This replaces RequiresClient in MatrixCapabilities.\n     */\n    RequiresClient = \"io.element.requires_client\",\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2021, 2022 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type Room, RoomStateEvent, type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { MapWithDefault, recursiveMapToObject } from \"matrix-js-sdk/src/utils\";\nimport { type IWidget } from \"matrix-widget-api\";\nimport { clamp, defaultNumber, sum } from \"@element-hq/web-shared-components\";\n\nimport SettingsStore from \"../../settings/SettingsStore\";\nimport WidgetStore, { type IApp } from \"../WidgetStore\";\nimport { WidgetType } from \"../../widgets/WidgetType\";\nimport defaultDispatcher from \"../../dispatcher/dispatcher\";\nimport { ReadyWatchingStore } from \"../ReadyWatchingStore\";\nimport { SettingLevel } from \"../../settings/SettingLevel\";\nimport { arrayFastClone } from \"../../utils/arrays\";\nimport { UPDATE_EVENT } from \"../AsyncStore\";\nimport {\n    Container,\n    type IStoredLayout,\n    type ILayoutStateEvent,\n    WIDGET_LAYOUT_EVENT_TYPE,\n    type IWidgetLayouts,\n} from \"./types\";\n\nexport type { IStoredLayout, ILayoutStateEvent };\nexport { Container, WIDGET_LAYOUT_EVENT_TYPE };\n\nexport type ILayoutSettings = Partial<ILayoutStateEvent> & {\n    overrides?: string; // event ID for layout state event, if present\n};\n\n// Dev note: \"Pinned\" widgets are ones in the top container.\nexport const MAX_PINNED = 3;\n\n// These two are whole percentages and don't really mean anything. Later values will decide\n// minimum, but these help determine proportions during our calculations here. In fact, these\n// values should be *smaller* than the actual minimums imposed by later components.\nconst MIN_WIDGET_WIDTH_PCT = 10; // 10%\nconst MIN_WIDGET_HEIGHT_PCT = 2; // 2%\n\ninterface ContainerValue {\n    ordered: IApp[];\n    height?: number;\n    distributions?: number[];\n}\n\nexport class WidgetLayoutStore extends ReadyWatchingStore {\n    private static internalInstance: WidgetLayoutStore;\n\n    // Map: room Id → container → ContainerValue\n    private byRoom: MapWithDefault<string, Map<Container, ContainerValue>> = new MapWithDefault(() => new Map());\n    private pinnedRef: string | undefined;\n    private layoutRef: string | undefined;\n    private dynamicRef: string | undefined;\n\n    private constructor() {\n        super(defaultDispatcher);\n    }\n\n    public static get instance(): WidgetLayoutStore {\n        if (!this.internalInstance) {\n            this.internalInstance = new WidgetLayoutStore();\n            this.internalInstance.start();\n        }\n        return this.internalInstance;\n    }\n\n    public static emissionForRoom(room: Room): string {\n        return `update_${room.roomId}`;\n    }\n\n    private emitFor(room: Room): void {\n        this.emit(WidgetLayoutStore.emissionForRoom(room));\n    }\n\n    protected async onReady(): Promise<void> {\n        this.updateAllRooms();\n\n        this.matrixClient?.on(RoomStateEvent.Events, this.updateRoomFromState);\n        this.pinnedRef = SettingsStore.watchSetting(\"Widgets.pinned\", null, this.updateFromSettings);\n        this.layoutRef = SettingsStore.watchSetting(\"Widgets.layout\", null, this.updateFromSettings);\n        this.dynamicRef = SettingsStore.watchSetting(\n            \"feature_dynamic_room_predecessors\",\n            null,\n            this.updateFromSettings,\n        );\n        WidgetStore.instance.on(UPDATE_EVENT, this.updateFromWidgetStore);\n    }\n\n    protected async onNotReady(): Promise<void> {\n        this.byRoom = new MapWithDefault(() => new Map());\n\n        this.matrixClient?.off(RoomStateEvent.Events, this.updateRoomFromState);\n        SettingsStore.unwatchSetting(this.pinnedRef);\n        SettingsStore.unwatchSetting(this.layoutRef);\n        SettingsStore.unwatchSetting(this.dynamicRef);\n        WidgetStore.instance.off(UPDATE_EVENT, this.updateFromWidgetStore);\n    }\n\n    private updateAllRooms = (): void => {\n        const msc3946ProcessDynamicPredecessor = SettingsStore.getValue(\"feature_dynamic_room_predecessors\");\n        if (!this.matrixClient) return;\n        this.byRoom = new MapWithDefault(() => new Map());\n        for (const room of this.matrixClient.getVisibleRooms(msc3946ProcessDynamicPredecessor)) {\n            this.recalculateRoom(room);\n        }\n    };\n\n    private updateFromWidgetStore = (roomId?: string): void => {\n        if (roomId) {\n            const room = this.matrixClient?.getRoom(roomId);\n            if (room) this.recalculateRoom(room);\n        } else {\n            this.updateAllRooms();\n        }\n    };\n\n    private updateRoomFromState = (ev: MatrixEvent): void => {\n        if (ev.getType() !== WIDGET_LAYOUT_EVENT_TYPE) return;\n        const room = this.matrixClient?.getRoom(ev.getRoomId());\n        if (room) this.recalculateRoom(room);\n    };\n\n    private updateFromSettings = (\n        _settingName: string,\n        roomId: string | null,\n        _atLevel: SettingLevel,\n        _newValAtLevel: any,\n        _newVal: any,\n    ): void => {\n        if (roomId) {\n            const room = this.matrixClient?.getRoom(roomId);\n            if (room) this.recalculateRoom(room);\n        } else {\n            this.updateAllRooms();\n        }\n    };\n\n    public recalculateRoom(room: Room): void {\n        const widgets = WidgetStore.instance.getApps(room.roomId);\n        if (!widgets?.length) {\n            this.byRoom.set(room.roomId, new Map());\n            this.emitFor(room);\n            return;\n        }\n\n        const roomContainers = this.byRoom.getOrCreate(room.roomId);\n        const beforeChanges = JSON.stringify(recursiveMapToObject(roomContainers));\n\n        const layoutEv = room.currentState.getStateEvents(WIDGET_LAYOUT_EVENT_TYPE, \"\");\n        const legacyPinned = SettingsStore.getValue(\"Widgets.pinned\", room.roomId);\n        let userLayout = SettingsStore.getValue(\"Widgets.layout\", room.roomId);\n\n        if (layoutEv && userLayout && userLayout.overrides !== layoutEv.getId()) {\n            // For some other layout that we don't really care about. The user can reset this\n            // by updating their personal layout.\n            userLayout = null;\n        }\n\n        const roomLayout = layoutEv?.getContent<ILayoutStateEvent>() ?? null;\n        // We filter for the center container first.\n        // (An error is raised, if there are multiple widgets marked for the center container)\n        // For the right and top container multiple widgets are allowed.\n        const topWidgets: IApp[] = [];\n        const rightWidgets: IApp[] = [];\n        const centerWidgets: IApp[] = [];\n        for (const widget of widgets) {\n            const stateContainer = roomLayout?.widgets?.[widget.id]?.container;\n            const manualContainer = userLayout?.widgets?.[widget.id]?.container;\n            const isLegacyPinned = !!legacyPinned?.[widget.id];\n            const defaultContainer = WidgetType.JITSI.matches(widget.type) ? Container.Top : Container.Right;\n            if (manualContainer ? manualContainer === Container.Center : stateContainer === Container.Center) {\n                if (centerWidgets.length) {\n                    console.error(\"Tried to push a second widget into the center container\");\n                } else {\n                    centerWidgets.push(widget);\n                }\n                // The widget won't need to be put in any other container.\n                continue;\n            }\n            let targetContainer: Container = defaultContainer;\n            if (!!manualContainer || !!stateContainer) {\n                targetContainer = manualContainer ?? stateContainer!;\n            } else if (isLegacyPinned && !stateContainer) {\n                // Special legacy case\n                targetContainer = Container.Top;\n            }\n            (targetContainer === Container.Top ? topWidgets : rightWidgets).push(widget);\n        }\n\n        // Trim to MAX_PINNED\n        const runoff = topWidgets.slice(MAX_PINNED);\n        rightWidgets.push(...runoff);\n\n        const collator = new Intl.Collator();\n\n        // Order the widgets in the top container, putting autopinned Jitsi widgets first\n        // unless they have a specific order in mind\n        topWidgets.sort((a, b) => {\n            const layoutA = roomLayout?.widgets?.[a.id];\n            const layoutB = roomLayout?.widgets?.[b.id];\n\n            const userLayoutA = userLayout?.widgets?.[a.id];\n            const userLayoutB = userLayout?.widgets?.[b.id];\n\n            // Jitsi widgets are defaulted to be the leftmost widget whereas other widgets\n            // default to the right side.\n            const defaultA = WidgetType.JITSI.matches(a.type) ? Number.MIN_SAFE_INTEGER : Number.MAX_SAFE_INTEGER;\n            const defaultB = WidgetType.JITSI.matches(b.type) ? Number.MIN_SAFE_INTEGER : Number.MAX_SAFE_INTEGER;\n\n            const orderA = defaultNumber(userLayoutA?.index, defaultNumber(layoutA?.index, defaultA));\n            const orderB = defaultNumber(userLayoutB?.index, defaultNumber(layoutB?.index, defaultB));\n\n            if (orderA === orderB) {\n                // We just need a tiebreak\n                return collator.compare(a.id, b.id);\n            }\n\n            return orderA - orderB;\n        });\n\n        // Determine width distribution and height of the top container now (the only relevant one)\n        const widths: number[] = [];\n        let maxHeight: number | null = null; // null == default\n        let doAutobalance = true;\n        for (let i = 0; i < topWidgets.length; i++) {\n            const widget = topWidgets[i];\n            const widgetLayout = roomLayout?.widgets?.[widget.id];\n            const userWidgetLayout = userLayout?.widgets?.[widget.id];\n\n            if (Number.isFinite(userWidgetLayout?.width) || Number.isFinite(widgetLayout?.width)) {\n                const val = (userWidgetLayout?.width || widgetLayout?.width)!;\n                const normalized = clamp(val, MIN_WIDGET_WIDTH_PCT, 100);\n                widths.push(normalized);\n                doAutobalance = false; // a manual width was specified\n            } else {\n                widths.push(100); // we'll figure this out later\n            }\n\n            if (widgetLayout?.height || userWidgetLayout?.height) {\n                const defRoomHeight = defaultNumber(widgetLayout?.height, MIN_WIDGET_HEIGHT_PCT);\n                const h = defaultNumber(userWidgetLayout?.height, defRoomHeight);\n                maxHeight = Math.max(maxHeight ?? 0, clamp(h, MIN_WIDGET_HEIGHT_PCT, 100));\n            }\n        }\n        if (doAutobalance) {\n            for (let i = 0; i < widths.length; i++) {\n                widths[i] = 100 / widths.length;\n            }\n        } else {\n            // If we're not autobalancing then it means that we're trying to make\n            // sure that widgets make up exactly 100% of space (not over, not under)\n            const difference = sum(...widths) - 100; // positive = over, negative = under\n            if (difference < 0) {\n                // For a deficit we just fill everything in equally\n                for (let i = 0; i < widths.length; i++) {\n                    widths[i] += Math.abs(difference) / widths.length;\n                }\n            } else if (difference > 0) {\n                // When we're over, we try to scale all the widgets within range first.\n                // We clamp values to try and keep ourselves sane and within range.\n                for (let i = 0; i < widths.length; i++) {\n                    widths[i] = clamp(widths[i] - difference / widths.length, MIN_WIDGET_WIDTH_PCT, 100);\n                }\n\n                // If we're still over, find the widgets which have more width than the minimum\n                // and balance them out until we're at 100%. This should keep us as close as possible\n                // to the intended distributions.\n                //\n                // Note: if we ever decide to set a minimum which is larger than 100%/MAX_WIDGETS then\n                // we probably have other issues - this code assumes we don't do that.\n                const toReclaim = sum(...widths) - 100;\n                if (toReclaim > 0) {\n                    const largeIndices = widths\n                        .map((v, i) => [i, v])\n                        .filter((p) => p[1] > MIN_WIDGET_WIDTH_PCT)\n                        .map((p) => p[0]);\n                    for (const idx of largeIndices) {\n                        widths[idx] -= toReclaim / largeIndices.length;\n                    }\n                }\n            }\n        }\n\n        // Finally, fill in our cache and update\n        const newRoomContainers = new Map();\n        this.byRoom.set(room.roomId, newRoomContainers);\n        if (topWidgets.length) {\n            newRoomContainers.set(Container.Top, {\n                ordered: topWidgets,\n                distributions: widths,\n                height: maxHeight,\n            });\n        }\n        if (rightWidgets.length) {\n            newRoomContainers.set(Container.Right, {\n                ordered: rightWidgets,\n            });\n        }\n        if (centerWidgets.length) {\n            newRoomContainers.set(Container.Center, {\n                ordered: centerWidgets,\n            });\n        }\n\n        const afterChanges = JSON.stringify(recursiveMapToObject(newRoomContainers));\n\n        if (afterChanges !== beforeChanges) {\n            this.emitFor(room);\n        }\n    }\n\n    public getContainerWidgets(room: Room | null, container: Container): IWidget[] {\n        return (room && this.byRoom.get(room.roomId)?.get(container)?.ordered) || [];\n    }\n\n    public isInContainer(room: Room, widget: IWidget, container: Container): boolean {\n        return this.getContainerWidgets(room, container).some((w) => w.id === widget.id);\n    }\n\n    public canAddToContainer(room: Room, container: Container): boolean {\n        switch (container) {\n            case Container.Top:\n                return this.getContainerWidgets(room, container).length < MAX_PINNED;\n            case Container.Right:\n                return this.getContainerWidgets(room, container).length < MAX_PINNED;\n            case Container.Center:\n                return this.getContainerWidgets(room, container).length < 1;\n        }\n    }\n\n    public getResizerDistributions(room: Room, container: Container): string[] {\n        // yes, string.\n        let distributions = this.byRoom.get(room.roomId)?.get(container)?.distributions;\n        if (!distributions || distributions.length < 2) return [];\n\n        // The distributor actually expects to be fed N-1 sizes and expands the middle section\n        // instead of the edges. Therefore, we need to return [0] when there's two widgets or\n        // [0, 2] when there's three (skipping [1] because it's irrelevant).\n\n        if (distributions.length === 2) distributions = [distributions[0]];\n        if (distributions.length === 3) distributions = [distributions[0], distributions[2]];\n        return distributions.map((d) => `${d.toFixed(1)}%`); // actual percents - these are decoded later\n    }\n\n    public setResizerDistributions(room: Room, container: Container, distributions: string[]): void {\n        if (container !== Container.Top) return; // ignore - not relevant\n\n        const numbers = distributions.map((d) => Number(Number(d.substring(0, d.length - 1)).toFixed(1)));\n        const widgets = this.getContainerWidgets(room, container);\n\n        // From getResizerDistributions, we need to fill in the middle size if applicable.\n        const remaining = 100 - sum(...numbers);\n        if (numbers.length === 2) numbers.splice(1, 0, remaining);\n        if (numbers.length === 1) numbers.push(remaining);\n\n        const localLayout: Record<string, IStoredLayout> = {};\n        widgets.forEach((w, i) => {\n            localLayout[w.id] = {\n                container: container,\n                width: numbers[i],\n                index: i,\n                height: this.byRoom.get(room.roomId)?.get(container)?.height || MIN_WIDGET_HEIGHT_PCT,\n            };\n        });\n        this.updateUserLayout(room, localLayout);\n    }\n\n    public getContainerHeight(room: Room, container: Container): number | null {\n        return this.byRoom.get(room.roomId)?.get(container)?.height ?? null; // let the default get returned if needed\n    }\n\n    public setContainerHeight(room: Room, container: Container, height?: number | null): void {\n        const widgets = this.getContainerWidgets(room, container);\n        const widths = this.byRoom.get(room.roomId)?.get(container)?.distributions;\n        const localLayout: Record<string, IStoredLayout> = {};\n        widgets.forEach((w, i) => {\n            localLayout[w.id] = {\n                container: container,\n                width: widths?.[i],\n                index: i,\n                height: height,\n            };\n        });\n        this.updateUserLayout(room, localLayout);\n    }\n\n    public moveWithinContainer(room: Room, container: Container, widget: IWidget, delta: number): void {\n        const widgets = arrayFastClone(this.getContainerWidgets(room, container));\n        const currentIdx = widgets.findIndex((w) => w.id === widget.id);\n        if (currentIdx < 0) return; // no change needed\n\n        widgets.splice(currentIdx, 1); // remove existing widget\n        const newIdx = clamp(currentIdx + delta, 0, widgets.length);\n        widgets.splice(newIdx, 0, widget);\n\n        const widths = this.byRoom.get(room.roomId)?.get(container)?.distributions;\n        const height = this.byRoom.get(room.roomId)?.get(container)?.height;\n        const localLayout: Record<string, IStoredLayout> = {};\n        widgets.forEach((w, i) => {\n            localLayout[w.id] = {\n                container: container,\n                width: widths?.[i],\n                index: i,\n                height,\n            };\n        });\n        this.updateUserLayout(room, localLayout);\n    }\n\n    public moveToContainer(room: Room, widget: IWidget, toContainer: Container): void {\n        const allWidgets = this.getAllWidgets(room);\n        if (!allWidgets.some(([w]) => w.id === widget.id)) return; // invalid\n        // Prepare other containers (potentially move widgets to obey the following rules)\n        const newLayout: Record<string, IStoredLayout> = {};\n        switch (toContainer) {\n            case Container.Right:\n                // new \"right\" widget\n                break;\n            case Container.Center:\n                // new \"center\" widget => all other widgets go into \"right\"\n                for (const w of this.getContainerWidgets(room, Container.Top)) {\n                    newLayout[w.id] = { container: Container.Right };\n                }\n                for (const w of this.getContainerWidgets(room, Container.Center)) {\n                    newLayout[w.id] = { container: Container.Right };\n                }\n                break;\n            case Container.Top:\n                // new \"top\" widget => the center widget moves into \"right\"\n                if (this.hasMaximisedWidget(room)) {\n                    const centerWidget = this.getContainerWidgets(room, Container.Center)[0];\n                    newLayout[centerWidget.id] = { container: Container.Right };\n                }\n                break;\n        }\n\n        newLayout[widget.id] = { container: toContainer };\n\n        // move widgets into requested containers.\n        this.updateUserLayout(room, newLayout);\n    }\n\n    public hasMaximisedWidget(room: Room): boolean {\n        return this.getContainerWidgets(room, Container.Center).length > 0;\n    }\n\n    public hasPinnedWidgets(room: Room): boolean {\n        return this.getContainerWidgets(room, Container.Top).length > 0;\n    }\n\n    public canCopyLayoutToRoom(room: Room): boolean {\n        if (!this.matrixClient) return false; // not ready yet\n        return room.currentState.maySendStateEvent(WIDGET_LAYOUT_EVENT_TYPE, this.matrixClient.getUserId()!);\n    }\n\n    public copyLayoutToRoom(room: Room): void {\n        const allWidgets = this.getAllWidgets(room);\n        const evContent: ILayoutStateEvent = { widgets: {} };\n        for (const [widget, container] of allWidgets) {\n            evContent.widgets[widget.id] = { container };\n            if (container === Container.Top) {\n                const containerWidgets = this.getContainerWidgets(room, container);\n                const idx = containerWidgets.findIndex((w) => w.id === widget.id);\n                const widths = this.byRoom.get(room.roomId)?.get(container)?.distributions;\n                const height = this.byRoom.get(room.roomId)?.get(container)?.height;\n                evContent.widgets[widget.id] = {\n                    ...evContent.widgets[widget.id],\n                    height: height ? Math.round(height) : undefined,\n                    width: widths?.[idx] ? Math.round(widths[idx]) : undefined,\n                    index: idx,\n                };\n            }\n        }\n        this.matrixClient?.sendStateEvent(room.roomId, WIDGET_LAYOUT_EVENT_TYPE, evContent, \"\");\n    }\n\n    private getAllWidgets(room: Room): [IApp, Container][] {\n        const containers = this.byRoom.get(room.roomId);\n        if (!containers) return [];\n\n        const ret: [IApp, Container][] = [];\n        for (const [container, containerValue] of containers) {\n            const widgets = containerValue.ordered;\n            for (const widget of widgets) {\n                ret.push([widget, container as Container]);\n            }\n        }\n        return ret;\n    }\n\n    private updateUserLayout(room: Room, newLayout: IWidgetLayouts): void {\n        // Polyfill any missing widgets\n        const allWidgets = this.getAllWidgets(room);\n        for (const [widget, container] of allWidgets) {\n            const containerWidgets = this.getContainerWidgets(room, container);\n            const idx = containerWidgets.findIndex((w) => w.id === widget.id);\n            const widths = this.byRoom.get(room.roomId)?.get(container)?.distributions;\n            if (!newLayout[widget.id]) {\n                newLayout[widget.id] = {\n                    container: container,\n                    index: idx,\n                    height: this.byRoom.get(room.roomId)?.get(container)?.height,\n                    width: widths?.[idx],\n                };\n            }\n        }\n\n        const layoutEv = room.currentState.getStateEvents(WIDGET_LAYOUT_EVENT_TYPE, \"\");\n        SettingsStore.setValue(\"Widgets.layout\", room.roomId, SettingLevel.ROOM_ACCOUNT, {\n            overrides: layoutEv?.getId(),\n            widgets: newLayout,\n        }).catch(() => this.recalculateRoom(room));\n        this.recalculateRoom(room); // call to try local echo on changes (the catch above undoes any errors)\n    }\n}\n\nwindow.mxWidgetLayoutStore = WidgetLayoutStore.instance;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\nCopyright 2019 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEventHandler } from \"react\";\nimport { type Widget, type WidgetKind } from \"matrix-widget-api\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { Form, SettingsToggleInput } from \"@vector-im/compound-web\";\n\nimport { _t } from \"../../../languageHandler\";\nimport { OIDCState } from \"../../../stores/widgets/WidgetPermissionStore\";\nimport BaseDialog from \"./BaseDialog\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport { SdkContextClass } from \"../../../contexts/SDKContext\";\n\ninterface IProps {\n    widget: Widget;\n    widgetKind: WidgetKind;\n    inRoomId?: string;\n    onFinished(allowed?: boolean): void;\n}\n\ninterface IState {\n    rememberSelection: boolean;\n}\n\nexport default class WidgetOpenIDPermissionsDialog extends React.PureComponent<IProps, IState> {\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {\n            rememberSelection: false,\n        };\n    }\n\n    private onAllow = (): void => {\n        this.onPermissionSelection(true);\n    };\n\n    private onDeny = (): void => {\n        this.onPermissionSelection(false);\n    };\n\n    private onPermissionSelection(allowed: boolean): void {\n        if (this.state.rememberSelection) {\n            logger.log(`Remembering ${this.props.widget.id} as allowed=${allowed} for OpenID`);\n\n            SdkContextClass.instance.widgetPermissionStore.setOIDCState(\n                this.props.widget,\n                this.props.widgetKind,\n                this.props.inRoomId,\n                allowed ? OIDCState.Allowed : OIDCState.Denied,\n            );\n        }\n\n        this.props.onFinished(allowed);\n    }\n\n    private onRememberSelectionChange: ChangeEventHandler<HTMLInputElement> = (evt): void => {\n        this.setState({ rememberSelection: evt.target.checked });\n    };\n\n    public render(): React.ReactNode {\n        return (\n            <BaseDialog\n                className=\"mx_WidgetOpenIDPermissionsDialog\"\n                hasCancel={true}\n                onFinished={this.props.onFinished}\n                title={_t(\"widget|open_id_permissions_dialog|title\")}\n            >\n                <div className=\"mx_WidgetOpenIDPermissionsDialog_content\">\n                    <p>{_t(\"widget|open_id_permissions_dialog|starting_text\")}</p>\n                    <p className=\"text-muted\">\n                        {/* cheap trim to just get the path */}\n                        {this.props.widget.templateUrl.split(\"?\")[0].split(\"#\")[0]}\n                    </p>\n                </div>\n                <DialogButtons\n                    primaryButton={_t(\"action|continue\")}\n                    onPrimaryButtonClick={this.onAllow}\n                    onCancel={this.onDeny}\n                    additive={\n                        <Form.Root\n                            onSubmit={(evt) => {\n                                evt.preventDefault();\n                                evt.stopPropagation();\n                            }}\n                        >\n                            <SettingsToggleInput\n                                name=\"remember-selection\"\n                                checked={this.state.rememberSelection}\n                                onChange={this.onRememberSelectionChange}\n                                label={_t(\"widget|open_id_permissions_dialog|remember_selection\")}\n                            />\n                        </Form.Root>\n                    }\n                />\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type Capability,\n    EventDirection,\n    EventKind,\n    getTimelineRoomIDFromCapability,\n    isTimelineCapability,\n    isTimelineCapabilityFor,\n    MatrixCapabilities,\n    Symbols,\n    WidgetEventCapability,\n    WidgetKind,\n} from \"matrix-widget-api\";\nimport { EventType, MsgType } from \"matrix-js-sdk/src/matrix\";\nimport React from \"react\";\n\nimport { _t, _td, type TranslatedString } from \"../languageHandler\";\nimport { ElementWidgetCapabilities } from \"../stores/widgets/ElementWidgetCapabilities\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport TextWithTooltip from \"../components/views/elements/TextWithTooltip\";\n\ntype GENERIC_WIDGET_KIND = \"generic\"; // eslint-disable-line @typescript-eslint/naming-convention\nconst GENERIC_WIDGET_KIND: GENERIC_WIDGET_KIND = \"generic\";\n\ntype SendRecvStaticCapText = Partial<\n    Record<\n        EventType | string,\n        Partial<Record<WidgetKind | GENERIC_WIDGET_KIND, Record<EventDirection, TranslationKey>>>\n    >\n>;\n\nexport interface TranslatedCapabilityText {\n    primary: TranslatedString;\n    byline?: TranslatedString;\n}\n\nexport class CapabilityText {\n    private static simpleCaps: Record<Capability, Partial<Record<WidgetKind | GENERIC_WIDGET_KIND, TranslationKey>>> = {\n        [MatrixCapabilities.AlwaysOnScreen]: {\n            [WidgetKind.Room]: _td(\"widget|capability|always_on_screen_viewing_another_room\"),\n            [GENERIC_WIDGET_KIND]: _td(\"widget|capability|always_on_screen_generic\"),\n        },\n        [MatrixCapabilities.StickerSending]: {\n            [WidgetKind.Room]: _td(\"widget|capability|send_stickers_this_room\"),\n            [GENERIC_WIDGET_KIND]: _td(\"widget|capability|send_stickers_active_room\"),\n        },\n        [ElementWidgetCapabilities.CanChangeViewedRoom]: {\n            [GENERIC_WIDGET_KIND]: _td(\"widget|capability|switch_room\"),\n        },\n        [MatrixCapabilities.MSC2931Navigate]: {\n            [GENERIC_WIDGET_KIND]: _td(\"widget|capability|switch_room_message_user\"),\n        },\n    };\n\n    private static stateSendRecvCaps: SendRecvStaticCapText = {\n        [EventType.RoomTopic]: {\n            [WidgetKind.Room]: {\n                [EventDirection.Send]: _td(\"widget|capability|change_topic_this_room\"),\n                [EventDirection.Receive]: _td(\"widget|capability|see_topic_change_this_room\"),\n            },\n            [GENERIC_WIDGET_KIND]: {\n                [EventDirection.Send]: _td(\"widget|capability|change_topic_active_room\"),\n                [EventDirection.Receive]: _td(\"widget|capability|see_topic_change_active_room\"),\n            },\n        },\n        [EventType.RoomName]: {\n            [WidgetKind.Room]: {\n                [EventDirection.Send]: _td(\"widget|capability|change_name_this_room\"),\n                [EventDirection.Receive]: _td(\"widget|capability|see_name_change_this_room\"),\n            },\n            [GENERIC_WIDGET_KIND]: {\n                [EventDirection.Send]: _td(\"widget|capability|change_name_active_room\"),\n                [EventDirection.Receive]: _td(\"widget|capability|see_name_change_active_room\"),\n            },\n        },\n        [EventType.RoomAvatar]: {\n            [WidgetKind.Room]: {\n                [EventDirection.Send]: _td(\"widget|capability|change_avatar_this_room\"),\n                [EventDirection.Receive]: _td(\"widget|capability|see_avatar_change_this_room\"),\n            },\n            [GENERIC_WIDGET_KIND]: {\n                [EventDirection.Send]: _td(\"widget|capability|change_avatar_active_room\"),\n                [EventDirection.Receive]: _td(\"widget|capability|see_avatar_change_active_room\"),\n            },\n        },\n        [EventType.RoomMember]: {\n            [WidgetKind.Room]: {\n                [EventDirection.Send]: _td(\"widget|capability|remove_ban_invite_leave_this_room\"),\n                [EventDirection.Receive]: _td(\"widget|capability|receive_membership_this_room\"),\n            },\n            [GENERIC_WIDGET_KIND]: {\n                [EventDirection.Send]: _td(\"widget|capability|remove_ban_invite_leave_active_room\"),\n                [EventDirection.Receive]: _td(\"widget|capability|receive_membership_active_room\"),\n            },\n        },\n    };\n\n    private static nonStateSendRecvCaps: SendRecvStaticCapText = {\n        [EventType.Sticker]: {\n            [WidgetKind.Room]: {\n                [EventDirection.Send]: _td(\"widget|capability|send_stickers_this_room_as_you\"),\n                [EventDirection.Receive]: _td(\"widget|capability|see_sticker_posted_this_room\"),\n            },\n            [GENERIC_WIDGET_KIND]: {\n                [EventDirection.Send]: _td(\"widget|capability|send_stickers_active_room_as_you\"),\n                [EventDirection.Receive]: _td(\"widget|capability|see_sticker_posted_active_room\"),\n            },\n        },\n    };\n\n    private static bylineFor(eventCap: WidgetEventCapability): TranslatedString {\n        if (eventCap.kind === EventKind.State) {\n            return !eventCap.keyStr\n                ? _t(\"widget|capability|byline_empty_state_key\")\n                : _t(\"widget|capability|byline_state_key\", { stateKey: eventCap.keyStr });\n        }\n        return null; // room messages are handled specially\n    }\n\n    public static for(capability: Capability, kind: WidgetKind): TranslatedCapabilityText {\n        // TODO: Support MSC3819 (to-device capabilities)\n\n        // First see if we have a super simple line of text to provide back\n        if (CapabilityText.simpleCaps[capability]) {\n            const textForKind = CapabilityText.simpleCaps[capability];\n            if (textForKind[kind]) return { primary: _t(textForKind[kind]!) };\n            if (textForKind[GENERIC_WIDGET_KIND]) return { primary: _t(textForKind[GENERIC_WIDGET_KIND]) };\n\n            // ... we'll fall through to the generic capability processing at the end of this\n            // function if we fail to generate a string for the capability.\n        }\n\n        // Try to handle timeline capabilities. The text here implies that the caller has sorted\n        // the timeline caps to the end for UI purposes.\n        if (isTimelineCapability(capability)) {\n            if (isTimelineCapabilityFor(capability, Symbols.AnyRoom)) {\n                return { primary: _t(\"widget|capability|any_room\") };\n            } else {\n                const roomId = getTimelineRoomIDFromCapability(capability);\n                const room = MatrixClientPeg.safeGet().getRoom(roomId);\n                return {\n                    primary: _t(\n                        \"widget|capability|specific_room\",\n                        {},\n                        {\n                            Room: () => {\n                                if (room) {\n                                    return (\n                                        <TextWithTooltip tooltip={room.getCanonicalAlias() ?? roomId}>\n                                            <strong>{room.name}</strong>\n                                        </TextWithTooltip>\n                                    );\n                                } else {\n                                    return (\n                                        <strong>\n                                            <code>{roomId}</code>\n                                        </strong>\n                                    );\n                                }\n                            },\n                        },\n                    ),\n                };\n            }\n        }\n\n        // We didn't have a super simple line of text, so try processing the capability as the\n        // more complex event send/receive permission type.\n        const [eventCap] = WidgetEventCapability.findEventCapabilities([capability]);\n        if (eventCap) {\n            // Special case room messages so they show up a bit cleaner to the user. Result is\n            // effectively \"Send images\" instead of \"Send messages... of type images\" if we were\n            // to handle the msgtype nuances in this function.\n            if (eventCap.kind === EventKind.Event && eventCap.eventType === EventType.RoomMessage) {\n                return CapabilityText.forRoomMessageCap(eventCap, kind);\n            }\n\n            // See if we have a static line of text to provide for the given event type and\n            // direction. The hope is that we do for common event types for friendlier copy.\n            const evSendRecv =\n                eventCap.kind === EventKind.State\n                    ? CapabilityText.stateSendRecvCaps\n                    : CapabilityText.nonStateSendRecvCaps;\n            if (evSendRecv[eventCap.eventType]) {\n                const textForKind = evSendRecv[eventCap.eventType];\n                const textForDirection = textForKind?.[kind] || textForKind?.[GENERIC_WIDGET_KIND];\n                if (textForDirection?.[eventCap.direction]) {\n                    return {\n                        primary: _t(textForDirection[eventCap.direction]),\n                        // no byline because we would have already represented the event properly\n                    };\n                }\n            }\n\n            // We don't have anything simple, so just return a generic string for the event cap\n            if (kind === WidgetKind.Room) {\n                if (eventCap.direction === EventDirection.Send) {\n                    return {\n                        primary: _t(\n                            \"widget|capability|send_event_type_this_room\",\n                            {\n                                eventType: eventCap.eventType,\n                            },\n                            {\n                                b: (sub) => <strong>{sub}</strong>,\n                            },\n                        ),\n                        byline: CapabilityText.bylineFor(eventCap),\n                    };\n                } else {\n                    return {\n                        primary: _t(\n                            \"widget|capability|see_event_type_sent_this_room\",\n                            {\n                                eventType: eventCap.eventType,\n                            },\n                            {\n                                b: (sub) => <strong>{sub}</strong>,\n                            },\n                        ),\n                        byline: CapabilityText.bylineFor(eventCap),\n                    };\n                }\n            } else {\n                // assume generic\n                if (eventCap.direction === EventDirection.Send) {\n                    return {\n                        primary: _t(\n                            \"widget|capability|send_event_type_active_room\",\n                            {\n                                eventType: eventCap.eventType,\n                            },\n                            {\n                                b: (sub) => <strong>{sub}</strong>,\n                            },\n                        ),\n                        byline: CapabilityText.bylineFor(eventCap),\n                    };\n                } else {\n                    return {\n                        primary: _t(\n                            \"widget|capability|see_event_type_sent_active_room\",\n                            {\n                                eventType: eventCap.eventType,\n                            },\n                            {\n                                b: (sub) => <strong>{sub}</strong>,\n                            },\n                        ),\n                        byline: CapabilityText.bylineFor(eventCap),\n                    };\n                }\n            }\n        }\n\n        // We don't have enough context to render this capability specially, so we'll present it as-is\n        return {\n            primary: _t(\n                \"widget|capability|capability\",\n                { capability },\n                {\n                    b: (sub) => <strong>{sub}</strong>,\n                },\n            ),\n        };\n    }\n\n    private static forRoomMessageCap(eventCap: WidgetEventCapability, kind: WidgetKind): TranslatedCapabilityText {\n        // First handle the case of \"all messages\" to make the switch later on a bit clearer\n        if (!eventCap.keyStr) {\n            if (eventCap.direction === EventDirection.Send) {\n                return {\n                    primary:\n                        kind === WidgetKind.Room\n                            ? _t(\"widget|capability|send_messages_this_room\")\n                            : _t(\"widget|capability|send_messages_active_room\"),\n                };\n            } else {\n                return {\n                    primary:\n                        kind === WidgetKind.Room\n                            ? _t(\"widget|capability|see_messages_sent_this_room\")\n                            : _t(\"widget|capability|see_messages_sent_active_room\"),\n                };\n            }\n        }\n\n        // Now handle all the message types we care about. There are more message types available, however\n        // they are not as common so we don't bother rendering them. They'll fall into the generic case.\n        switch (eventCap.keyStr) {\n            case MsgType.Text: {\n                if (eventCap.direction === EventDirection.Send) {\n                    return {\n                        primary:\n                            kind === WidgetKind.Room\n                                ? _t(\"widget|capability|send_text_messages_this_room\")\n                                : _t(\"widget|capability|send_text_messages_active_room\"),\n                    };\n                } else {\n                    return {\n                        primary:\n                            kind === WidgetKind.Room\n                                ? _t(\"widget|capability|see_text_messages_sent_this_room\")\n                                : _t(\"widget|capability|see_text_messages_sent_active_room\"),\n                    };\n                }\n            }\n            case MsgType.Emote: {\n                if (eventCap.direction === EventDirection.Send) {\n                    return {\n                        primary:\n                            kind === WidgetKind.Room\n                                ? _t(\"widget|capability|send_emotes_this_room\")\n                                : _t(\"widget|capability|send_emotes_active_room\"),\n                    };\n                } else {\n                    return {\n                        primary:\n                            kind === WidgetKind.Room\n                                ? _t(\"widget|capability|see_sent_emotes_this_room\")\n                                : _t(\"widget|capability|see_sent_emotes_active_room\"),\n                    };\n                }\n            }\n            case MsgType.Image: {\n                if (eventCap.direction === EventDirection.Send) {\n                    return {\n                        primary:\n                            kind === WidgetKind.Room\n                                ? _t(\"widget|capability|send_images_this_room\")\n                                : _t(\"widget|capability|send_images_active_room\"),\n                    };\n                } else {\n                    return {\n                        primary:\n                            kind === WidgetKind.Room\n                                ? _t(\"widget|capability|see_images_sent_this_room\")\n                                : _t(\"widget|capability|see_images_sent_active_room\"),\n                    };\n                }\n            }\n            case MsgType.Video: {\n                if (eventCap.direction === EventDirection.Send) {\n                    return {\n                        primary:\n                            kind === WidgetKind.Room\n                                ? _t(\"widget|capability|send_videos_this_room\")\n                                : _t(\"widget|capability|send_videos_active_room\"),\n                    };\n                } else {\n                    return {\n                        primary:\n                            kind === WidgetKind.Room\n                                ? _t(\"widget|capability|see_videos_sent_this_room\")\n                                : _t(\"widget|capability|see_videos_sent_active_room\"),\n                    };\n                }\n            }\n            case MsgType.File: {\n                if (eventCap.direction === EventDirection.Send) {\n                    return {\n                        primary:\n                            kind === WidgetKind.Room\n                                ? _t(\"widget|capability|send_files_this_room\")\n                                : _t(\"widget|capability|send_files_active_room\"),\n                    };\n                } else {\n                    return {\n                        primary:\n                            kind === WidgetKind.Room\n                                ? _t(\"widget|capability|see_sent_files_this_room\")\n                                : _t(\"widget|capability|see_sent_files_active_room\"),\n                    };\n                }\n            }\n            default: {\n                let primary: TranslatedString;\n                if (eventCap.direction === EventDirection.Send) {\n                    if (kind === WidgetKind.Room) {\n                        primary = _t(\n                            \"widget|capability|send_msgtype_this_room\",\n                            {\n                                msgtype: eventCap.keyStr,\n                            },\n                            {\n                                b: (sub) => <strong>{sub}</strong>,\n                            },\n                        );\n                    } else {\n                        primary = _t(\n                            \"widget|capability|send_msgtype_active_room\",\n                            {\n                                msgtype: eventCap.keyStr,\n                            },\n                            {\n                                b: (sub) => <strong>{sub}</strong>,\n                            },\n                        );\n                    }\n                } else {\n                    if (kind === WidgetKind.Room) {\n                        primary = _t(\n                            \"widget|capability|see_msgtype_sent_this_room\",\n                            {\n                                msgtype: eventCap.keyStr,\n                            },\n                            {\n                                b: (sub) => <strong>{sub}</strong>,\n                            },\n                        );\n                    } else {\n                        primary = _t(\n                            \"widget|capability|see_msgtype_sent_active_room\",\n                            {\n                                msgtype: eventCap.keyStr,\n                            },\n                            {\n                                b: (sub) => <strong>{sub}</strong>,\n                            },\n                        );\n                    }\n                }\n                return { primary };\n            }\n        }\n    }\n}\n","/*\nCopyright 2024,2025 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type ChangeEventHandler } from \"react\";\nimport {\n    type Capability,\n    isTimelineCapability,\n    type Widget,\n    WidgetEventCapability,\n    type WidgetKind,\n} from \"matrix-widget-api\";\nimport { lexicographicCompare } from \"matrix-js-sdk/src/utils\";\nimport { Form, SettingsToggleInput } from \"@vector-im/compound-web\";\n\nimport BaseDialog from \"./BaseDialog\";\nimport { _t } from \"../../../languageHandler\";\nimport { objectShallowClone } from \"../../../utils/objects\";\nimport StyledCheckbox from \"../elements/StyledCheckbox\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport { CapabilityText } from \"../../../widgets/CapabilityText\";\n\ninterface IProps {\n    requestedCapabilities: Set<Capability>;\n    widget: Widget;\n    widgetKind: WidgetKind; // TODO: Refactor into the Widget class\n    onFinished(result?: { approved: Capability[]; remember: boolean }): void;\n}\n\ntype BooleanStates = Partial<{\n    [capability in Capability]: boolean;\n}>;\n\ninterface IState {\n    booleanStates: BooleanStates;\n    rememberSelection: boolean;\n}\n\nexport default class WidgetCapabilitiesPromptDialog extends React.PureComponent<IProps, IState> {\n    private eventPermissionsMap = new Map<Capability, WidgetEventCapability>();\n\n    public constructor(props: IProps) {\n        super(props);\n\n        const parsedEvents = WidgetEventCapability.findEventCapabilities(this.props.requestedCapabilities);\n        parsedEvents.forEach((e) => this.eventPermissionsMap.set(e.raw, e));\n\n        const states: BooleanStates = {};\n        this.props.requestedCapabilities.forEach((c) => (states[c] = true));\n\n        this.state = {\n            booleanStates: states,\n            rememberSelection: true,\n        };\n    }\n\n    private onToggle = (capability: Capability): void => {\n        const newStates = objectShallowClone(this.state.booleanStates);\n        newStates[capability] = !newStates[capability];\n        this.setState({ booleanStates: newStates });\n    };\n\n    private onRememberSelectionChange: ChangeEventHandler<HTMLInputElement> = (evt): void => {\n        this.setState({ rememberSelection: evt.target.checked });\n    };\n\n    private onSubmit = async (): Promise<void> => {\n        this.closeAndTryRemember(\n            Object.entries(this.state.booleanStates)\n                .filter(([_, isSelected]) => isSelected)\n                .map(([cap]) => cap),\n        );\n    };\n\n    private onReject = async (): Promise<void> => {\n        this.closeAndTryRemember([]); // nothing was approved\n    };\n\n    private closeAndTryRemember(approved: Capability[]): void {\n        this.props.onFinished({ approved, remember: this.state.rememberSelection });\n    }\n\n    public render(): React.ReactNode {\n        // We specifically order the timeline capabilities down to the bottom. The capability text\n        // generation cares strongly about this.\n        const orderedCapabilities = Object.entries(this.state.booleanStates).sort(([capA], [capB]) => {\n            const isTimelineA = isTimelineCapability(capA);\n            const isTimelineB = isTimelineCapability(capB);\n\n            // Sort timeline capabilities to the bottom, non-timeline to the top\n            if (isTimelineA !== isTimelineB) {\n                return isTimelineA ? 1 : -1;\n            }\n\n            // Both are the same type (both timeline or both non-timeline), sort lexicographically\n            return lexicographicCompare(capA, capB);\n        });\n        const checkboxRows = orderedCapabilities.map(([cap, isChecked], i) => {\n            const text = CapabilityText.for(cap, this.props.widgetKind);\n\n            return (\n                <div className=\"mx_WidgetCapabilitiesPromptDialog_cap\" key={cap + i}>\n                    <StyledCheckbox checked={isChecked} onChange={() => this.onToggle(cap)} description={text.byline}>\n                        {text.primary}\n                    </StyledCheckbox>\n                </div>\n            );\n        });\n\n        return (\n            <BaseDialog\n                className=\"mx_WidgetCapabilitiesPromptDialog\"\n                onFinished={this.props.onFinished}\n                title={_t(\"widget|capabilities_dialog|title\")}\n            >\n                <Form.Root onSubmit={this.onSubmit}>\n                    <div className=\"mx_Dialog_content\">\n                        <div className=\"text-muted\">{_t(\"widget|capabilities_dialog|content_starting_text\")}</div>\n                        {checkboxRows}\n                        <DialogButtons\n                            primaryButton={_t(\"action|approve\")}\n                            cancelButton={_t(\"widget|capabilities_dialog|decline_all_permission\")}\n                            onPrimaryButtonClick={this.onSubmit}\n                            onCancel={this.onReject}\n                            additive={\n                                <SettingsToggleInput\n                                    name=\"remember-selection\"\n                                    checked={this.state.rememberSelection}\n                                    onChange={this.onRememberSelectionChange}\n                                    label={_t(\"widget|capabilities_dialog|remember_Selection\")}\n                                />\n                            }\n                        />\n                    </div>\n                </Form.Root>\n            </BaseDialog>\n        );\n    }\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2020-2023 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport {\n    type Capability,\n    EventDirection,\n    type IOpenIDCredentials,\n    type IOpenIDUpdate,\n    type ISendDelayedEventDetails,\n    type ISendEventDetails,\n    type ITurnServer,\n    type IReadEventRelationsResult,\n    type IRoomEvent,\n    MatrixCapabilities,\n    OpenIDRequestState,\n    type SimpleObservable,\n    type Widget,\n    WidgetDriver,\n    WidgetEventCapability,\n    WidgetKind,\n    type IWidgetApiErrorResponseDataDetails,\n    type ISearchUserDirectoryResult,\n    type IGetMediaConfigResult,\n} from \"matrix-widget-api\";\nimport {\n    ClientEvent,\n    type ITurnServer as IClientTurnServer,\n    EventType,\n    type IContent,\n    MatrixError,\n    Direction,\n    THREAD_RELATION_TYPE,\n    type SendDelayedEventResponse,\n    type StateEvents,\n    type TimelineEvents,\n    type Room,\n    type SendDelayedEventRequestOpts,\n    type MatrixClient,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport {\n    type ApprovalOpts,\n    type CapabilitiesOpts,\n    WidgetLifecycle,\n} from \"@matrix-org/react-sdk-module-api/lib/lifecycles/WidgetLifecycle\";\n\nimport { iterableDiff, iterableIntersection } from \"../../utils/iterables\";\nimport { MatrixClientPeg } from \"../../MatrixClientPeg\";\nimport Modal from \"../../Modal\";\nimport WidgetOpenIDPermissionsDialog from \"../../components/views/dialogs/WidgetOpenIDPermissionsDialog\";\nimport WidgetCapabilitiesPromptDialog from \"../../components/views/dialogs/WidgetCapabilitiesPromptDialog\";\nimport { WidgetPermissionCustomisations } from \"../../customisations/WidgetPermissions\";\nimport { OIDCState } from \"./WidgetPermissionStore\";\nimport { WidgetType } from \"../../widgets/WidgetType\";\nimport { CHAT_EFFECTS } from \"../../effects\";\nimport { containsEmoji } from \"../../effects/utils\";\nimport dis from \"../../dispatcher/dispatcher\";\nimport { ElementWidgetCapabilities } from \"./ElementWidgetCapabilities\";\nimport { navigateToPermalink } from \"../../utils/permalinks/navigator\";\nimport { SdkContextClass } from \"../../contexts/SDKContext\";\nimport { ModuleRunner } from \"../../modules/ModuleRunner\";\nimport SettingsStore from \"../../settings/SettingsStore\";\nimport { mediaFromMxc } from \"../../customisations/Media\";\n\nfunction getRememberedCapabilitiesForWidget(widget: Widget): Capability[] {\n    return JSON.parse(localStorage.getItem(`widget_${widget.id}_approved_caps`) || \"[]\");\n}\n\nfunction setRememberedCapabilitiesForWidget(widget: Widget, caps: Capability[]): void {\n    localStorage.setItem(`widget_${widget.id}_approved_caps`, JSON.stringify(caps));\n}\n\nconst normalizeTurnServer = ({ urls, username, credential }: IClientTurnServer): ITurnServer => ({\n    uris: urls,\n    username,\n    password: credential,\n});\n\n/**\n * Element Web's implementation of a widget driver (the object that\n * matrix-widget-api uses to retrieve information from the client and carry out\n * authorized actions on the widget's behalf). Essentially this is a glorified\n * set of callbacks.\n */\n// TODO: Consider alternative designs for matrix-widget-api?\n// Replace with matrix-rust-sdk?\nexport class ElementWidgetDriver extends WidgetDriver {\n    private allowedCapabilities: Set<Capability>;\n\n    // TODO: Refactor widgetKind into the Widget class\n    public constructor(\n        private forWidget: Widget,\n        private forWidgetKind: WidgetKind,\n        virtual: boolean,\n        private inRoomId?: string,\n    ) {\n        super();\n\n        // Always allow screenshots to be taken because it's a client-induced flow. The widget can't\n        // spew screenshots at us and can't request screenshots of us, so it's up to us to provide the\n        // button if the widget says it supports screenshots.\n        this.allowedCapabilities = new Set([MatrixCapabilities.Screenshots, ElementWidgetCapabilities.RequiresClient]);\n\n        // Grant the permissions that are specific to given widget types\n        if (WidgetType.JITSI.matches(this.forWidget.type) && forWidgetKind === WidgetKind.Room) {\n            this.allowedCapabilities.add(MatrixCapabilities.AlwaysOnScreen);\n        } else if (WidgetType.STICKERPICKER.matches(this.forWidget.type) && forWidgetKind === WidgetKind.Account) {\n            const stickerSendingCap = WidgetEventCapability.forRoomEvent(EventDirection.Send, EventType.Sticker).raw;\n            this.allowedCapabilities.add(MatrixCapabilities.StickerSending); // legacy as far as MSC2762 is concerned\n            this.allowedCapabilities.add(stickerSendingCap);\n\n            // Auto-approve the legacy visibility capability. We send it regardless of capability.\n            // Widgets don't technically need to request this capability, but Scalar still does.\n            this.allowedCapabilities.add(\"visibility\");\n        } else if (virtual && WidgetType.CALL.matches(this.forWidget.type) && forWidgetKind === WidgetKind.Room) {\n            // This is a trusted Element Call widget that we control\n            this.allowedCapabilities.add(MatrixCapabilities.AlwaysOnScreen);\n            this.allowedCapabilities.add(MatrixCapabilities.MSC3846TurnServers);\n            this.allowedCapabilities.add(`org.matrix.msc2762.timeline:${inRoomId}`);\n            this.allowedCapabilities.add(MatrixCapabilities.MSC4157SendDelayedEvent);\n            this.allowedCapabilities.add(MatrixCapabilities.MSC4157UpdateDelayedEvent);\n            this.allowedCapabilities.add(MatrixCapabilities.MSC4407SendStickyEvent);\n            this.allowedCapabilities.add(MatrixCapabilities.MSC4407ReceiveStickyEvent);\n\n            this.allowedCapabilities.add(\n                WidgetEventCapability.forStateEvent(EventDirection.Receive, EventType.RoomName).raw,\n            );\n            this.allowedCapabilities.add(\n                WidgetEventCapability.forStateEvent(EventDirection.Receive, EventType.RoomMember).raw,\n            );\n            this.allowedCapabilities.add(\n                WidgetEventCapability.forStateEvent(EventDirection.Receive, \"org.matrix.msc3401.call\").raw,\n            );\n            this.allowedCapabilities.add(\n                WidgetEventCapability.forStateEvent(EventDirection.Receive, EventType.RoomEncryption).raw,\n            );\n            const clientUserId = MatrixClientPeg.safeGet().getSafeUserId();\n            // For the legacy membership type\n            this.allowedCapabilities.add(\n                WidgetEventCapability.forStateEvent(EventDirection.Send, \"org.matrix.msc3401.call.member\", clientUserId)\n                    .raw,\n            );\n            const clientDeviceId = MatrixClientPeg.safeGet().getDeviceId();\n            if (clientDeviceId !== null) {\n                // For the session membership type compliant with MSC4143\n                // Note MSC4143 still uses the org.matrix.msc3401 unstable prefix\n                this.allowedCapabilities.add(\n                    WidgetEventCapability.forStateEvent(\n                        EventDirection.Send,\n                        \"org.matrix.msc3401.call.member\",\n                        `_${clientUserId}_${clientDeviceId}`,\n                    ).raw,\n                );\n                this.allowedCapabilities.add(\n                    WidgetEventCapability.forStateEvent(\n                        EventDirection.Send,\n                        \"org.matrix.msc3401.call.member\",\n                        `_${clientUserId}_${clientDeviceId}_m.call`,\n                    ).raw,\n                );\n                // Version with no leading underscore, for room versions whose auth rules allow it\n                this.allowedCapabilities.add(\n                    WidgetEventCapability.forStateEvent(\n                        EventDirection.Send,\n                        \"org.matrix.msc3401.call.member\",\n                        `${clientUserId}_${clientDeviceId}`,\n                    ).raw,\n                );\n                this.allowedCapabilities.add(\n                    WidgetEventCapability.forStateEvent(\n                        EventDirection.Send,\n                        \"org.matrix.msc3401.call.member\",\n                        `${clientUserId}_${clientDeviceId}_m.call`,\n                    ).raw,\n                );\n            }\n            this.allowedCapabilities.add(\n                WidgetEventCapability.forStateEvent(EventDirection.Receive, \"org.matrix.msc3401.call.member\").raw,\n            );\n            // for determining auth rules specific to the room version\n            this.allowedCapabilities.add(\n                WidgetEventCapability.forStateEvent(EventDirection.Receive, EventType.RoomCreate).raw,\n            );\n\n            const sendRoomEvents = [EventType.CallNotify, EventType.RTCNotification];\n            const sendRecvRoomEvents = [\n                \"io.element.call.encryption_keys\",\n                \"org.matrix.rageshake_request\",\n                EventType.Reaction,\n                EventType.RoomRedaction,\n                \"io.element.call.reaction\",\n                //  MSC4310: Add dev and final event to ease future transition,\n                EventType.RTCDecline,\n                \"m.rtc.decline\",\n                // MSC4310 The main membership event is sent via a room sticky event.\n                EventType.RTCMembership,\n                \"m.rtc.member\",\n            ];\n            for (const eventType of [...sendRoomEvents, ...sendRecvRoomEvents])\n                this.allowedCapabilities.add(WidgetEventCapability.forRoomEvent(EventDirection.Send, eventType).raw);\n            for (const eventType of sendRecvRoomEvents)\n                this.allowedCapabilities.add(WidgetEventCapability.forRoomEvent(EventDirection.Receive, eventType).raw);\n\n            const sendRecvToDevice = [\n                EventType.CallInvite,\n                EventType.CallCandidates,\n                EventType.CallAnswer,\n                EventType.CallHangup,\n                EventType.CallReject,\n                EventType.CallSelectAnswer,\n                EventType.CallNegotiate,\n                EventType.CallSDPStreamMetadataChanged,\n                EventType.CallSDPStreamMetadataChangedPrefix,\n                EventType.CallReplaces,\n                EventType.CallEncryptionKeysPrefix,\n            ];\n            for (const eventType of sendRecvToDevice) {\n                this.allowedCapabilities.add(\n                    WidgetEventCapability.forToDeviceEvent(EventDirection.Send, eventType).raw,\n                );\n                this.allowedCapabilities.add(\n                    WidgetEventCapability.forToDeviceEvent(EventDirection.Receive, eventType).raw,\n                );\n            }\n\n            // To always allow OIDC requests for element call, the widgetPermissionStore is used:\n            SdkContextClass.instance.widgetPermissionStore.setOIDCState(\n                forWidget,\n                forWidgetKind,\n                inRoomId,\n                OIDCState.Allowed,\n            );\n        }\n    }\n\n    public async validateCapabilities(requested: Set<Capability>): Promise<Set<Capability>> {\n        // Check to see if any capabilities aren't automatically accepted (such as sticker pickers\n        // allowing stickers to be sent). If there are excess capabilities to be approved, the user\n        // will be prompted to accept them.\n        const diff = iterableDiff(requested, this.allowedCapabilities);\n        const missing = new Set(diff.removed); // \"removed\" is \"in A (requested) but not in B (allowed)\"\n        const allowedSoFar = new Set(this.allowedCapabilities);\n        getRememberedCapabilitiesForWidget(this.forWidget).forEach((cap) => {\n            allowedSoFar.add(cap);\n            missing.delete(cap);\n        });\n\n        let approved: Set<string> | undefined;\n        if (WidgetPermissionCustomisations.preapproveCapabilities) {\n            approved = await WidgetPermissionCustomisations.preapproveCapabilities(this.forWidget, requested);\n        } else {\n            const opts: CapabilitiesOpts = { approvedCapabilities: undefined };\n            ModuleRunner.instance.invoke(WidgetLifecycle.CapabilitiesRequest, opts, this.forWidget, requested);\n            approved = opts.approvedCapabilities;\n        }\n        if (approved) {\n            approved.forEach((cap) => {\n                allowedSoFar.add(cap);\n                missing.delete(cap);\n            });\n        }\n\n        // TODO: Do something when the widget requests new capabilities not yet asked for\n        let rememberApproved = false;\n        if (missing.size > 0) {\n            try {\n                const [result] = await Modal.createDialog(WidgetCapabilitiesPromptDialog, {\n                    requestedCapabilities: missing,\n                    widget: this.forWidget,\n                    widgetKind: this.forWidgetKind,\n                }).finished;\n                result?.approved?.forEach((cap) => allowedSoFar.add(cap));\n                rememberApproved = !!result?.remember;\n            } catch (e) {\n                logger.error(\"Non-fatal error getting capabilities: \", e);\n            }\n        }\n\n        // discard all previously allowed capabilities if they are not requested\n        // TODO: this results in an unexpected behavior when this function is called during the capabilities renegotiation of MSC2974 that will be resolved later.\n        const allAllowed = new Set(iterableIntersection(allowedSoFar, requested));\n\n        if (rememberApproved) {\n            setRememberedCapabilitiesForWidget(this.forWidget, Array.from(allAllowed));\n        }\n\n        return allAllowed;\n    }\n\n    private getSendEventTarget(roomId: string | null = null): { client: MatrixClient; roomId: string } {\n        const client = MatrixClientPeg.safeGet();\n        roomId = roomId || SdkContextClass.instance.roomViewStore.getRoomId() || null;\n        if (!roomId) throw new Error(\"No room specified and no room in RoomViewStore focus.\");\n        return { client, roomId };\n    }\n\n    public async sendEvent<K extends keyof StateEvents>(\n        eventType: K,\n        content: StateEvents[K],\n        stateKey: string | null,\n        targetRoomId: string | null,\n    ): Promise<ISendEventDetails>;\n    public async sendEvent<K extends keyof TimelineEvents>(\n        eventType: K,\n        content: TimelineEvents[K],\n        stateKey: null,\n        targetRoomId: string | null,\n    ): Promise<ISendEventDetails>;\n    public async sendEvent(\n        eventType: string,\n        content: IContent,\n        stateKey: string | null = null,\n        targetRoomId: string | null = null,\n    ): Promise<ISendEventDetails> {\n        const { client, roomId } = this.getSendEventTarget(targetRoomId);\n\n        let r: { event_id: string } | null;\n        if (stateKey !== null) {\n            // state event\n            r = await client.sendStateEvent(\n                roomId,\n                eventType as keyof StateEvents,\n                content as StateEvents[keyof StateEvents],\n                stateKey,\n            );\n        } else if (eventType === EventType.RoomRedaction) {\n            // special case: extract the `redacts` property and call redact\n            r = await client.redactEvent(roomId, content[\"redacts\"]);\n        } else {\n            // message event\n            r = await client.sendEvent(\n                roomId,\n                eventType as keyof TimelineEvents,\n                content as TimelineEvents[keyof TimelineEvents],\n            );\n\n            if (eventType === EventType.RoomMessage) {\n                CHAT_EFFECTS.forEach((effect) => {\n                    if (containsEmoji(content, effect.emojis)) {\n                        // For initial threads launch, chat effects are disabled\n                        // see #19731\n                        const isNotThread = content[\"m.relates_to\"]?.rel_type !== THREAD_RELATION_TYPE.name;\n                        if (isNotThread) {\n                            dis.dispatch({ action: `effects.${effect.command}` });\n                        }\n                    }\n                });\n            }\n        }\n\n        return { roomId, eventId: r.event_id };\n    }\n\n    /**\n     * @experimental Part of MSC4354\n     * @see {@link WidgetDriver#sendStickyEvent}\n     */\n    public async sendStickyEvent(\n        stickyDurationMs: number,\n        eventType: string,\n        content: unknown,\n        targetRoomId?: string | null,\n    ): Promise<ISendEventDetails> {\n        const { client, roomId } = this.getSendEventTarget(targetRoomId);\n\n        const r = await client._unstable_sendStickyEvent(\n            roomId,\n            stickyDurationMs,\n            null,\n            eventType as keyof TimelineEvents,\n            content as TimelineEvents[keyof TimelineEvents] & { msc4354_sticky_key: string },\n        );\n        return { roomId, eventId: r.event_id };\n    }\n\n    private getSendDelayedEventOpts(delay: number | null, parentDelayId: string | null): SendDelayedEventRequestOpts {\n        if (delay !== null) {\n            return {\n                delay,\n                ...(parentDelayId !== null && { parent_delay_id: parentDelayId }),\n            };\n        } else if (parentDelayId !== null) {\n            return {\n                parent_delay_id: parentDelayId,\n            };\n        }\n        throw new Error(\"Must provide at least one of delay or parentDelayId\");\n    }\n\n    /**\n     * @experimental Part of MSC4140 & MSC4157\n     * @see {@link WidgetDriver#sendDelayedEvent}\n     */\n    public async sendDelayedEvent<K extends keyof StateEvents>(\n        delay: number | null,\n        parentDelayId: string | null,\n        eventType: K,\n        content: StateEvents[K],\n        stateKey: string | null,\n        targetRoomId: string | null,\n    ): Promise<ISendDelayedEventDetails>;\n    /**\n     * @experimental Part of MSC4140 & MSC4157\n     */\n    public async sendDelayedEvent<K extends keyof TimelineEvents>(\n        delay: number | null,\n        parentDelayId: string | null,\n        eventType: K,\n        content: TimelineEvents[K],\n        stateKey: null,\n        targetRoomId: string | null,\n    ): Promise<ISendDelayedEventDetails>;\n    public async sendDelayedEvent(\n        delay: number | null,\n        parentDelayId: string | null,\n        eventType: string,\n        content: IContent,\n        stateKey: string | null = null,\n        targetRoomId: string | null = null,\n    ): Promise<ISendDelayedEventDetails> {\n        const { client, roomId } = this.getSendEventTarget(targetRoomId);\n        const delayOpts = this.getSendDelayedEventOpts(delay, parentDelayId);\n\n        let r: SendDelayedEventResponse | null;\n        if (stateKey !== null) {\n            // state event\n            r = await client._unstable_sendDelayedStateEvent(\n                roomId,\n                delayOpts,\n                eventType as keyof StateEvents,\n                content as StateEvents[keyof StateEvents],\n                stateKey,\n            );\n        } else {\n            // message event\n            r = await client._unstable_sendDelayedEvent(\n                roomId,\n                delayOpts,\n                null,\n                eventType as keyof TimelineEvents,\n                content as TimelineEvents[keyof TimelineEvents],\n            );\n        }\n\n        return {\n            roomId,\n            delayId: r.delay_id,\n        };\n    }\n\n    /**\n     * @experimental Part of MSC4354\n     * @see {@link WidgetDriver#sendStickyEvent}\n     */\n    public async sendDelayedStickyEvent(\n        delay: number | null,\n        parentDelayId: string | null,\n        stickyDurationMs: number,\n        eventType: string,\n        content: unknown,\n        targetRoomId?: string | null,\n    ): Promise<ISendDelayedEventDetails> {\n        const { client, roomId } = this.getSendEventTarget(targetRoomId);\n        const delayOpts = this.getSendDelayedEventOpts(delay, parentDelayId);\n\n        const r = await client._unstable_sendStickyDelayedEvent(\n            roomId,\n            stickyDurationMs,\n            delayOpts,\n            null,\n            eventType as keyof TimelineEvents,\n            content as TimelineEvents[keyof TimelineEvents] & { msc4354_sticky_key: string },\n        );\n        return { roomId, delayId: r.delay_id };\n    }\n\n    /**\n     * @experimental Part of MSC4140 & MSC4157\n     */\n    public async cancelScheduledDelayedEvent(delayId: string): Promise<void> {\n        const client = MatrixClientPeg.get();\n\n        if (!client) throw new Error(\"Not attached to a client\");\n\n        await client._unstable_cancelScheduledDelayedEvent(delayId);\n    }\n\n    /**\n     * @experimental Part of MSC4140 & MSC4157\n     */\n    public async restartScheduledDelayedEvent(delayId: string): Promise<void> {\n        const client = MatrixClientPeg.get();\n\n        if (!client) throw new Error(\"Not attached to a client\");\n\n        await client._unstable_restartScheduledDelayedEvent(delayId);\n    }\n\n    /**\n     * @experimental Part of MSC4140 & MSC4157\n     */\n    public async sendScheduledDelayedEvent(delayId: string): Promise<void> {\n        const client = MatrixClientPeg.get();\n\n        if (!client) throw new Error(\"Not attached to a client\");\n\n        await client._unstable_sendScheduledDelayedEvent(delayId);\n    }\n\n    /**\n     * Implements {@link WidgetDriver#sendToDevice}\n     */\n    public async sendToDevice(\n        eventType: string,\n        encrypted: boolean,\n        contentMap: { [userId: string]: { [deviceId: string]: object } },\n    ): Promise<void> {\n        const client = MatrixClientPeg.safeGet();\n\n        if (encrypted) {\n            const crypto = client.getCrypto();\n            if (!crypto) throw new Error(\"E2EE not enabled\");\n\n            // attempt to re-batch these up into a single request\n            const invertedContentMap: { [content: string]: { userId: string; deviceId: string }[] } = {};\n\n            for (const userId of Object.keys(contentMap)) {\n                const userContentMap = contentMap[userId];\n                for (const deviceId of Object.keys(userContentMap)) {\n                    const content = userContentMap[deviceId];\n                    const stringifiedContent = JSON.stringify(content);\n                    invertedContentMap[stringifiedContent] = invertedContentMap[stringifiedContent] || [];\n                    invertedContentMap[stringifiedContent].push({ userId, deviceId });\n                }\n            }\n\n            await Promise.all(\n                Object.entries(invertedContentMap).map(async ([stringifiedContent, recipients]) => {\n                    const batch = await crypto.encryptToDeviceMessages(\n                        eventType,\n                        recipients,\n                        JSON.parse(stringifiedContent),\n                    );\n\n                    await client.queueToDevice(batch);\n                }),\n            );\n        } else {\n            await client.queueToDevice({\n                eventType,\n                batch: Object.entries(contentMap).flatMap(([userId, userContentMap]) =>\n                    Object.entries(userContentMap).map(([deviceId, content]) => ({\n                        userId,\n                        deviceId,\n                        payload: content,\n                    })),\n                ),\n            });\n        }\n    }\n\n    /**\n     * Generator function that retrieves events for readRoomTimeline\n     * @param room The room to check the timeline of.\n     * @param eventType The event type to be read.\n     * @param msgtype The msgtype of the events to be read, if applicable/defined.\n     * @param stateKey The state key of the events to be read, if applicable/defined.\n     * @param limit The maximum number of events to retrieve. Will be zero to denote \"as many as\n     * possible\".\n     * @param since When null, retrieves the number of events specified by the \"limit\" parameter.\n     * Otherwise, the event ID at which only subsequent events will be returned, as many as specified\n     * in \"limit\".\n     * @returns A generator that emits events.\n     */\n    private *readRoomTimelineIterator(\n        room: Room,\n        eventType: string,\n        msgtype: string | undefined,\n        stateKey: string | undefined,\n        limit: number,\n        since: string | undefined,\n    ): Generator<IRoomEvent, void, void> {\n        let resultCount: number = 0;\n        const events = [...room.getLiveTimeline().getEvents()]; // timelines are most recent last\n        for (let ev = events.pop(); ev && resultCount < limit && ev.getId() !== since; ev = events.pop()) {\n            if (ev.getType() !== eventType) continue;\n            if (eventType === EventType.RoomMessage && msgtype && msgtype !== ev.getContent()[\"msgtype\"]) continue;\n            if (stateKey !== undefined && ev.getStateKey() !== stateKey) continue;\n            yield ev.getEffectiveEvent() as IRoomEvent;\n            resultCount++;\n        }\n    }\n\n    /**\n     * Reads all events of the given type, and optionally `msgtype` (if applicable/defined),\n     * the user has access to. The widget API will have already verified that the widget is\n     * capable of receiving the events. Less events than the limit are allowed to be returned,\n     * but not more.\n     * @param roomId The ID of the room to look within.\n     * @param eventType The event type to be read.\n     * @param msgtype The msgtype of the events to be read, if applicable/defined.\n     * @param stateKey The state key of the events to be read, if applicable/defined.\n     * @param limit The maximum number of events to retrieve. Will be zero to denote \"as many as\n     * possible\".\n     * @param since When null, retrieves the number of events specified by the \"limit\" parameter.\n     * Otherwise, the event ID at which only subsequent events will be returned, as many as specified\n     * in \"limit\".\n     * @returns {Promise<IRoomEvent[]>} Resolves to the room events, or an empty array.\n     */\n    public async readRoomTimeline(\n        roomId: string,\n        eventType: string,\n        msgtype: string | undefined,\n        stateKey: string | undefined,\n        limit: number,\n        since: string | undefined,\n    ): Promise<IRoomEvent[]> {\n        limit = limit > 0 ? Math.min(limit, Number.MAX_SAFE_INTEGER) : Number.MAX_SAFE_INTEGER; // relatively arbitrary\n        const room = MatrixClientPeg.safeGet().getRoom(roomId);\n        if (room === null) return [];\n        return [...this.readRoomTimelineIterator(room, eventType, msgtype, stateKey, limit, since)];\n    }\n\n    /**\n     * Reads the current values of all matching room state entries.\n     * @param roomId The ID of the room.\n     * @param eventType The event type of the entries to be read.\n     * @param stateKey The state key of the entry to be read. If undefined,\n     * all room state entries with a matching event type should be returned.\n     * @returns {Promise<IRoomEvent[]>} Resolves to the events representing the\n     * current values of the room state entries.\n     */\n    public async readRoomState(roomId: string, eventType: string, stateKey: string | undefined): Promise<IRoomEvent[]> {\n        const room = MatrixClientPeg.safeGet().getRoom(roomId);\n        if (room === null) return [];\n        const state = room.getLiveTimeline().getState(Direction.Forward);\n        if (state === undefined) return [];\n\n        if (stateKey === undefined)\n            return state.getStateEvents(eventType).map((e) => e.getEffectiveEvent() as IRoomEvent);\n        const event = state.getStateEvents(eventType, stateKey);\n        return event === null ? [] : [event.getEffectiveEvent() as IRoomEvent];\n    }\n\n    public async askOpenID(observer: SimpleObservable<IOpenIDUpdate>): Promise<void> {\n        const opts: ApprovalOpts = { approved: undefined };\n        ModuleRunner.instance.invoke(WidgetLifecycle.IdentityRequest, opts, this.forWidget);\n        if (opts.approved) {\n            return observer.update({\n                state: OpenIDRequestState.Allowed,\n                token: await MatrixClientPeg.safeGet().getOpenIdToken(),\n            });\n        }\n\n        const oidcState = SdkContextClass.instance.widgetPermissionStore.getOIDCState(\n            this.forWidget,\n            this.forWidgetKind,\n            this.inRoomId,\n        );\n\n        const getToken = (): Promise<IOpenIDCredentials> => {\n            return MatrixClientPeg.safeGet().getOpenIdToken();\n        };\n\n        if (oidcState === OIDCState.Denied) {\n            return observer.update({ state: OpenIDRequestState.Blocked });\n        }\n        if (oidcState === OIDCState.Allowed) {\n            return observer.update({ state: OpenIDRequestState.Allowed, token: await getToken() });\n        }\n\n        observer.update({ state: OpenIDRequestState.PendingUserConfirmation });\n\n        const { finished } = Modal.createDialog(WidgetOpenIDPermissionsDialog, {\n            widget: this.forWidget,\n            widgetKind: this.forWidgetKind,\n            inRoomId: this.inRoomId,\n        });\n        const [confirm] = await finished;\n        if (!confirm) {\n            observer.update({ state: OpenIDRequestState.Blocked });\n        } else {\n            observer.update({ state: OpenIDRequestState.Allowed, token: await getToken() });\n        }\n    }\n\n    public async navigate(uri: string): Promise<void> {\n        navigateToPermalink(uri);\n    }\n\n    public async *getTurnServers(): AsyncGenerator<ITurnServer> {\n        const client = MatrixClientPeg.safeGet();\n        if (!client.pollingTurnServers || !client.getTurnServers().length) return;\n\n        let setTurnServer: (server: ITurnServer) => void;\n        let setError: (error: Error) => void;\n\n        const onTurnServers = ([server]: IClientTurnServer[]): void => setTurnServer(normalizeTurnServer(server));\n        const onTurnServersError = (error: Error, fatal: boolean): void => {\n            if (fatal) setError(error);\n        };\n\n        client.on(ClientEvent.TurnServers, onTurnServers);\n        client.on(ClientEvent.TurnServersError, onTurnServersError);\n\n        try {\n            const initialTurnServer = client.getTurnServers()[0];\n            yield normalizeTurnServer(initialTurnServer);\n\n            // Repeatedly listen for new TURN servers until an error occurs or\n            // the caller stops this generator\n            while (true) {\n                yield await new Promise<ITurnServer>((resolve, reject) => {\n                    setTurnServer = resolve;\n                    setError = reject;\n                });\n            }\n        } finally {\n            // The loop was broken - clean up\n            client.off(ClientEvent.TurnServers, onTurnServers);\n            client.off(ClientEvent.TurnServersError, onTurnServersError);\n        }\n    }\n\n    public async readEventRelations(\n        eventId: string,\n        roomId?: string,\n        relationType?: string,\n        eventType?: string,\n        from?: string,\n        to?: string,\n        limit?: number,\n        direction?: \"f\" | \"b\",\n    ): Promise<IReadEventRelationsResult> {\n        const client = MatrixClientPeg.safeGet();\n        const dir = direction as Direction;\n        roomId = roomId ?? SdkContextClass.instance.roomViewStore.getRoomId() ?? undefined;\n\n        if (typeof roomId !== \"string\") {\n            throw new Error(\"Error while reading the current room\");\n        }\n\n        const { events, nextBatch, prevBatch } = await client.relations(\n            roomId,\n            eventId,\n            relationType ?? null,\n            eventType ?? null,\n            { from, to, limit, dir },\n        );\n\n        return {\n            chunk: events.map((e) => e.getEffectiveEvent() as IRoomEvent),\n            nextBatch: nextBatch ?? undefined,\n            prevBatch: prevBatch ?? undefined,\n        };\n    }\n\n    public async searchUserDirectory(searchTerm: string, limit?: number): Promise<ISearchUserDirectoryResult> {\n        const client = MatrixClientPeg.safeGet();\n\n        const { limited, results } = await client.searchUserDirectory({ term: searchTerm, limit });\n\n        return {\n            limited,\n            results: results.map((r) => ({\n                userId: r.user_id,\n                displayName: r.display_name,\n                avatarUrl: r.avatar_url,\n            })),\n        };\n    }\n\n    public async getMediaConfig(): Promise<IGetMediaConfigResult> {\n        const client = MatrixClientPeg.safeGet();\n\n        return await client.getMediaConfig();\n    }\n\n    public async uploadFile(file: XMLHttpRequestBodyInit): Promise<{ contentUri: string }> {\n        const client = MatrixClientPeg.safeGet();\n\n        const uploadResult = await client.uploadContent(file);\n\n        return { contentUri: uploadResult.content_uri };\n    }\n\n    /**\n     * Download a file from the media repository on the homeserver.\n     *\n     * @param contentUri - the MXC URI of the file to download\n     * @returns an object with: file - response contents as Blob\n     */\n    public async downloadFile(contentUri: string): Promise<{ file: XMLHttpRequestBodyInit }> {\n        const client = MatrixClientPeg.safeGet();\n        const media = mediaFromMxc(contentUri, client);\n        const response = await media.downloadSource();\n        const blob = await response.blob();\n        return { file: blob };\n    }\n\n    /**\n     * Gets the IDs of all joined or invited rooms currently known to the\n     * client.\n     * @returns The room IDs.\n     */\n    public getKnownRooms(): string[] {\n        return MatrixClientPeg.safeGet()\n            .getVisibleRooms(SettingsStore.getValue(\"feature_dynamic_room_predecessors\"))\n            .map((r) => r.roomId);\n    }\n\n    /**\n     * Expresses a {@link MatrixError} as a JSON payload\n     * for use by Widget API error responses.\n     * @param error The error to handle.\n     * @returns The error expressed as a JSON payload,\n     * or undefined if it is not a {@link MatrixError}.\n     */\n    public processError(error: unknown): IWidgetApiErrorResponseDataDetails | undefined {\n        return error instanceof MatrixError ? { matrix_api_error: error.asWidgetApiErrorData() } : undefined;\n    }\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2020 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { arrayDiff, arrayIntersection } from \"./arrays\";\n\nexport function iterableIntersection<T>(a: Iterable<T>, b: Iterable<T>): Iterable<T> {\n    return arrayIntersection(Array.from(a), Array.from(b));\n}\n\nexport function iterableDiff<T>(a: Iterable<T>, b: Iterable<T>): { added: Iterable<T>; removed: Iterable<T> } {\n    return arrayDiff(Array.from(a), Array.from(b));\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2021 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nexport const ELEMENT_CLIENT_ID = \"io.element.web\";\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport {\n    ClientWidgetApi,\n    type IModalWidgetCloseRequest,\n    type IModalWidgetOpenRequestData,\n    type IModalWidgetReturnData,\n    type ISetModalButtonEnabledActionRequest,\n    type IWidgetApiAcknowledgeResponseData,\n    type IWidgetApiErrorResponseData,\n    BuiltInModalButtonID,\n    type ModalButtonID,\n    ModalButtonKind,\n    type Widget,\n    WidgetApiFromWidgetAction,\n    WidgetKind,\n} from \"matrix-widget-api\";\nimport { ErrorIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport BaseDialog from \"./BaseDialog\";\nimport { _t, getUserLanguage } from \"../../../languageHandler\";\nimport AccessibleButton, { type AccessibleButtonKind } from \"../elements/AccessibleButton\";\nimport { ElementWidgetDriver } from \"../../../stores/widgets/ElementWidgetDriver\";\nimport { MatrixClientPeg } from \"../../../MatrixClientPeg\";\nimport { OwnProfileStore } from \"../../../stores/OwnProfileStore\";\nimport { arrayFastClone } from \"../../../utils/arrays\";\nimport { ElementWidget } from \"../../../stores/widgets/WidgetMessaging\";\nimport { ELEMENT_CLIENT_ID } from \"../../../identifiers\";\nimport ThemeWatcher, { ThemeWatcherEvent } from \"../../../settings/watchers/ThemeWatcher\";\n\ninterface IProps {\n    widgetDefinition: IModalWidgetOpenRequestData;\n    widgetRoomId?: string;\n    sourceWidgetId: string;\n    onFinished(success: true, data: IModalWidgetReturnData): void;\n    onFinished(success?: false, data?: void): void;\n}\n\ninterface IState {\n    messaging?: ClientWidgetApi;\n    disabledButtonIds: ModalButtonID[];\n}\n\nconst MAX_BUTTONS = 3;\n\nexport default class ModalWidgetDialog extends React.PureComponent<IProps, IState> {\n    private readonly widget: Widget;\n    private readonly possibleButtons: ModalButtonID[];\n    private appFrame = React.createRef<HTMLIFrameElement>();\n    private readonly themeWatcher = new ThemeWatcher();\n\n    public state: IState = {\n        disabledButtonIds: (this.props.widgetDefinition.buttons || []).filter((b) => b.disabled).map((b) => b.id),\n    };\n\n    public constructor(props: IProps) {\n        super(props);\n\n        this.widget = new ElementWidget({\n            ...this.props.widgetDefinition,\n            creatorUserId: MatrixClientPeg.safeGet().getSafeUserId(),\n            id: `modal_${this.props.sourceWidgetId}`,\n        });\n        this.possibleButtons = (this.props.widgetDefinition.buttons || []).map((b) => b.id);\n    }\n\n    public componentDidMount(): void {\n        const driver = new ElementWidgetDriver(this.widget, WidgetKind.Modal, false);\n        const messaging = new ClientWidgetApi(this.widget, this.appFrame.current!, driver);\n        this.setState({ messaging });\n    }\n\n    public componentWillUnmount(): void {\n        this.themeWatcher.off(ThemeWatcherEvent.Change, this.onThemeChange);\n        this.themeWatcher.stop();\n        if (!this.state.messaging) return;\n        this.state.messaging.off(\"ready\", this.onReady);\n        this.state.messaging.off(`action:${WidgetApiFromWidgetAction.CloseModalWidget}`, this.onWidgetClose);\n        this.state.messaging.stop();\n    }\n\n    private onReady = (): void => {\n        this.themeWatcher.start();\n        this.themeWatcher.on(ThemeWatcherEvent.Change, this.onThemeChange);\n        // Theme may have changed while messaging was starting\n        this.onThemeChange(this.themeWatcher.getEffectiveTheme());\n        this.state.messaging?.sendWidgetConfig(this.props.widgetDefinition);\n    };\n\n    private onLoad = (): void => {\n        if (!this.state.messaging) return;\n        this.state.messaging.once(\"ready\", this.onReady);\n        this.state.messaging.on(`action:${WidgetApiFromWidgetAction.CloseModalWidget}`, this.onWidgetClose);\n        this.state.messaging.on(`action:${WidgetApiFromWidgetAction.SetModalButtonEnabled}`, this.onButtonEnableToggle);\n    };\n\n    private onThemeChange = (theme: string): void => {\n        this.state.messaging?.updateTheme({ name: theme });\n    };\n\n    private onWidgetClose = (ev: CustomEvent<IModalWidgetCloseRequest>): void => {\n        this.props.onFinished(true, ev.detail.data);\n    };\n\n    private onButtonEnableToggle = (ev: CustomEvent<ISetModalButtonEnabledActionRequest>): void => {\n        ev.preventDefault();\n        const isClose = ev.detail.data.button === BuiltInModalButtonID.Close;\n        if (isClose || !this.possibleButtons.includes(ev.detail.data.button)) {\n            return this.state.messaging?.transport.reply(ev.detail, {\n                error: { message: \"Invalid button\" },\n            } as IWidgetApiErrorResponseData);\n        }\n\n        let buttonIds: ModalButtonID[];\n        if (ev.detail.data.enabled) {\n            buttonIds = arrayFastClone(this.state.disabledButtonIds).filter((i) => i !== ev.detail.data.button);\n        } else {\n            // use a set to swap the operation to avoid memory leaky arrays.\n            const tempSet = new Set(this.state.disabledButtonIds);\n            tempSet.add(ev.detail.data.button);\n            buttonIds = Array.from(tempSet);\n        }\n        this.setState({ disabledButtonIds: buttonIds });\n        this.state.messaging?.transport.reply(ev.detail, {} as IWidgetApiAcknowledgeResponseData);\n    };\n\n    public render(): React.ReactNode {\n        const templated = this.widget.getCompleteUrl({\n            widgetRoomId: this.props.widgetRoomId,\n            currentUserId: MatrixClientPeg.safeGet().getSafeUserId(),\n            userDisplayName: OwnProfileStore.instance.displayName ?? undefined,\n            userHttpAvatarUrl: OwnProfileStore.instance.getHttpAvatarUrl() ?? undefined,\n            clientId: ELEMENT_CLIENT_ID,\n            clientTheme: this.themeWatcher.getEffectiveTheme(),\n            clientLanguage: getUserLanguage(),\n            baseUrl: MatrixClientPeg.safeGet().baseUrl,\n        });\n\n        const parsed = new URL(templated);\n\n        // Add in some legacy support sprinkles (for non-popout widgets)\n        // TODO: Replace these with proper widget params\n        // See https://github.com/matrix-org/matrix-doc/pull/1958/files#r405714833\n        parsed.searchParams.set(\"widgetId\", this.widget.id);\n        parsed.searchParams.set(\"parentUrl\", window.location.href.split(\"#\", 2)[0]);\n\n        // Replace the encoded dollar signs back to dollar signs. They have no special meaning\n        // in HTTP, but URL parsers encode them anyways.\n        const widgetUrl = parsed.toString().replace(/%24/g, \"$\");\n\n        let buttons;\n        if (this.props.widgetDefinition.buttons) {\n            // show first button rightmost for a more natural specification\n            buttons = this.props.widgetDefinition.buttons\n                .slice(0, MAX_BUTTONS)\n                .reverse()\n                .map((def) => {\n                    let kind: AccessibleButtonKind = \"secondary\";\n                    switch (def.kind) {\n                        case ModalButtonKind.Primary:\n                            kind = \"primary\";\n                            break;\n                        case ModalButtonKind.Secondary:\n                            kind = \"primary_outline\";\n                            break;\n                        case ModalButtonKind.Danger:\n                            kind = \"danger\";\n                            break;\n                    }\n\n                    const onClick = (): void => {\n                        this.state.messaging?.notifyModalWidgetButtonClicked(def.id);\n                    };\n\n                    const isDisabled = this.state.disabledButtonIds.includes(def.id);\n\n                    return (\n                        <AccessibleButton key={def.id} kind={kind} onClick={onClick} disabled={isDisabled}>\n                            {def.label}\n                        </AccessibleButton>\n                    );\n                });\n        }\n\n        return (\n            <BaseDialog\n                title={this.props.widgetDefinition.name || _t(\"widget|modal_title_default\")}\n                className=\"mx_ModalWidgetDialog\"\n                contentId=\"mx_Dialog_content\"\n                onFinished={this.props.onFinished}\n            >\n                <div className=\"mx_ModalWidgetDialog_warning\">\n                    <ErrorIcon width=\"16px\" height=\"16px\" />\n                    {_t(\"widget|modal_data_warning\", {\n                        widgetDomain: parsed.hostname,\n                    })}\n                </div>\n                <div>\n                    <iframe\n                        title={this.widget.name ?? undefined}\n                        ref={this.appFrame}\n                        sandbox=\"allow-forms allow-scripts allow-same-origin\"\n                        src={widgetUrl}\n                        onLoad={this.onLoad}\n                    />\n                </div>\n                <div className=\"mx_ModalWidgetDialog_buttons\">{buttons}</div>\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type IModalWidgetOpenRequestData, type IModalWidgetReturnData, type Widget } from \"matrix-widget-api\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { AsyncStoreWithClient } from \"./AsyncStoreWithClient\";\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport { type ActionPayload } from \"../dispatcher/payloads\";\nimport Modal, { type IHandle, type IModal } from \"../Modal\";\nimport ModalWidgetDialog from \"../components/views/dialogs/ModalWidgetDialog\";\nimport { WidgetMessagingStore } from \"./widgets/WidgetMessagingStore\";\n\ninterface IState {\n    modal?: IModal<any>;\n    openedFromId?: string;\n}\n\nexport class ModalWidgetStore extends AsyncStoreWithClient<IState> {\n    private static readonly internalInstance = (() => {\n        const instance = new ModalWidgetStore();\n        instance.start();\n        return instance;\n    })();\n    private modalInstance: IHandle<typeof ModalWidgetDialog> | null = null;\n    private openSourceWidgetId: string | null = null;\n    private openSourceWidgetRoomId: string | null = null;\n\n    private constructor() {\n        super(defaultDispatcher, {});\n    }\n\n    public static get instance(): ModalWidgetStore {\n        return ModalWidgetStore.internalInstance;\n    }\n\n    protected async onAction(payload: ActionPayload): Promise<any> {\n        // nothing\n    }\n\n    public canOpenModalWidget = (): boolean => {\n        return !this.modalInstance;\n    };\n\n    public openModalWidget = (\n        requestData: IModalWidgetOpenRequestData,\n        sourceWidget: Widget,\n        widgetRoomId?: string,\n    ): void => {\n        if (this.modalInstance) return;\n        this.openSourceWidgetId = sourceWidget.id;\n        this.openSourceWidgetRoomId = widgetRoomId ?? null;\n        this.modalInstance = Modal.createDialog(\n            ModalWidgetDialog,\n            {\n                widgetDefinition: { ...requestData },\n                widgetRoomId,\n                sourceWidgetId: sourceWidget.id,\n            },\n            undefined,\n            /* priority = */ false,\n            /* static = */ true,\n        );\n        this.modalInstance!.finished.then(([success, data]) => {\n            this.closeModalWidget(sourceWidget, widgetRoomId, success && data ? data : { \"m.exited\": true });\n\n            this.openSourceWidgetId = null;\n            this.openSourceWidgetRoomId = null;\n            this.modalInstance = null;\n        });\n    };\n\n    public closeModalWidget = (\n        sourceWidget: Widget,\n        widgetRoomId: string | undefined,\n        data: IModalWidgetReturnData,\n    ): void => {\n        if (!this.modalInstance) return;\n        if (this.openSourceWidgetId === sourceWidget.id && this.openSourceWidgetRoomId === widgetRoomId) {\n            this.openSourceWidgetId = null;\n            this.openSourceWidgetRoomId = null;\n            this.modalInstance.close();\n            this.modalInstance = null;\n\n            const sourceMessaging = WidgetMessagingStore.instance.getMessaging(sourceWidget, widgetRoomId);\n            if (!sourceMessaging?.widgetApi) {\n                logger.error(\"No source widget API for modal widget\");\n                return;\n            }\n            sourceMessaging.widgetApi.notifyModalWidgetClose(data);\n        }\n    };\n}\n\nwindow.mxModalWidgetStore = ModalWidgetStore.instance;\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2020-2022 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport {\n    type Room,\n    type MatrixEvent,\n    MatrixEventEvent,\n    type MatrixClient,\n    ClientEvent,\n    RoomStateEvent,\n    type ReceivedToDeviceMessage,\n    TypedEventEmitter,\n} from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport {\n    ClientWidgetApi,\n    type IModalWidgetOpenRequest,\n    type IRoomEvent,\n    type IStickerActionRequest,\n    type IStickyActionRequest,\n    type ITemplateParams,\n    type IWidget,\n    type IWidgetApiErrorResponseData,\n    type IWidgetApiRequest,\n    type IWidgetApiRequestEmptyData,\n    type IWidgetData,\n    MatrixCapabilities,\n    runTemplate,\n    Widget,\n    WidgetApiFromWidgetAction,\n    WidgetKind,\n} from \"matrix-widget-api\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { _t, getUserLanguage } from \"../../languageHandler\";\nimport { ElementWidgetDriver } from \"./ElementWidgetDriver\";\nimport { WidgetMessagingStore } from \"./WidgetMessagingStore\";\nimport { MatrixClientPeg } from \"../../MatrixClientPeg\";\nimport { OwnProfileStore } from \"../OwnProfileStore\";\nimport WidgetUtils from \"../../utils/WidgetUtils\";\nimport { IntegrationManagers } from \"../../integrations/IntegrationManagers\";\nimport { WidgetType } from \"../../widgets/WidgetType\";\nimport ActiveWidgetStore from \"../ActiveWidgetStore\";\nimport defaultDispatcher from \"../../dispatcher/dispatcher\";\nimport { Action } from \"../../dispatcher/actions\";\nimport { ElementWidgetActions, type IHangupCallApiRequest, type IViewRoomApiRequest } from \"./ElementWidgetActions\";\nimport { ModalWidgetStore } from \"../ModalWidgetStore\";\nimport { isAppWidget } from \"../WidgetStore\";\nimport ThemeWatcher, { ThemeWatcherEvent } from \"../../settings/watchers/ThemeWatcher\";\nimport { getCustomTheme } from \"../../theme\";\nimport { ElementWidgetCapabilities } from \"./ElementWidgetCapabilities\";\nimport { ELEMENT_CLIENT_ID } from \"../../identifiers\";\nimport { WidgetVariableCustomisations } from \"../../customisations/WidgetVariables\";\nimport { arrayFastClone } from \"../../utils/arrays\";\nimport { type ViewRoomPayload } from \"../../dispatcher/payloads/ViewRoomPayload\";\nimport Modal from \"../../Modal\";\nimport ErrorDialog from \"../../components/views/dialogs/ErrorDialog\";\nimport { SdkContextClass } from \"../../contexts/SDKContext\";\nimport { UPDATE_EVENT } from \"../AsyncStore\";\n\n// TODO: Purge this code of its overgrown hacks and compatibility shims.\n\n// TODO: Don't use this. We should avoid overriding/mocking matrix-widget-api\n// behavior and instead strive to use widgets in more transparent ways.\nexport class ElementWidget extends Widget {\n    public constructor(private rawDefinition: IWidget) {\n        super(rawDefinition);\n    }\n\n    public get templateUrl(): string {\n        if (WidgetType.JITSI.matches(this.type)) {\n            return WidgetUtils.getLocalJitsiWrapperUrl({\n                forLocalRender: true,\n                auth: super.rawData?.auth as string, // this.rawData can call templateUrl, do this to prevent looping\n            });\n        }\n        return super.templateUrl;\n    }\n\n    public get popoutTemplateUrl(): string {\n        if (WidgetType.JITSI.matches(this.type)) {\n            return WidgetUtils.getLocalJitsiWrapperUrl({\n                forLocalRender: false, // The only important difference between this and templateUrl()\n                auth: super.rawData?.auth as string,\n            });\n        }\n        return this.templateUrl; // use this instead of super to ensure we get appropriate templating\n    }\n\n    public get rawData(): IWidgetData {\n        let conferenceId = super.rawData[\"conferenceId\"];\n        if (conferenceId === undefined) {\n            // we'll need to parse the conference ID out of the URL for v1 Jitsi widgets\n            const parsedUrl = new URL(super.templateUrl); // use super to get the raw widget URL\n            conferenceId = parsedUrl.searchParams.get(\"confId\");\n        }\n        let domain = super.rawData[\"domain\"];\n        if (domain === undefined) {\n            // v1 widgets default to meet.element.io regardless of user settings\n            domain = \"meet.element.io\";\n        }\n\n        let theme = new ThemeWatcher().getEffectiveTheme();\n        if (theme.startsWith(\"custom-\")) {\n            const customTheme = getCustomTheme(theme.slice(7));\n            // Jitsi only understands light/dark\n            theme = customTheme.is_dark ? \"dark\" : \"light\";\n        }\n\n        // only allow light/dark through, defaulting to dark as that was previously the only state\n        // accounts for legacy-light/legacy-dark themes too\n        if (theme.includes(\"light\")) {\n            theme = \"light\";\n        } else {\n            theme = \"dark\";\n        }\n\n        return {\n            ...super.rawData,\n            theme,\n            conferenceId,\n            domain,\n        };\n    }\n\n    public getCompleteUrl(params: ITemplateParams, asPopout = false): string {\n        return runTemplate(\n            asPopout ? this.popoutTemplateUrl : this.templateUrl,\n            {\n                ...this.rawDefinition,\n                data: this.rawData,\n            },\n            params,\n        );\n    }\n}\n\nexport enum WidgetMessagingEvent {\n    Start = \"start\",\n    Stop = \"stop\",\n}\n\ninterface WidgetMessagingEventMap {\n    [WidgetMessagingEvent.Start]: (widgetApi: ClientWidgetApi) => void;\n    [WidgetMessagingEvent.Stop]: (widgetApi: ClientWidgetApi) => void;\n}\n\ninterface WidgetMessagingOptions {\n    app: IWidget;\n    room?: Room; // without a room it is a user widget\n    userId: string;\n    creatorUserId: string;\n    waitForIframeLoad: boolean;\n    userWidget: boolean;\n    /**\n     * If defined this async method will be called when the widget requests to become sticky.\n     * It will only become sticky once the returned promise resolves.\n     * This is useful because: Widget B is sticky. Making widget A sticky will kill widget B immediately.\n     * This promise allows to do Widget B related cleanup before Widget A becomes sticky. (e.g. hangup a Voip call)\n     */\n    stickyPromise?: () => Promise<void>;\n}\n\n/**\n * A running instance of a widget, associated with an iframe and an active communication\n * channel. Instances must be tracked by WidgetMessagingStore, as only one WidgetMessaging\n * instance should exist for a given widget.\n *\n * This class is responsible for:\n * - Computing the templated widget URL\n * - Starting a {@link ClientWidgetApi} communication channel with the widget\n * - Eagerly pushing events from the Matrix client to the widget\n *\n * @see {@link ElementWidgetDriver} for the class used to *pull* data lazily from the\n *   Matrix client to the widget on the widget's behalf.\n * @see {@link WidgetMessagingStore} for the store that holds these instances.\n */\nexport class WidgetMessaging extends TypedEventEmitter<WidgetMessagingEvent, WidgetMessagingEventMap> {\n    private client: MatrixClient;\n    private iframe: HTMLIFrameElement | null = null;\n    private scalarToken?: string;\n    private roomId?: string;\n    // The room that we're currently allowing the widget to interact with. Only\n    // used for account widgets, which may follow the user to different rooms.\n    private viewedRoomId: string | null = null;\n    private kind: WidgetKind;\n    private readonly virtual: boolean;\n    private readonly themeWatcher = new ThemeWatcher();\n    private readUpToMap: { [roomId: string]: string } = {}; // room ID to event ID\n    // This promise will be called and needs to resolve before the widget will actually become sticky.\n    private stickyPromise?: () => Promise<void>;\n    // Holds events that should be fed to the widget once they finish decrypting\n    private readonly eventsToFeed = new WeakSet<MatrixEvent>();\n\n    public constructor(\n        private readonly widget: ElementWidget,\n        options: WidgetMessagingOptions,\n    ) {\n        super();\n        this.client = MatrixClientPeg.safeGet();\n        this.roomId = options.room?.roomId;\n        this.kind = options.userWidget ? WidgetKind.Account : WidgetKind.Room; // probably\n        this.virtual = isAppWidget(options.app) && options.app.eventId === undefined;\n        this.stickyPromise = options.stickyPromise;\n    }\n\n    private _widgetApi: ClientWidgetApi | null = null;\n    private set widgetApi(value: ClientWidgetApi | null) {\n        this._widgetApi = value;\n    }\n\n    /**\n     * The widget API interface to the widget, or null if disconnected.\n     */\n    public get widgetApi(): ClientWidgetApi | null {\n        return this._widgetApi;\n    }\n\n    /**\n     * The URL to use in the iframe\n     */\n    public get embedUrl(): string {\n        return this.runUrlTemplate({ asPopout: false });\n    }\n\n    /**\n     * The URL to use in the popout\n     */\n    public get popoutUrl(): string {\n        return this.runUrlTemplate({ asPopout: true });\n    }\n\n    private runUrlTemplate(opts = { asPopout: false }): string {\n        const fromCustomisation = WidgetVariableCustomisations?.provideVariables?.() ?? {};\n        const defaults: ITemplateParams = {\n            widgetRoomId: this.roomId,\n            currentUserId: this.client.getUserId()!,\n            userDisplayName: OwnProfileStore.instance.displayName ?? undefined,\n            userHttpAvatarUrl: OwnProfileStore.instance.getHttpAvatarUrl() ?? undefined,\n            clientId: ELEMENT_CLIENT_ID,\n            clientTheme: this.themeWatcher.getEffectiveTheme(),\n            clientLanguage: getUserLanguage(),\n            deviceId: this.client.getDeviceId() ?? undefined,\n            baseUrl: this.client.baseUrl,\n        };\n        const templated = this.widget.getCompleteUrl(Object.assign(defaults, fromCustomisation), opts?.asPopout);\n\n        const parsed = new URL(templated);\n\n        // Add in some legacy support sprinkles (for non-popout widgets)\n        // TODO: Replace these with proper widget params\n        // See https://github.com/matrix-org/matrix-doc/pull/1958/files#r405714833\n        if (!opts?.asPopout) {\n            parsed.searchParams.set(\"widgetId\", this.widget.id);\n            parsed.searchParams.set(\"parentUrl\", window.location.href.split(\"#\", 2)[0]);\n\n            // Give the widget a scalar token if we're supposed to (more legacy)\n            // TODO: Stop doing this\n            if (this.scalarToken) {\n                parsed.searchParams.set(\"scalar_token\", this.scalarToken);\n            }\n        }\n\n        // Replace the encoded dollar signs back to dollar signs. They have no special meaning\n        // in HTTP, but URL parsers encode them anyways.\n        return parsed.toString().replace(/%24/g, \"$\");\n    }\n\n    private onThemeChange = (theme: string): void => {\n        this.widgetApi?.updateTheme({ name: theme });\n    };\n\n    private onOpenModal = async (ev: CustomEvent<IModalWidgetOpenRequest>): Promise<void> => {\n        ev.preventDefault();\n        if (ModalWidgetStore.instance.canOpenModalWidget()) {\n            ModalWidgetStore.instance.openModalWidget(ev.detail.data, this.widget, this.roomId);\n            this.widgetApi?.transport.reply(ev.detail, {}); // ack\n        } else {\n            this.widgetApi?.transport.reply(ev.detail, {\n                error: {\n                    message: \"Unable to open modal at this time\",\n                },\n            });\n        }\n    };\n\n    // This listener is only active for account widgets, which may follow the\n    // user to different rooms\n    private onRoomViewStoreUpdate = (): void => {\n        const roomId = SdkContextClass.instance.roomViewStore.getRoomId() ?? null;\n        if (roomId !== this.viewedRoomId) {\n            this.widgetApi!.setViewedRoomId(roomId);\n            this.viewedRoomId = roomId;\n        }\n    };\n\n    /**\n     * This starts the messaging for the widget if it is not in the state `started` yet.\n     * @param iframe the iframe the widget should use\n     */\n    public start(iframe: HTMLIFrameElement): void {\n        if (this.widgetApi !== null) return;\n\n        this.iframe = iframe;\n        const driver = new ElementWidgetDriver(this.widget, this.kind, this.virtual, this.roomId);\n\n        this.widgetApi = new ClientWidgetApi(this.widget, iframe, driver);\n        this.widgetApi.once(\"ready\", () => {\n            this.themeWatcher.start();\n            this.themeWatcher.on(ThemeWatcherEvent.Change, this.onThemeChange);\n            // Theme may have changed while messaging was starting\n            this.onThemeChange(this.themeWatcher.getEffectiveTheme());\n        });\n        this.widgetApi.on(`action:${WidgetApiFromWidgetAction.OpenModalWidget}`, this.onOpenModal);\n\n        // When widgets are listening to events, we need to make sure they're only\n        // receiving events for the right room\n        if (this.roomId === undefined) {\n            // Account widgets listen to the currently active room\n            this.widgetApi.setViewedRoomId(SdkContextClass.instance.roomViewStore.getRoomId() ?? null);\n            SdkContextClass.instance.roomViewStore.on(UPDATE_EVENT, this.onRoomViewStoreUpdate);\n        } else {\n            // Room widgets get locked to the room they were added in\n            this.widgetApi.setViewedRoomId(this.roomId);\n        }\n\n        // Always attach a handler for ViewRoom, but permission check it internally\n        this.widgetApi.on(`action:${ElementWidgetActions.ViewRoom}`, (ev: CustomEvent<IViewRoomApiRequest>) => {\n            ev.preventDefault(); // stop the widget API from auto-rejecting this\n\n            // Check up front if this is even a valid request\n            const targetRoomId = (ev.detail.data || {}).room_id;\n            if (!targetRoomId) {\n                return this.widgetApi?.transport.reply(ev.detail, <IWidgetApiErrorResponseData>{\n                    error: { message: \"Room ID not supplied.\" },\n                });\n            }\n\n            // Check the widget's permission\n            if (!this.widgetApi?.hasCapability(ElementWidgetCapabilities.CanChangeViewedRoom)) {\n                return this.widgetApi?.transport.reply(ev.detail, <IWidgetApiErrorResponseData>{\n                    error: { message: \"This widget does not have permission for this action (denied).\" },\n                });\n            }\n\n            // at this point we can change rooms, so do that\n            defaultDispatcher.dispatch<ViewRoomPayload>({\n                action: Action.ViewRoom,\n                room_id: targetRoomId,\n                metricsTrigger: \"Widget\",\n            });\n\n            // acknowledge so the widget doesn't freak out\n            this.widgetApi.transport.reply(ev.detail, <IWidgetApiRequestEmptyData>{});\n        });\n\n        // Populate the map of \"read up to\" events for this widget with the current event in every room.\n        // This is a bit inefficient, but should be okay. We do this for all rooms in case the widget\n        // requests timeline capabilities in other rooms down the road. It's just easier to manage here.\n        for (const room of this.client.getRooms()) {\n            // Timelines are most recent last\n            const events = room.getLiveTimeline()?.getEvents() || [];\n            const roomEvent = events[events.length - 1];\n            if (!roomEvent) continue; // force later code to think the room is fresh\n            this.readUpToMap[room.roomId] = roomEvent.getId()!;\n        }\n\n        // Attach listeners for feeding events - the underlying widget classes handle permissions for us\n        this.client.on(ClientEvent.Event, this.onEvent);\n        this.client.on(MatrixEventEvent.Decrypted, this.onEventDecrypted);\n        this.client.on(RoomStateEvent.Events, this.onStateUpdate);\n        this.client.on(ClientEvent.ReceivedToDeviceMessage, this.onToDeviceMessage);\n\n        this.widgetApi.on(\n            `action:${WidgetApiFromWidgetAction.UpdateAlwaysOnScreen}`,\n            async (ev: CustomEvent<IStickyActionRequest>) => {\n                if (this.widgetApi?.hasCapability(MatrixCapabilities.AlwaysOnScreen)) {\n                    ev.preventDefault();\n                    if (ev.detail.data.value) {\n                        // If the widget wants to become sticky we wait for the stickyPromise to resolve\n                        if (this.stickyPromise) await this.stickyPromise();\n                    }\n                    // Stop being persistent can be done instantly\n                    ActiveWidgetStore.instance.setWidgetPersistence(\n                        this.widget.id,\n                        this.roomId ?? null,\n                        ev.detail.data.value,\n                    );\n                    // Send the ack after the widget actually has become sticky.\n                    this.widgetApi.transport.reply(ev.detail, <IWidgetApiRequestEmptyData>{});\n                }\n            },\n        );\n\n        // TODO: Replace this event listener with appropriate driver functionality once the API\n        // establishes a sane way to send events back and forth.\n        this.widgetApi.on(\n            `action:${WidgetApiFromWidgetAction.SendSticker}`,\n            (ev: CustomEvent<IStickerActionRequest>) => {\n                if (this.widgetApi?.hasCapability(MatrixCapabilities.StickerSending)) {\n                    // Acknowledge first\n                    ev.preventDefault();\n                    this.widgetApi.transport.reply(ev.detail, <IWidgetApiRequestEmptyData>{});\n\n                    // Send the sticker\n                    defaultDispatcher.dispatch({\n                        action: \"m.sticker\",\n                        data: ev.detail.data,\n                        widgetId: this.widget.id,\n                    });\n                }\n            },\n        );\n\n        if (WidgetType.STICKERPICKER.matches(this.widget.type)) {\n            this.widgetApi.on(\n                `action:${ElementWidgetActions.OpenIntegrationManager}`,\n                (ev: CustomEvent<IWidgetApiRequest>) => {\n                    // Acknowledge first\n                    ev.preventDefault();\n                    this.widgetApi?.transport.reply(ev.detail, <IWidgetApiRequestEmptyData>{});\n\n                    // First close the stickerpicker\n                    defaultDispatcher.dispatch({ action: \"stickerpicker_close\" });\n\n                    // Now open the integration manager\n                    // TODO: Spec this interaction.\n                    const data = ev.detail.data;\n                    const integType = data?.integType as string;\n                    const integId = <string>data?.integId;\n\n                    const roomId = SdkContextClass.instance.roomViewStore.getRoomId();\n                    const room = roomId ? this.client.getRoom(roomId) : undefined;\n                    if (!room) return;\n\n                    // noinspection JSIgnoredPromiseFromCall\n                    IntegrationManagers.sharedInstance()?.getPrimaryManager()?.open(room, `type_${integType}`, integId);\n                },\n            );\n        }\n\n        if (WidgetType.JITSI.matches(this.widget.type)) {\n            this.widgetApi.on(`action:${ElementWidgetActions.HangupCall}`, (ev: CustomEvent<IHangupCallApiRequest>) => {\n                ev.preventDefault();\n                if (ev.detail.data?.errorMessage) {\n                    Modal.createDialog(ErrorDialog, {\n                        title: _t(\"widget|error_hangup_title\"),\n                        description: _t(\"widget|error_hangup_description\", {\n                            message: ev.detail.data.errorMessage,\n                        }),\n                    });\n                }\n                this.widgetApi?.transport.reply(ev.detail, <IWidgetApiRequestEmptyData>{});\n            });\n        }\n\n        this.emit(WidgetMessagingEvent.Start, this.widgetApi);\n    }\n\n    public async prepare(): Promise<void> {\n        // Ensure the variables are ready for us to be rendered before continuing\n        await (WidgetVariableCustomisations?.isReady?.() ?? Promise.resolve());\n\n        if (this.scalarToken) return;\n        try {\n            if (WidgetUtils.isScalarUrl(this.widget.templateUrl)) {\n                const managers = IntegrationManagers.sharedInstance();\n                if (managers.hasManager()) {\n                    // TODO: Pick the right manager for the widget\n                    const defaultManager = managers.getPrimaryManager();\n                    if (defaultManager && WidgetUtils.isScalarUrl(defaultManager.apiUrl)) {\n                        const scalar = defaultManager.getScalarClient();\n                        this.scalarToken = await scalar.getScalarToken();\n                    }\n                }\n            }\n        } catch (e) {\n            // All errors are non-fatal\n            logger.error(\"Error preparing widget communications: \", e);\n        }\n    }\n\n    /**\n     * Stops the widget messaging for if it is started. Skips stopping if it is an active\n     * widget.\n     * @param opts\n     */\n    public stop(opts = { forceDestroy: false }): void {\n        if (this.widgetApi === null || this.iframe === null) return;\n        if (opts.forceDestroy) {\n            // HACK: This is a really dirty way to ensure that Jitsi cleans up\n            // its hold on the webcam. Without this, the widget holds a media\n            // stream open, even after death. See https://github.com/vector-im/element-web/issues/7351\n            // In practice we could just do `+= ''` to trick the browser into\n            // thinking the URL changed, however I can foresee this being\n            // optimized out by a browser. Instead, we'll just point the iframe\n            // at a page that is reasonably safe to use in the event the iframe\n            // doesn't wink away.\n            this.iframe!.src = \"about:blank\";\n        } else if (ActiveWidgetStore.instance.getWidgetPersistence(this.widget.id, this.roomId ?? null)) {\n            logger.log(\"Skipping destroy - persistent widget\");\n            return;\n        }\n\n        this.emit(WidgetMessagingEvent.Stop, this.widgetApi);\n        this.widgetApi?.stop();\n        // XXX is the removeAllListeners necessary here?\n        this.widgetApi?.removeAllListeners(); // Insurance against resource leaks\n        this.widgetApi = null;\n        this.iframe = null;\n        WidgetMessagingStore.instance.stopMessaging(this.widget, this.roomId);\n\n        SdkContextClass.instance.roomViewStore.off(UPDATE_EVENT, this.onRoomViewStoreUpdate);\n\n        this.client.off(ClientEvent.Event, this.onEvent);\n        this.client.off(MatrixEventEvent.Decrypted, this.onEventDecrypted);\n        this.client.off(RoomStateEvent.Events, this.onStateUpdate);\n        this.client.off(ClientEvent.ReceivedToDeviceMessage, this.onToDeviceMessage);\n    }\n\n    private onEvent = (ev: MatrixEvent): void => {\n        this.client.decryptEventIfNeeded(ev);\n        this.feedEvent(ev);\n    };\n\n    private onEventDecrypted = (ev: MatrixEvent): void => {\n        this.feedEvent(ev);\n    };\n\n    private onStateUpdate = (ev: MatrixEvent): void => {\n        if (this.widgetApi === null) return;\n        const raw = ev.getEffectiveEvent();\n        this.widgetApi.feedStateUpdate(raw as IRoomEvent).catch((e) => {\n            logger.error(\"Error sending state update to widget: \", e);\n        });\n    };\n\n    private onToDeviceMessage = async ({ message, encryptionInfo }: ReceivedToDeviceMessage): Promise<void> => {\n        await this.widgetApi?.feedToDevice(message, encryptionInfo != null);\n    };\n\n    /**\n     * Determines whether the event has a relation to an unknown parent.\n     */\n    private relatesToUnknown(ev: MatrixEvent): boolean {\n        // Replies to unknown events don't count\n        if (!ev.relationEventId || ev.replyEventId) return false;\n        const room = this.client.getRoom(ev.getRoomId());\n        return room === null || !room.findEventById(ev.relationEventId);\n    }\n\n    /**\n     * Determines whether the event comes from a room that we've been invited to\n     * (in which case we likely don't have the full timeline).\n     */\n    private isFromInvite(ev: MatrixEvent): boolean {\n        const room = this.client.getRoom(ev.getRoomId());\n        return room?.getMyMembership() === KnownMembership.Invite;\n    }\n\n    /**\n     * Advances the \"read up to\" marker for a room to a certain event. No-ops if\n     * the event is before the marker.\n     * @returns Whether the \"read up to\" marker was advanced.\n     */\n    private advanceReadUpToMarker(ev: MatrixEvent): boolean {\n        const evId = ev.getId();\n        if (evId === undefined) return false;\n        const roomId = ev.getRoomId();\n        if (roomId === undefined) return false;\n        const room = this.client.getRoom(roomId);\n        if (room === null) return false;\n\n        const upToEventId = this.readUpToMap[ev.getRoomId()!];\n        if (!upToEventId) {\n            // There's no marker yet; start it at this event\n            this.readUpToMap[roomId] = evId;\n            return true;\n        }\n\n        // Small optimization for exact match (skip the search)\n        if (upToEventId === evId) return false;\n\n        // Timelines are most recent last, so reverse the order and limit ourselves to 100 events\n        // to avoid overusing the CPU.\n        const timeline = room.getLiveTimeline();\n        const events = arrayFastClone(timeline.getEvents()).reverse().slice(0, 100);\n\n        for (const timelineEvent of events) {\n            if (timelineEvent.getId() === upToEventId) {\n                // The event must be somewhere before the \"read up to\" marker\n                return false;\n            } else if (timelineEvent.getId() === ev.getId()) {\n                // The event is after the marker; advance it\n                this.readUpToMap[roomId] = evId;\n                return true;\n            }\n        }\n\n        // We can't say for sure whether the widget has seen the event; let's\n        // just assume that it has\n        return false;\n    }\n\n    private feedEvent(ev: MatrixEvent): void {\n        if (this.widgetApi === null) return;\n        if (\n            // If we had decided earlier to feed this event to the widget, but\n            // it just wasn't ready, give it another try\n            this.eventsToFeed.delete(ev) ||\n            // Skip marker timeline check for events with relations to unknown parent because these\n            // events are not added to the timeline here and will be ignored otherwise:\n            // https://github.com/matrix-org/matrix-js-sdk/blob/d3dfcd924201d71b434af3d77343b5229b6ed75e/src/models/room.ts#L2207-L2213\n            this.relatesToUnknown(ev) ||\n            // Skip marker timeline check for rooms where membership is\n            // 'invite', otherwise the membership event from the invitation room\n            // will advance the marker and new state events will not be\n            // forwarded to the widget.\n            this.isFromInvite(ev) ||\n            // Check whether this event would be before or after our \"read up to\" marker. If it's\n            // before, or we can't decide, then we assume the widget will have already seen the event.\n            // If the event is after, or we don't have a marker for the room, then the marker will advance and we'll\n            // send it through.\n            // This approach of \"read up to\" prevents widgets receiving decryption spam from startup or\n            // receiving ancient events from backfill and such.\n            this.advanceReadUpToMarker(ev)\n        ) {\n            // If the event is still being decrypted, remember that we want to\n            // feed it to the widget (even if not strictly in the order given by\n            // the timeline) and get back to it later\n            if (ev.isBeingDecrypted() || ev.isDecryptionFailure()) {\n                this.eventsToFeed.add(ev);\n            } else {\n                const raw = ev.getEffectiveEvent();\n                this.widgetApi.feedEvent(raw as IRoomEvent).catch((e) => {\n                    logger.error(\"Error sending event to widget: \", e);\n                });\n            }\n        }\n    }\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2020 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type Widget } from \"matrix-widget-api\";\nimport { type EmptyObject } from \"matrix-js-sdk/src/matrix\";\n\nimport { AsyncStoreWithClient } from \"../AsyncStoreWithClient\";\nimport defaultDispatcher from \"../../dispatcher/dispatcher\";\nimport { type ActionPayload } from \"../../dispatcher/payloads\";\nimport { EnhancedMap } from \"../../utils/maps\";\nimport WidgetUtils from \"../../utils/WidgetUtils\";\nimport { type WidgetMessaging } from \"./WidgetMessaging\";\n\nexport enum WidgetMessagingStoreEvent {\n    StoreMessaging = \"store_messaging\",\n    StopMessaging = \"stop_messaging\",\n}\n\n/**\n * Temporary holding store for widget messaging instances. This is eventually\n * going to be merged with a more complete WidgetStore, but for now it's\n * easiest to split this into a single place.\n */\nexport class WidgetMessagingStore extends AsyncStoreWithClient<EmptyObject> {\n    private static readonly internalInstance = (() => {\n        const instance = new WidgetMessagingStore();\n        instance.start();\n        return instance;\n    })();\n\n    private widgetMap = new EnhancedMap<string, WidgetMessaging>(); // <widget UID, messaging>\n\n    public constructor() {\n        super(defaultDispatcher);\n    }\n\n    public static get instance(): WidgetMessagingStore {\n        return WidgetMessagingStore.internalInstance;\n    }\n\n    protected async onAction(payload: ActionPayload): Promise<void> {\n        // nothing to do\n    }\n\n    protected async onReady(): Promise<any> {\n        // just in case\n        this.widgetMap.clear();\n    }\n\n    public storeMessaging(widget: Widget, roomId: string | undefined, messaging: WidgetMessaging): void {\n        this.stopMessaging(widget, roomId);\n        const uid = WidgetUtils.calcWidgetUid(widget.id, roomId);\n        this.widgetMap.set(uid, messaging);\n\n        this.emit(WidgetMessagingStoreEvent.StoreMessaging, uid, messaging);\n    }\n\n    public stopMessaging(widget: Widget, roomId: string | undefined): void {\n        this.stopMessagingByUid(WidgetUtils.calcWidgetUid(widget.id, roomId));\n    }\n\n    public getMessaging(widget: Widget, roomId: string | undefined): WidgetMessaging | undefined {\n        return this.widgetMap.get(WidgetUtils.calcWidgetUid(widget.id, roomId));\n    }\n\n    /**\n     * Stops the widget messaging instance for a given widget UID.\n     * @param {string} widgetUid The widget UID.\n     */\n    public stopMessagingByUid(widgetUid: string): void {\n        const messaging = this.widgetMap.remove(widgetUid);\n        if (messaging !== undefined) {\n            messaging.stop();\n            this.emit(WidgetMessagingStoreEvent.StopMessaging, widgetUid);\n        }\n    }\n\n    /**\n     * Gets the widget messaging class for a given widget UID.\n     * @param {string} widgetUid The widget UID.\n     * @returns {ClientWidgetApi} The widget API, or a falsy value if not found.\n     */\n    public getMessagingForUid(widgetUid: string): WidgetMessaging | undefined {\n        return this.widgetMap.get(widgetUid);\n    }\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2020 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type Widget, WidgetKind } from \"matrix-widget-api\";\n\nimport SettingsStore from \"../../settings/SettingsStore\";\nimport { SettingLevel } from \"../../settings/SettingLevel\";\nimport { type SdkContextClass } from \"../../contexts/SDKContext\";\n\nexport enum OIDCState {\n    Allowed, // user has set the remembered value as allowed\n    Denied, // user has set the remembered value as disallowed\n    Unknown, // user has not set a remembered value\n}\n\nexport class WidgetPermissionStore {\n    public constructor(private readonly context: SdkContextClass) {}\n\n    // TODO (all functions here): Merge widgetKind with the widget definition\n\n    private packSettingKey(widget: Widget, kind: WidgetKind, roomId?: string): string {\n        let location: string | null | undefined = roomId;\n        if (kind !== WidgetKind.Room) {\n            location = this.context.client?.getUserId();\n        }\n        if (kind === WidgetKind.Modal) {\n            location = \"*MODAL*-\" + location; // to guarantee differentiation from whatever spawned it\n        }\n        if (!location) {\n            throw new Error(\"Failed to determine a location to check the widget's OIDC state with\");\n        }\n\n        return encodeURIComponent(`${location}::${widget.templateUrl}`);\n    }\n\n    public getOIDCState(widget: Widget, kind: WidgetKind, roomId?: string): OIDCState {\n        const settingsKey = this.packSettingKey(widget, kind, roomId);\n        const settings = SettingsStore.getValue(\"widgetOpenIDPermissions\");\n        if (settings?.deny?.includes(settingsKey)) {\n            return OIDCState.Denied;\n        }\n        if (settings?.allow?.includes(settingsKey)) {\n            return OIDCState.Allowed;\n        }\n        return OIDCState.Unknown;\n    }\n\n    public setOIDCState(widget: Widget, kind: WidgetKind, roomId: string | undefined, newState: OIDCState): void {\n        const settingsKey = this.packSettingKey(widget, kind, roomId);\n\n        let currentValues = SettingsStore.getValue(\"widgetOpenIDPermissions\");\n        if (!currentValues) {\n            currentValues = {};\n        }\n        if (!currentValues.allow) currentValues.allow = [];\n        if (!currentValues.deny) currentValues.deny = [];\n\n        if (newState === OIDCState.Allowed) {\n            currentValues.allow.push(settingsKey);\n        } else if (newState === OIDCState.Denied) {\n            currentValues.deny.push(settingsKey);\n        } else {\n            currentValues.allow = currentValues.allow.filter((c) => c !== settingsKey);\n            currentValues.deny = currentValues.deny.filter((c) => c !== settingsKey);\n        }\n\n        SettingsStore.setValue(\"widgetOpenIDPermissions\", null, SettingLevel.DEVICE, currentValues);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport interface IStoredLayout {\n    // Where to store the widget. Required.\n    container: Container;\n\n    // The index (order) to position the widgets in. Only applies for\n    // ordered containers (like the top container). Smaller numbers first,\n    // and conflicts resolved by comparing widget IDs.\n    index?: number;\n\n    // Percentage (integer) for relative width of the container to consume.\n    // Clamped to 0-100 and may have minimums imposed upon it. Only applies\n    // to containers which support inner resizing (currently only the top\n    // container).\n    width?: number;\n\n    // Percentage (integer) for relative height of the container. Note that\n    // this only applies to the top container currently, and that container\n    // will take the highest value among widgets in the container. Clamped\n    // to 0-100 and may have minimums imposed on it.\n    height?: number | null;\n\n    // TODO: [Deferred] Maximizing (fullscreen) widgets by default.\n}\n\nexport interface IWidgetLayouts {\n    [widgetId: string]: IStoredLayout;\n}\n\nexport interface ILayoutStateEvent {\n    // TODO: [Deferred] Forced layout (fixed with no changes)\n\n    // The widget layouts.\n    widgets: IWidgetLayouts;\n}\n\nexport const WIDGET_LAYOUT_EVENT_TYPE = \"io.element.widgets.layout\";\n\nexport enum Container {\n    // \"Top\" is the app drawer, and currently the only sensible value.\n    Top = \"top\",\n\n    // \"Right\" is the right panel, and the default for widgets. Setting\n    // this as a container on a widget is essentially like saying \"no\n    // changes needed\", though this may change in the future.\n    Right = \"right\",\n\n    Center = \"center\",\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport \"@fontsource/inter/400.css\";\nimport \"@fontsource/inter/400-italic.css\";\nimport \"@fontsource/inter/500.css\";\nimport \"@fontsource/inter/500-italic.css\";\nimport \"@fontsource/inter/600.css\";\nimport \"@fontsource/inter/600-italic.css\";\nimport \"@fontsource/inter/700.css\";\nimport \"@fontsource/inter/700-italic.css\";\n\nimport \"@fontsource/fira-code/latin-ext-400.css\";\nimport \"@fontsource/fira-code/latin-400.css\";\nimport \"@fontsource/fira-code/latin-ext-700.css\";\nimport \"@fontsource/fira-code/latin-700.css\";\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { _t } from \"./languageHandler\";\nimport SettingsStore from \"./settings/SettingsStore\";\nimport ThemeWatcher from \"./settings/watchers/ThemeWatcher\";\nimport { FontWatcher } from \"./settings/watchers/FontWatcher\";\n\nexport const DEFAULT_THEME = \"light\";\nconst HIGH_CONTRAST_THEMES: Record<string, string> = {\n    light: \"light-high-contrast\",\n};\n\ninterface IFontFaces extends Omit<Record<(typeof allowedFontFaceProps)[number], string>, \"src\"> {\n    src: {\n        format: string;\n        url: string;\n        local: string;\n    }[];\n}\n\ninterface CompoundTheme {\n    [token: string]: string;\n}\n\nexport type CustomTheme = {\n    name: string;\n    is_dark?: boolean; // eslint-disable-line camelcase\n    colors?: {\n        [key: string]: string;\n    };\n    fonts?: {\n        faces: IFontFaces[];\n        general: string;\n        monospace: string;\n    };\n    compound?: CompoundTheme;\n};\n\n/**\n * Given a non-high-contrast theme, find the corresponding high-contrast one\n * if it exists, or return undefined if not.\n */\nexport function findHighContrastTheme(theme: string): string | undefined {\n    return HIGH_CONTRAST_THEMES[theme];\n}\n\n/**\n * Given a high-contrast theme, find the corresponding non-high-contrast one\n * if it exists, or return undefined if not.\n */\nexport function findNonHighContrastTheme(hcTheme: string): string | undefined {\n    for (const theme in HIGH_CONTRAST_THEMES) {\n        if (HIGH_CONTRAST_THEMES[theme] === hcTheme) {\n            return theme;\n        }\n    }\n}\n\n/**\n * Decide whether the supplied theme is high contrast.\n */\nexport function isHighContrastTheme(theme: string): boolean {\n    return Object.values(HIGH_CONTRAST_THEMES).includes(theme);\n}\n\nexport function enumerateThemes(): { [key: string]: string } {\n    const BUILTIN_THEMES = {\n        \"light\": _t(\"common|light\"),\n        \"light-high-contrast\": _t(\"theme|light_high_contrast\"),\n        \"dark\": _t(\"common|dark\"),\n    };\n    const customThemes = SettingsStore.getValue(\"custom_themes\") || [];\n    const customThemeNames: Record<string, string> = {};\n\n    try {\n        for (const { name } of customThemes) {\n            customThemeNames[`custom-${name}`] = name;\n        }\n    } catch (err) {\n        logger.warn(\"Error loading custom themes\", {\n            err,\n            customThemes,\n        });\n    }\n\n    return Object.assign({}, customThemeNames, BUILTIN_THEMES);\n}\n\nexport interface ITheme {\n    id: string;\n    name: string;\n}\n\nexport function getOrderedThemes(): ITheme[] {\n    const themes = Object.entries(enumerateThemes())\n        .map((p) => ({ id: p[0], name: p[1] })) // convert pairs to objects for code readability\n        .filter((p) => !isHighContrastTheme(p.id));\n    const builtInThemes = themes.filter((p) => !p.id.startsWith(\"custom-\"));\n    const collator = new Intl.Collator();\n    const customThemes = themes\n        .filter((p) => !builtInThemes.includes(p))\n        .sort((a, b) => collator.compare(a.name, b.name));\n    return [...builtInThemes, ...customThemes];\n}\n\nfunction clearCustomTheme(): void {\n    // remove all css variables (except font and emoji variables), we assume these are there because of the custom theme\n    const inlineStyleProps = Object.values(document.body.style);\n    for (const prop of inlineStyleProps) {\n        if (\n            typeof prop === \"string\" &&\n            prop.startsWith(\"--\") &&\n            prop !== FontWatcher.FONT_FAMILY_CUSTOM_PROPERTY &&\n            prop !== FontWatcher.EMOJI_FONT_FAMILY_CUSTOM_PROPERTY\n        ) {\n            document.body.style.removeProperty(prop);\n        }\n    }\n\n    // remove the custom style sheets\n    document.querySelector(\"head > style[title='custom-theme-font-faces']\")?.remove();\n    document.querySelector(\"head > style[title='custom-theme-compound']\")?.remove();\n}\n\nconst allowedFontFaceProps = [\n    \"font-display\",\n    \"font-family\",\n    \"font-stretch\",\n    \"font-style\",\n    \"font-weight\",\n    \"font-variant\",\n    \"font-feature-settings\",\n    \"font-variation-settings\",\n    \"src\",\n    \"unicode-range\",\n] as const;\n\nfunction generateCustomFontFaceCSS(faces: IFontFaces[]): string {\n    return faces\n        .map((face) => {\n            const src = face.src\n                ?.map((srcElement) => {\n                    let format = \"\";\n                    if (srcElement.format) {\n                        format = `format(\"${srcElement.format}\")`;\n                    }\n                    if (srcElement.url) {\n                        return `url(\"${srcElement.url}\") ${format}`;\n                    } else if (srcElement.local) {\n                        return `local(\"${srcElement.local}\") ${format}`;\n                    }\n                    return \"\";\n                })\n                .join(\", \");\n            const props = Object.keys(face).filter((prop) =>\n                allowedFontFaceProps.includes(prop as (typeof allowedFontFaceProps)[number]),\n            ) as Array<(typeof allowedFontFaceProps)[number]>;\n            const body = props\n                .map((prop) => {\n                    let value: string;\n                    if (prop === \"src\") {\n                        value = src;\n                    } else if (prop === \"font-family\") {\n                        value = `\"${face[prop]}\"`;\n                    } else {\n                        value = face[prop];\n                    }\n                    return `${prop}: ${value}`;\n                })\n                .join(\";\");\n            return `@font-face {${body}}`;\n        })\n        .join(\"\\n\");\n}\n\nconst COMPOUND_TOKEN = /^--cpd-[a-z0-9-]+$/;\n\n/**\n * Generates a style sheet to override Compound design tokens as specified in\n * the given theme.\n */\nfunction generateCustomCompoundCSS(theme: CompoundTheme): string {\n    const properties: string[] = [];\n    for (const [token, value] of Object.entries(theme))\n        if (COMPOUND_TOKEN.test(token)) properties.push(`${token}: ${value};`);\n        else logger.warn(`'${token}' is not a valid Compound token`);\n    // Insert the design token overrides into the 'custom' cascade layer as\n    // documented at https://compound.element.io/?path=/docs/develop-theming--docs\n    return `@layer compound.custom { :root, [class*=\"cpd-theme-\"] { ${properties.join(\" \")} } }`;\n}\n\n/**\n * Normalizes the hex colour to 8 characters (including alpha)\n * @param hexColor the hex colour to normalize\n */\nfunction normalizeHexColour(hexColor: string): string {\n    switch (hexColor.length) {\n        case 4:\n        case 5:\n            // Short RGB or RGBA hex\n            return `#${hexColor\n                .slice(1)\n                .split(\"\")\n                .map((c) => c + c)\n                .join(\"\")}`;\n        case 7:\n            // Long RGB hex\n            return `${hexColor}ff`;\n        default:\n            return hexColor;\n    }\n}\n\nfunction setHexAlpha(normalizedHexColor: string, alpha: number): string {\n    return normalizeHexColour(normalizedHexColor).slice(0, 7) + Math.round(alpha).toString(16).padStart(2, \"0\");\n}\n\nfunction parseAlpha(normalizedHexColor: string): number {\n    return parseInt(normalizedHexColor.slice(7), 16);\n}\n\nfunction setCustomThemeVars(customTheme: CustomTheme): void {\n    const { style } = document.body;\n\n    function setCSSColorVariable(name: string, hexColor: string, doPct = true): void {\n        style.setProperty(`--${name}`, hexColor);\n        const normalizedHexColor = normalizeHexColour(hexColor);\n        const baseAlpha = parseAlpha(normalizedHexColor);\n\n        if (doPct) {\n            // uses #rrggbbaa to define the color with alpha values at 0%, 15% and 50% (relative to base alpha channel)\n            style.setProperty(`--${name}-0pct`, setHexAlpha(normalizedHexColor, 0));\n            style.setProperty(`--${name}-15pct`, setHexAlpha(normalizedHexColor, baseAlpha * 0.15));\n            style.setProperty(`--${name}-50pct`, setHexAlpha(normalizedHexColor, baseAlpha * 0.5));\n        }\n    }\n\n    if (customTheme.colors) {\n        for (const [name, value] of Object.entries(customTheme.colors)) {\n            if (Array.isArray(value)) {\n                for (let i = 0; i < value.length; i += 1) {\n                    setCSSColorVariable(`${name}_${i}`, value[i], false);\n                }\n            } else {\n                setCSSColorVariable(name, value);\n            }\n        }\n    }\n    if (customTheme.fonts) {\n        const { fonts } = customTheme;\n        if (fonts.faces) {\n            const css = generateCustomFontFaceCSS(fonts.faces);\n            const style = document.createElement(\"style\");\n            style.setAttribute(\"title\", \"custom-theme-font-faces\");\n            style.setAttribute(\"type\", \"text/css\");\n            style.appendChild(document.createTextNode(css));\n            document.head.appendChild(style);\n        }\n        if (fonts.general) {\n            style.setProperty(\"--font-family\", fonts.general);\n        }\n        if (fonts.monospace) {\n            style.setProperty(\"--font-family-monospace\", fonts.monospace);\n        }\n    }\n    if (customTheme.compound) {\n        const css = generateCustomCompoundCSS(customTheme.compound);\n        const style = document.createElement(\"style\");\n        style.setAttribute(\"title\", \"custom-theme-compound\");\n        style.setAttribute(\"type\", \"text/css\");\n        style.appendChild(document.createTextNode(css));\n        document.head.appendChild(style);\n    }\n}\n\nexport function getCustomTheme(themeName: string): CustomTheme {\n    // set css variables\n    const customThemes = SettingsStore.getValue(\"custom_themes\");\n    if (!customThemes) {\n        throw new Error(`No custom themes set, can't set custom theme \"${themeName}\"`);\n    }\n    const customTheme = customThemes.find((t: CustomTheme) => t.name === themeName);\n    if (!customTheme) {\n        const knownNames = customThemes.map((t: CustomTheme) => t.name).join(\", \");\n        throw new Error(`Can't find custom theme \"${themeName}\", only know ${knownNames}`);\n    }\n    return customTheme;\n}\n\n/**\n * Called whenever someone changes the theme\n * Async function that returns once the theme has been set\n * (ie. the CSS has been loaded)\n *\n * @param {string} theme new theme\n */\nexport async function setTheme(theme?: string): Promise<void> {\n    if (!theme) {\n        const themeWatcher = new ThemeWatcher();\n        theme = themeWatcher.getEffectiveTheme();\n    }\n    clearCustomTheme();\n    let stylesheetName = theme;\n    if (theme.startsWith(\"custom-\")) {\n        const customTheme = getCustomTheme(theme.slice(7));\n        stylesheetName = customTheme.is_dark ? \"dark-custom\" : \"light-custom\";\n        setCustomThemeVars(customTheme);\n    }\n\n    // look for the stylesheet elements.\n    // styleElements is a map from style name to HTMLLinkElement.\n    const styleElements = new Map<string, HTMLLinkElement>();\n    const themes = Array.from(document.querySelectorAll<HTMLLinkElement>(\"[data-mx-theme]\"));\n    themes.forEach((theme) => {\n        styleElements.set(theme.dataset.mxTheme!.toLowerCase(), theme);\n    });\n\n    if (!styleElements.has(stylesheetName)) {\n        throw new Error(\"Unknown theme \" + stylesheetName);\n    }\n\n    // disable all of them first, then enable the one we want. Chrome only\n    // bothers to do an update on a true->false transition, so this ensures\n    // that we get exactly one update, at the right time.\n    //\n    // ^ This comment was true when we used to use alternative stylesheets\n    // for the CSS.  Nowadays we just set them all as disabled in index.html\n    // and enable them as needed.  It might be cleaner to disable them all\n    // at the same time to prevent loading two themes simultaneously and\n    // having them interact badly... but this causes a flash of unstyled app\n    // which is even uglier.  So we don't.\n\n    const styleSheet = styleElements.get(stylesheetName)!;\n    styleSheet.disabled = false;\n\n    /**\n     * Adds the Compound theme class to the top-most element in the document\n     * This will automatically refresh the colour scales based on the OS or user\n     * preferences\n     */\n    document.body.classList.remove(\"cpd-theme-light\", \"cpd-theme-dark\", \"cpd-theme-light-hc\", \"cpd-theme-dark-hc\");\n\n    let compoundThemeClassName = `cpd-theme-` + (stylesheetName.includes(\"light\") ? \"light\" : \"dark\");\n    // Always respect user OS preference!\n    if (isHighContrastTheme(theme) || window.matchMedia(\"(prefers-contrast: more)\").matches) {\n        compoundThemeClassName += \"-hc\";\n    }\n\n    document.body.classList.add(compoundThemeClassName);\n\n    return new Promise((resolve, reject) => {\n        const switchTheme = function (): void {\n            // we re-enable our theme here just in case we raced with another\n            // theme set request as per https://github.com/vector-im/element-web/issues/5601.\n            // We could alternatively lock or similar to stop the race, but\n            // this is probably good enough for now.\n            styleSheet.disabled = false;\n            styleElements.forEach((a) => {\n                if (a == styleSheet) return;\n                a.disabled = true;\n            });\n            const bodyStyles = global.getComputedStyle(document.body);\n            if (bodyStyles.backgroundColor) {\n                const metaElement = document.querySelector<HTMLMetaElement>('meta[name=\"theme-color\"]')!;\n                metaElement.content = bodyStyles.backgroundColor;\n            }\n            resolve();\n        };\n\n        const isStyleSheetLoaded = (): boolean =>\n            Boolean([...document.styleSheets].find((_styleSheet) => _styleSheet?.href === styleSheet.href));\n\n        function waitForStyleSheetLoading(): void {\n            // turns out that Firefox preloads the CSS for link elements with\n            // the disabled attribute, but Chrome doesn't.\n            if (isStyleSheetLoaded()) {\n                switchTheme();\n                return;\n            }\n\n            let counter = 0;\n\n            // In case of theme toggling (white => black => white)\n            // Chrome doesn't fire the `load` event when the white theme is selected the second times\n            const intervalId = window.setInterval(() => {\n                if (isStyleSheetLoaded()) {\n                    clearInterval(intervalId);\n                    styleSheet.onload = null;\n                    styleSheet.onerror = null;\n                    switchTheme();\n                }\n\n                // Avoid to be stuck in an endless loop if there is an issue in the stylesheet loading\n                counter++;\n                if (counter === 10) {\n                    clearInterval(intervalId);\n                    reject();\n                }\n            }, 200);\n\n            styleSheet.onload = () => {\n                clearInterval(intervalId);\n                switchTheme();\n            };\n\n            styleSheet.onerror = (e) => {\n                clearInterval(intervalId);\n                reject(e);\n            };\n        }\n\n        waitForStyleSheetLoading();\n    });\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { _t } from \"../languageHandler\";\nimport Notifier from \"../Notifier\";\nimport GenericToast from \"../components/views/toasts/GenericToast\";\nimport ToastStore from \"../stores/ToastStore\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport { getLocalNotificationAccountDataEventType } from \"../utils/notifications\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { SettingLevel } from \"../settings/SettingLevel\";\n\nconst onAccept = async (): Promise<void> => {\n    await SettingsStore.setValue(\"notificationsEnabled\", null, SettingLevel.DEVICE, true);\n    const cli = MatrixClientPeg.safeGet();\n    const eventType = getLocalNotificationAccountDataEventType(cli.deviceId!);\n    cli.setAccountData(eventType, {\n        is_silenced: false,\n    });\n};\n\nconst onReject = (): void => {\n    Notifier.setPromptHidden(true);\n};\n\nconst TOAST_KEY = \"desktopnotifications\";\n\nexport const showToast = (fromMessageSend: boolean): void => {\n    ToastStore.sharedInstance().addOrReplaceToast({\n        key: TOAST_KEY,\n        title: fromMessageSend\n            ? _t(\"notifications|enable_prompt_toast_title_from_message_send\")\n            : _t(\"notifications|enable_prompt_toast_title\"),\n        props: {\n            description: _t(\"notifications|enable_prompt_toast_description\"),\n            primaryLabel: _t(\"action|enable\"),\n            onPrimaryClick: onAccept,\n            secondaryLabel: _t(\"action|dismiss\"),\n            onSecondaryClick: onReject,\n        },\n        component: GenericToast,\n        priority: 30,\n    });\n};\n\nexport const hideToast = (): void => {\n    ToastStore.sharedInstance().dismissToast(TOAST_KEY);\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2016 Aviral Dasgupta\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n */\n\nimport React, { type JSX } from \"react\";\n\nimport { _t } from \"../../../languageHandler\";\nimport QuestionDialog from \"./QuestionDialog\";\nimport Spinner from \"../elements/Spinner\";\nimport Heading from \"../typography/Heading\";\n\ninterface IProps {\n    newVersion: DevelopVersionString;\n    version: DevelopVersionString;\n    onFinished: (success: boolean) => void;\n}\n\ntype State = Partial<Record<(typeof REPOS)[number], null | string | Commit[]>>;\n\ninterface Commit {\n    sha: string;\n    html_url: string;\n    commit: {\n        message: string;\n    };\n}\n\nconst REPOS = [\"element-hq/element-web\", \"matrix-org/matrix-js-sdk\"] as const;\n\nexport type DevelopVersionString = string & { _developVersionString: never };\n\n/*\n * Parse a version string is compatible with the Changelog dialog ([element-version]-js-[js-sdk-version])\n */\nexport function parseVersion(version: string): Record<(typeof REPOS)[number], string> | null {\n    const parts = version.split(\"-\");\n    if (parts.length === 3 && parts[1] === \"js\") {\n        const obj: Record<string, string> = {};\n        for (let i = 0; i < REPOS.length; i++) {\n            const commit = parts[2 * i];\n            obj[REPOS[i]] = commit;\n        }\n        return obj;\n    }\n    return null;\n}\n\nexport function checkVersion(version: string): version is DevelopVersionString {\n    return parseVersion(version) !== null;\n}\n\nexport default class ChangelogDialog extends React.Component<IProps, State> {\n    public constructor(props: IProps) {\n        super(props);\n\n        this.state = {};\n    }\n\n    private async fetchChanges(repo: (typeof REPOS)[number], oldVersion: string, newVersion: string): Promise<void> {\n        const url = `https://riot.im/github/repos/${repo}/compare/${oldVersion}...${newVersion}`;\n\n        try {\n            const res = await fetch(url);\n\n            if (!res.ok) {\n                this.setState({ [repo]: res.statusText });\n                return;\n            }\n\n            const body = await res.json();\n            this.setState({ [repo]: body.commits });\n        } catch (err) {\n            this.setState({ [repo]: err instanceof Error ? err.message : _t(\"error|unknown\") });\n        }\n    }\n\n    public componentDidMount(): void {\n        const commits = parseVersion(this.props.version)!;\n        const newCommits = parseVersion(this.props.newVersion)!;\n\n        for (const repo of REPOS) {\n            this.fetchChanges(repo, commits[repo], newCommits[repo]);\n        }\n    }\n\n    private elementsForCommit(commit: Commit): JSX.Element {\n        return (\n            <li key={commit.sha} className=\"mx_ChangelogDialog_li\">\n                <a href={commit.html_url} target=\"_blank\" rel=\"noreferrer noopener\">\n                    {commit.commit.message.split(\"\\n\")[0]}\n                </a>\n            </li>\n        );\n    }\n\n    public render(): React.ReactNode {\n        const logs = REPOS.map((repo) => {\n            let content;\n            if (this.state[repo] == null) {\n                content = <Spinner key={repo} />;\n            } else if (typeof this.state[repo] === \"string\") {\n                content = _t(\"update|error_unable_load_commit\", {\n                    msg: this.state[repo],\n                });\n            } else {\n                content = (this.state[repo] as Commit[]).map(this.elementsForCommit);\n            }\n            return (\n                <div key={repo}>\n                    <Heading as=\"h2\" size=\"4\">\n                        {repo}\n                    </Heading>\n                    <ul>{content}</ul>\n                </div>\n            );\n        });\n\n        const content = (\n            <div className=\"mx_ChangelogDialog_content\">\n                {this.props.version == null || this.props.newVersion == null ? (\n                    <h2>{_t(\"update|unavailable\")}</h2>\n                ) : (\n                    logs\n                )}\n            </div>\n        );\n\n        return (\n            <QuestionDialog\n                title={_t(\"update|changelog\")}\n                description={content}\n                button={_t(\"action|update\")}\n                onFinished={this.props.onFinished}\n            />\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport { _t } from \"../languageHandler\";\nimport SdkConfig from \"../SdkConfig\";\nimport GenericToast from \"../components/views/toasts/GenericToast\";\nimport ToastStore from \"../stores/ToastStore\";\nimport QuestionDialog from \"../components/views/dialogs/QuestionDialog\";\nimport ChangelogDialog, { checkVersion } from \"../components/views/dialogs/ChangelogDialog\";\nimport PlatformPeg from \"../PlatformPeg\";\nimport Modal from \"../Modal\";\n\nconst TOAST_KEY = \"update\";\n\nfunction installUpdate(): void {\n    PlatformPeg.get()?.installUpdate();\n}\n\nexport const showToast = (version: string, newVersion: string, releaseNotes?: string): void => {\n    function onReject(): void {\n        PlatformPeg.get()?.deferUpdate(newVersion);\n    }\n\n    let onAccept;\n    let acceptLabel = _t(\"update|see_changes_button\");\n    if (releaseNotes) {\n        onAccept = () => {\n            const { finished } = Modal.createDialog(QuestionDialog, {\n                title: _t(\"update|release_notes_toast_title\"),\n                description: <pre>{releaseNotes}</pre>,\n                button: _t(\"action|update\"),\n            });\n            finished.then(([update]) => {\n                if (update && PlatformPeg.get()) {\n                    PlatformPeg.get()!.installUpdate();\n                }\n            });\n        };\n    } else if (checkVersion(version) && checkVersion(newVersion)) {\n        onAccept = () => {\n            const { finished } = Modal.createDialog(ChangelogDialog, {\n                version,\n                newVersion,\n            });\n            finished.then(([update]) => {\n                if (update && PlatformPeg.get()) {\n                    PlatformPeg.get()!.installUpdate();\n                }\n            });\n        };\n    } else {\n        onAccept = installUpdate;\n        acceptLabel = _t(\"action|update\");\n    }\n\n    const brand = SdkConfig.get().brand;\n    ToastStore.sharedInstance().addOrReplaceToast({\n        key: TOAST_KEY,\n        title: _t(\"update|toast_title\", { brand }),\n        props: {\n            description: _t(\"update|toast_description\", { brand }),\n            primaryLabel: acceptLabel,\n            onPrimaryClick: onAccept,\n            secondaryLabel: _t(\"action|dismiss\"),\n            onSecondaryClick: onReject,\n        },\n        component: GenericToast,\n        priority: 20,\n    });\n};\n\nexport const hideToast = (): void => {\n    ToastStore.sharedInstance().dismissToast(TOAST_KEY);\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MouseEvent } from \"react\";\n\nexport function chromeFileInputFix(event: MouseEvent<HTMLInputElement>): void {\n    // Workaround for Chromium Bug\n    // Chrome does not fire onChange events if the same file is selected twice\n    // Only required on Chromium-based browsers (Electron, Chrome, Edge, Opera, Vivaldi, etc)\n    event.currentTarget.value = \"\";\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2016-2019 , 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { uniq } from \"lodash\";\nimport { type Room, type MatrixEvent, EventType, ClientEvent, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { filterValidMDirect } from \"./dm/filterValidMDirect\";\n\n/**\n * Class that takes a Matrix Client and flips the m.direct map\n * so the operation of mapping a room ID to which user it's a DM\n * with can be performed efficiently.\n *\n * With 'start', this can also keep itself up to date over time.\n */\nexport default class DMRoomMap {\n    private static sharedInstance: DMRoomMap;\n\n    // TODO: convert these to maps\n    private roomToUser: { [key: string]: string } | null = null;\n    private userToRooms: { [key: string]: string[] } | null = null;\n    private hasSentOutPatchDirectAccountDataPatch: boolean;\n    private mDirectEvent!: { [key: string]: string[] };\n\n    public constructor(private readonly matrixClient: MatrixClient) {\n        // see onAccountData\n        this.hasSentOutPatchDirectAccountDataPatch = false;\n\n        const mDirectRawContent = matrixClient.getAccountData(EventType.Direct)?.getContent() ?? {};\n        this.setMDirectFromContent(mDirectRawContent);\n    }\n\n    /**\n     * Makes and returns a new shared instance that can then be accessed\n     * with shared(). This returned instance is not automatically started.\n     */\n    public static makeShared(matrixClient: MatrixClient): DMRoomMap {\n        DMRoomMap.sharedInstance = new DMRoomMap(matrixClient);\n        return DMRoomMap.sharedInstance;\n    }\n\n    /**\n     * Set the shared instance to the instance supplied\n     * Used by tests\n     * @param inst the new shared instance\n     */\n    public static setShared(inst: DMRoomMap): void {\n        DMRoomMap.sharedInstance = inst;\n    }\n\n    /**\n     * Returns a shared instance of the class\n     * that uses the singleton matrix client\n     * The shared instance must be started before use.\n     */\n    public static shared(): DMRoomMap {\n        return DMRoomMap.sharedInstance;\n    }\n\n    public start(): void {\n        this.populateRoomToUser();\n        this.matrixClient.on(ClientEvent.AccountData, this.onAccountData);\n    }\n\n    public stop(): void {\n        this.matrixClient.removeListener(ClientEvent.AccountData, this.onAccountData);\n    }\n\n    /**\n     * Filter m.direct content to contain only valid data and then sets it.\n     * Logs if invalid m.direct content occurs.\n     * {@link filterValidMDirect}\n     *\n     * @param content - Raw m.direct content\n     */\n    private setMDirectFromContent(content: unknown): void {\n        const { valid, filteredContent } = filterValidMDirect(content);\n\n        if (!valid) {\n            logger.warn(\"Invalid m.direct content occurred\", content);\n        }\n\n        this.mDirectEvent = filteredContent;\n    }\n\n    private onAccountData = (ev: MatrixEvent): void => {\n        if (ev.getType() == EventType.Direct) {\n            this.setMDirectFromContent(ev.getContent());\n            this.userToRooms = null;\n            this.roomToUser = null;\n        }\n    };\n\n    /**\n     * some client bug somewhere is causing some DMs to be marked\n     * with ourself, not the other user. Fix it by guessing the other user and\n     * modifying userToRooms\n     */\n    private patchUpSelfDMs(userToRooms: Record<string, string[]>): boolean {\n        const myUserId = this.matrixClient.getUserId()!;\n        const selfRoomIds = userToRooms[myUserId];\n        if (selfRoomIds) {\n            // any self-chats that should not be self-chats?\n            const guessedUserIdsThatChanged = selfRoomIds\n                .map((roomId) => {\n                    const room = this.matrixClient.getRoom(roomId);\n                    if (room) {\n                        const userId = room.guessDMUserId();\n                        if (userId && userId !== myUserId) {\n                            return { userId, roomId };\n                        }\n                    }\n                })\n                .filter((ids) => !!ids) as { userId: string; roomId: string }[]; //filter out\n            // these are actually all legit self-chats\n            // bail out\n            if (!guessedUserIdsThatChanged.length) {\n                return false;\n            }\n            userToRooms[myUserId] = selfRoomIds.filter((roomId) => {\n                return !guessedUserIdsThatChanged.some((ids) => ids.roomId === roomId);\n            });\n            guessedUserIdsThatChanged.forEach(({ userId, roomId }) => {\n                const roomIds = userToRooms[userId];\n                if (!roomIds) {\n                    userToRooms[userId] = [roomId];\n                } else {\n                    roomIds.push(roomId);\n                    userToRooms[userId] = uniq(roomIds);\n                }\n            });\n            return true;\n        }\n        return false;\n    }\n\n    public getDMRoomsForUserId(userId: string): string[] {\n        // Here, we return the empty list if there are no rooms,\n        // since the number of conversations you have with this user is zero.\n        return this.getUserToRooms()[userId] || [];\n    }\n\n    /**\n     * Gets the DM room which the given IDs share, if any.\n     * @param {string[]} ids The identifiers (user IDs and email addresses) to look for.\n     * @returns {Room} The DM room which all IDs given share, or falsy if no common room.\n     */\n    public getDMRoomForIdentifiers(ids: string[]): Room | null {\n        // TODO: [Canonical DMs] Handle lookups for email addresses.\n        // For now we'll pretend we only get user IDs and end up returning nothing for email addresses\n\n        let commonRooms = this.getDMRoomsForUserId(ids[0]);\n        for (let i = 1; i < ids.length; i++) {\n            const userRooms = this.getDMRoomsForUserId(ids[i]);\n            commonRooms = commonRooms.filter((r) => userRooms.includes(r));\n        }\n\n        const joinedRooms = commonRooms\n            .map((r) => this.matrixClient.getRoom(r))\n            .filter((r) => r && r.getMyMembership() === KnownMembership.Join);\n\n        return joinedRooms[0];\n    }\n\n    public getUserIdForRoomId(roomId: string): string | undefined {\n        if (this.roomToUser == null) {\n            // we lazily populate roomToUser so you can use\n            // this class just to call getDMRoomsForUserId\n            // which doesn't do very much, but is a fairly\n            // convenient wrapper and there's no point\n            // iterating through the map if getUserIdForRoomId()\n            // is never called.\n            this.populateRoomToUser();\n        }\n        // Here, we return undefined if the room is not in the map:\n        // the room ID you gave is not a DM room for any user.\n        if (this.roomToUser![roomId] === undefined) {\n            // no entry? if the room is an invite, look for the is_direct hint.\n            const room = this.matrixClient.getRoom(roomId);\n            if (room) {\n                return room.getDMInviter();\n            }\n        }\n        return this.roomToUser![roomId];\n    }\n\n    public getUniqueRoomsWithIndividuals(): { [userId: string]: Room } {\n        if (!this.roomToUser) return {}; // No rooms means no map.\n        // map roomToUser to valid rooms with two participants\n        return Object.keys(this.roomToUser).reduce(\n            (acc, roomId: string) => {\n                const userId = this.getUserIdForRoomId(roomId);\n                const room = this.matrixClient.getRoom(roomId);\n                const hasTwoMembers = room?.getInvitedAndJoinedMemberCount() === 2;\n                if (userId && room && hasTwoMembers) {\n                    acc[userId] = room;\n                }\n                return acc;\n            },\n            {} as Record<string, Room>,\n        );\n    }\n\n    /**\n     * @returns all room Ids from m.direct\n     */\n    public getRoomIds(): Set<string> {\n        return Object.values(this.mDirectEvent).reduce((prevRoomIds: Set<string>, roomIds: string[]): Set<string> => {\n            roomIds.forEach((roomId) => prevRoomIds.add(roomId));\n            return prevRoomIds;\n        }, new Set<string>());\n    }\n\n    private getUserToRooms(): { [key: string]: string[] } {\n        if (!this.userToRooms) {\n            const userToRooms = this.mDirectEvent;\n            const myUserId = this.matrixClient.getUserId()!;\n            const selfDMs = userToRooms[myUserId];\n            if (selfDMs?.length) {\n                const neededPatching = this.patchUpSelfDMs(userToRooms);\n                // to avoid multiple devices fighting to correct\n                // the account data, only try to send the corrected\n                // version once.\n                logger.warn(`Invalid m.direct account data detected (self-chats that shouldn't be), patching it up.`);\n                if (neededPatching && !this.hasSentOutPatchDirectAccountDataPatch) {\n                    this.hasSentOutPatchDirectAccountDataPatch = true;\n                    this.matrixClient.setAccountData(EventType.Direct, userToRooms);\n                }\n            }\n            this.userToRooms = userToRooms;\n        }\n        return this.userToRooms;\n    }\n\n    private populateRoomToUser(): void {\n        this.roomToUser = {};\n        for (const user of Object.keys(this.getUserToRooms())) {\n            for (const roomId of this.userToRooms![user]) {\n                this.roomToUser[roomId] = user;\n            }\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2016-2018 , 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// Pull in the encryption lib so that we can decrypt attachments.\nimport encrypt from \"matrix-encrypt-attachment\";\nimport { parseErrorResponse } from \"matrix-js-sdk/src/matrix\";\nimport { type EncryptedFile, type MediaEventInfo } from \"matrix-js-sdk/src/types\";\n\nimport { mediaFromContent } from \"../customisations/Media\";\nimport { getBlobSafeMimeType } from \"./blobs\";\n\nexport class DownloadError extends Error {\n    public constructor(e: Error) {\n        super(e.message);\n        this.name = \"DownloadError\";\n        this.stack = e.stack;\n    }\n}\n\nexport class DecryptError extends Error {\n    public constructor(e: Error) {\n        super(e.message);\n        this.name = \"DecryptError\";\n        this.stack = e.stack;\n    }\n}\n\n/**\n * Decrypt a file attached to a matrix event.\n * @param {EncryptedFile} file The encrypted file information taken from the matrix event.\n *   This passed to [link]{@link https://github.com/matrix-org/matrix-encrypt-attachment}\n *   as the encryption info object, so will also have the those keys in addition to\n *   the keys below.\n * @param {MediaEventInfo} info The info parameter taken from the matrix event.\n * @returns {Promise<Blob>} Resolves to a Blob of the file.\n */\nexport async function decryptFile(file?: EncryptedFile, info?: MediaEventInfo): Promise<Blob> {\n    // throws if file is falsy\n    const media = mediaFromContent({ file });\n\n    let responseData: ArrayBuffer;\n    try {\n        // Download the encrypted file as an array buffer.\n        const response = await media.downloadSource();\n        if (!response.ok) {\n            throw parseErrorResponse(response, await response.text());\n        }\n        responseData = await response.arrayBuffer();\n    } catch (e) {\n        throw new DownloadError(e as Error);\n    }\n\n    try {\n        // Decrypt the array buffer using the information taken from the event content.\n        const dataArray = await encrypt.decryptAttachment(responseData, file!);\n        // Turn the array into a Blob and give it the correct MIME-type.\n\n        // IMPORTANT: we must not allow scriptable mime-types into Blobs otherwise\n        // they introduce XSS attacks if the Blob URI is viewed directly in the\n        // browser (e.g. by copying the URI into a new tab or window.)\n        // See warning at top of file.\n        const mimetype = getBlobSafeMimeType(info?.mimetype?.split(\";\")[0].trim() ?? \"\");\n\n        return new Blob([dataArray], { type: mimetype });\n    } catch (e) {\n        throw new DecryptError(e as Error);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    EventStatus,\n    MatrixEvent,\n    EventType,\n    EVENT_VISIBILITY_CHANGE_TYPE,\n    MsgType,\n    RelationType,\n    type MatrixClient,\n    THREAD_RELATION_TYPE,\n    M_POLL_END,\n    M_POLL_START,\n    M_LOCATION,\n    M_BEACON_INFO,\n} from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport shouldHideEvent from \"../shouldHideEvent\";\nimport { type GetRelationsForEvent } from \"../components/views/rooms/EventTile\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport { type TimelineRenderingType } from \"../contexts/RoomContext\";\nimport { launchPollEditor } from \"../components/views/messages/MPollBody\";\nimport { Action } from \"../dispatcher/actions\";\nimport { type ViewRoomPayload } from \"../dispatcher/payloads/ViewRoomPayload\";\nimport { ModuleApi } from \"../modules/Api\";\n\n/**\n * Returns whether an event should allow actions like reply, reactions, edit, etc.\n * which effectively checks whether it's a regular message that has been sent and that we\n * can display.\n *\n * @param {MatrixEvent} mxEvent The event to check\n * @returns {boolean} true if actionable\n */\nexport function isContentActionable(mxEvent: MatrixEvent): boolean {\n    const { status: eventStatus } = mxEvent;\n\n    // status is SENT before remote-echo, null after\n    const isSent = !eventStatus || eventStatus === EventStatus.SENT;\n\n    if (isSent && !mxEvent.isRedacted()) {\n        if (mxEvent.getType() === \"m.room.message\") {\n            const content = mxEvent.getContent();\n            if (content.msgtype && content.msgtype !== \"m.bad.encrypted\" && content.hasOwnProperty(\"body\")) {\n                return true;\n            }\n        } else if (\n            mxEvent.getType() === \"m.sticker\" ||\n            M_POLL_START.matches(mxEvent.getType()) ||\n            M_POLL_END.matches(mxEvent.getType()) ||\n            M_BEACON_INFO.matches(mxEvent.getType())\n        ) {\n            return true;\n        }\n    }\n\n    return false;\n}\n\nexport function canEditContent(matrixClient: MatrixClient, mxEvent: MatrixEvent): boolean {\n    const isCancellable = mxEvent.getType() === EventType.RoomMessage || M_POLL_START.matches(mxEvent.getType());\n\n    if (\n        !isCancellable ||\n        // Editing local echos is not supported(results in send a message that references the local ID).\n        // We need to ensure the event is not local, and therefore has no send status.\n        mxEvent.status !== null ||\n        mxEvent.isRedacted() ||\n        mxEvent.isRelation(RelationType.Replace) ||\n        mxEvent.getSender() !== matrixClient.getUserId()\n    ) {\n        return false;\n    }\n\n    if (ModuleApi.instance.customComponents.getHintsForMessage(mxEvent)?.allowEditingEvent === false) {\n        return false;\n    }\n\n    const { msgtype, body } = mxEvent.getOriginalContent();\n    return (\n        M_POLL_START.matches(mxEvent.getType()) ||\n        ((msgtype === MsgType.Text || msgtype === MsgType.Emote) && !!body && typeof body === \"string\")\n    );\n}\n\nexport function canEditOwnEvent(matrixClient: MatrixClient, mxEvent: MatrixEvent): boolean {\n    // for now we only allow editing\n    // your own events. So this just call through\n    // In the future though, moderators will be able to\n    // edit other people's messages as well but we don't\n    // want findEditableEvent to return other people's events\n    // hence this method.\n    return canEditContent(matrixClient, mxEvent);\n}\n\nconst MAX_JUMP_DISTANCE = 100;\nexport function findEditableEvent({\n    matrixClient,\n    events,\n    isForward,\n    fromEventId,\n}: {\n    matrixClient: MatrixClient;\n    events: MatrixEvent[];\n    isForward: boolean;\n    fromEventId?: string;\n}): MatrixEvent | undefined {\n    if (!events.length) return;\n    const maxIdx = events.length - 1;\n    const inc = isForward ? 1 : -1;\n    const beginIdx = isForward ? 0 : maxIdx;\n    let endIdx = isForward ? maxIdx : 0;\n    if (!fromEventId) {\n        endIdx = Math.min(Math.max(0, beginIdx + inc * MAX_JUMP_DISTANCE), maxIdx);\n    }\n    let foundFromEventId = !fromEventId;\n    for (let i = beginIdx; i !== endIdx + inc; i += inc) {\n        const e = events[i];\n        // find start event first\n        if (!foundFromEventId && e.getId() === fromEventId) {\n            foundFromEventId = true;\n            // don't look further than MAX_JUMP_DISTANCE events from `fromEventId`\n            // to not iterate potentially 1000nds of events on key up/down\n            endIdx = Math.min(Math.max(0, i + inc * MAX_JUMP_DISTANCE), maxIdx);\n        } else if (foundFromEventId && !shouldHideEvent(e) && canEditOwnEvent(matrixClient, e)) {\n            // otherwise look for editable event\n            return e;\n        }\n    }\n}\n\n/**\n * How we should render a message depending on its moderation state.\n */\nexport enum MessageModerationState {\n    /**\n     * The message is visible to all.\n     */\n    VISIBLE_FOR_ALL = \"VISIBLE_FOR_ALL\",\n    /**\n     * The message is hidden pending moderation and we're not a user who should\n     * see it nevertheless.\n     */\n    HIDDEN_TO_CURRENT_USER = \"HIDDEN_TO_CURRENT_USER\",\n    /**\n     * The message is hidden pending moderation and we're either the author of\n     * the message or a moderator. In either case, we need to see the message\n     * with a marker.\n     */\n    SEE_THROUGH_FOR_CURRENT_USER = \"SEE_THROUGH_FOR_CURRENT_USER\",\n}\n\n// This is lazily initialized and cached since getMessageModerationState needs it,\n// and is called on timeline rendering hot-paths\nlet msc3531Enabled: boolean | null = null;\nconst getMsc3531Enabled = (): boolean => {\n    if (msc3531Enabled === null) {\n        msc3531Enabled = SettingsStore.getValue(\"feature_msc3531_hide_messages_pending_moderation\");\n    }\n    return msc3531Enabled!;\n};\n\n/**\n * Determine whether a message should be displayed as hidden pending moderation.\n *\n * If MSC3531 is deactivated in settings, all messages are considered visible\n * to all.\n */\nexport function getMessageModerationState(mxEvent: MatrixEvent, client: MatrixClient): MessageModerationState {\n    if (!getMsc3531Enabled()) {\n        return MessageModerationState.VISIBLE_FOR_ALL;\n    }\n    const visibility = mxEvent.messageVisibility();\n    if (visibility.visible) {\n        return MessageModerationState.VISIBLE_FOR_ALL;\n    }\n\n    // At this point, we know that the message is marked as hidden\n    // pending moderation. However, if we're the author or a moderator,\n    // we still need to display it.\n\n    if (mxEvent.sender?.userId === client.getUserId()) {\n        // We're the author, show the message.\n        return MessageModerationState.SEE_THROUGH_FOR_CURRENT_USER;\n    }\n\n    const room = client.getRoom(mxEvent.getRoomId());\n    if (\n        EVENT_VISIBILITY_CHANGE_TYPE.name &&\n        room?.currentState.maySendStateEvent(EVENT_VISIBILITY_CHANGE_TYPE.name, client.getUserId()!)\n    ) {\n        // We're a moderator (as indicated by prefixed event name), show the message.\n        return MessageModerationState.SEE_THROUGH_FOR_CURRENT_USER;\n    }\n    if (\n        EVENT_VISIBILITY_CHANGE_TYPE.altName &&\n        room?.currentState.maySendStateEvent(EVENT_VISIBILITY_CHANGE_TYPE.altName, client.getUserId()!)\n    ) {\n        // We're a moderator (as indicated by unprefixed event name), show the message.\n        return MessageModerationState.SEE_THROUGH_FOR_CURRENT_USER;\n    }\n    // For everybody else, hide the message.\n    return MessageModerationState.HIDDEN_TO_CURRENT_USER;\n}\n\nexport function isVoiceMessage(mxEvent: MatrixEvent): boolean {\n    const content = mxEvent.getContent();\n    // MSC2516 is a legacy identifier. See https://github.com/matrix-org/matrix-doc/pull/3245\n    return !!content[\"org.matrix.msc2516.voice\"] || !!content[\"org.matrix.msc3245.voice\"];\n}\n\nexport async function fetchInitialEvent(\n    client: MatrixClient,\n    roomId: string,\n    eventId: string,\n): Promise<MatrixEvent | null> {\n    let initialEvent: MatrixEvent | null;\n\n    try {\n        const eventData = await client.fetchRoomEvent(roomId, eventId);\n        initialEvent = new MatrixEvent(eventData);\n    } catch {\n        logger.warn(\"Could not find initial event: \" + eventId);\n        initialEvent = null;\n    }\n\n    if (client.supportsThreads() && initialEvent?.isRelation(THREAD_RELATION_TYPE.name) && !initialEvent.getThread()) {\n        const threadId = initialEvent.threadRootId!;\n        const room = client.getRoom(roomId);\n        const mapper = client.getEventMapper();\n        const rootEvent = room?.findEventById(threadId) ?? mapper(await client.fetchRoomEvent(roomId, threadId));\n        try {\n            room?.createThread(threadId, rootEvent, [initialEvent], true);\n        } catch {\n            logger.warn(\"Could not find root event: \" + threadId);\n        }\n    }\n\n    return initialEvent;\n}\n\nexport function editEvent(\n    matrixClient: MatrixClient,\n    mxEvent: MatrixEvent,\n    timelineRenderingType: TimelineRenderingType,\n    getRelationsForEvent?: GetRelationsForEvent,\n): void {\n    if (!canEditContent(matrixClient, mxEvent)) return;\n\n    if (M_POLL_START.matches(mxEvent.getType())) {\n        launchPollEditor(mxEvent, getRelationsForEvent);\n    } else {\n        defaultDispatcher.dispatch({\n            action: Action.EditEvent,\n            event: mxEvent,\n            timelineRenderingType: timelineRenderingType,\n        });\n    }\n}\n\nexport function canCancel(status?: EventStatus | null): boolean {\n    return status === EventStatus.QUEUED || status === EventStatus.NOT_SENT || status === EventStatus.ENCRYPTING;\n}\n\nexport const isLocationEvent = (event: MatrixEvent): boolean => {\n    const eventType = event.getType();\n    return (\n        M_LOCATION.matches(eventType) ||\n        (eventType === EventType.RoomMessage && M_LOCATION.matches(event.getContent().msgtype!))\n    );\n};\n\nexport function hasThreadSummary(event: MatrixEvent): boolean {\n    return event.isThreadRoot && !!event.getThread()?.length && !!event.getThread()!.replyToEvent;\n}\n\nexport const highlightEvent = (roomId: string, eventId: string): void => {\n    defaultDispatcher.dispatch<ViewRoomPayload>({\n        action: Action.ViewRoom,\n        event_id: eventId,\n        highlighted: true,\n        room_id: roomId,\n        metricsTrigger: undefined, // room doesn't change\n    });\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { BugReportEndpointURLLocal } from \"../IConfigOptions\";\nimport SdkConfig from \"../SdkConfig\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { UIFeature } from \"../settings/UIFeature\";\n\nexport function shouldShowFeedback(): boolean {\n    const url = SdkConfig.get().bug_report_endpoint_url;\n    return !!url && url !== BugReportEndpointURLLocal && SettingsStore.getValue(UIFeature.Feedback);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport type GetIframeFn = () => HTMLIFrameElement | null;\n\nexport const DEFAULT_STYLES = {\n    imgSrc: \"\",\n    imgStyle: null as string | null, // css props\n    style: \"\",\n    textContent: \"\",\n};\n\ntype DownloadOptions = {\n    blob: Blob;\n    name: string;\n    autoDownload?: boolean;\n    opts?: typeof DEFAULT_STYLES;\n};\n\n// set up the iframe as a singleton so we don't have to figure out destruction of it down the line.\nlet managedIframe: HTMLIFrameElement;\nlet onLoadPromise: Promise<void>;\nfunction getManagedIframe(): { iframe: HTMLIFrameElement; onLoadPromise: Promise<void> } {\n    if (managedIframe) return { iframe: managedIframe, onLoadPromise };\n\n    managedIframe = document.createElement(\"iframe\");\n\n    // Need to append the iframe in order for the browser to load it.\n    document.body.appendChild(managedIframe);\n\n    // Dev note: the reassignment warnings are entirely incorrect here.\n\n    managedIframe.style.display = \"none\";\n\n    // @ts-ignore\n    // noinspection JSConstantReassignment\n    managedIframe.sandbox = \"allow-scripts allow-downloads\";\n\n    onLoadPromise = new Promise((resolve) => {\n        managedIframe.onload = () => {\n            resolve();\n        };\n        managedIframe.src = \"usercontent/\"; // XXX: Should come from the skin\n    });\n\n    return { iframe: managedIframe, onLoadPromise };\n}\n\n// TODO: If we decide to keep the download link behaviour, we should bring the style management into here.\n\n/**\n * Helper to handle safe file downloads. This operates off an iframe for reasons described\n * by the blob helpers. By default, this will use a hidden iframe to manage the download\n * through a user content wrapper, but can be given an iframe reference if the caller needs\n * additional control over the styling/position of the iframe itself.\n */\nexport class FileDownloader {\n    private onLoadPromise?: Promise<void>;\n\n    /**\n     * Creates a new file downloader\n     * @param iframeFn Function to get a pre-configured iframe. Set to null to have the downloader\n     * use a generic, hidden, iframe.\n     */\n    public constructor(private iframeFn?: GetIframeFn) {}\n\n    private get iframe(): HTMLIFrameElement {\n        const iframe = this.iframeFn?.();\n        if (!iframe) {\n            const managed = getManagedIframe();\n            this.onLoadPromise = managed.onLoadPromise;\n            return managed.iframe;\n        }\n        this.onLoadPromise = undefined;\n        return iframe;\n    }\n\n    public async download({ blob, name, autoDownload = true, opts = DEFAULT_STYLES }: DownloadOptions): Promise<void> {\n        const iframe = this.iframe; // get the iframe first just in case we need to await onload\n        if (this.onLoadPromise) await this.onLoadPromise;\n        iframe.contentWindow?.postMessage(\n            {\n                ...opts,\n                blob: blob,\n                download: name,\n                auto: autoDownload,\n            },\n            \"*\",\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2015-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { filesize, type FilesizeOptions, type FilesizeReturn } from \"filesize\";\nimport { type MediaEventContent } from \"matrix-js-sdk/src/types\";\n\nimport { _t } from \"../languageHandler\";\n\nexport function downloadLabelForFile(content: MediaEventContent, withSize = true): string {\n    let text = _t(\"action|download\");\n\n    if (content.info?.size && withSize) {\n        // If we know the size of the file then add it as human-readable string to the end of the link text\n        // so that the user knows how big a file they are downloading.\n        text += \" (\" + fileSize(content.info.size, { base: 2, standard: \"jedec\" }) + \")\";\n    }\n    return text;\n}\n\n/**\n * Extracts a human-readable label for the file attachment to use as\n * link text.\n *\n * @param {MediaEventContent} content The \"content\" key of the matrix event.\n * @param {string} fallbackText The fallback text\n * @param {boolean} withSize Whether to include size information. Default true.\n * @param {boolean} shortened Ensure the extension of the file name is visible. Default false.\n * @return {string} the human-readable link text for the attachment.\n */\nexport function presentableTextForFile(\n    content: MediaEventContent,\n    fallbackText = _t(\"common|attachment\"),\n    withSize = true,\n    shortened = false,\n): string {\n    let text = fallbackText;\n    if (content.filename?.length) {\n        text = content.filename;\n    } else if (content.body?.length) {\n        // The content body should be the name of the file including a\n        // file extension.\n        text = content.body;\n    }\n\n    // We shorten to 15 characters somewhat arbitrarily, and assume most files\n    // will have a 3 character (plus full stop) extension. The goal is to knock\n    // the label down to 15-25 characters, not perfect accuracy.\n    if (shortened && text.length > 19) {\n        const parts = text.split(\".\");\n        let fileName = parts\n            .slice(0, parts.length - 1)\n            .join(\".\")\n            .substring(0, 15);\n        const extension = parts[parts.length - 1];\n\n        // Trim off any full stops from the file name to avoid a case where we\n        // add an ellipsis that looks really funky.\n        fileName = fileName.replace(/\\.*$/g, \"\");\n\n        text = `${fileName}...${extension}`;\n    }\n\n    if (content.info?.size && withSize) {\n        // If we know the size of the file then add it as human readable\n        // string to the end of the link text so that the user knows how\n        // big a file they are downloading.\n        // The content.info also contains a MIME-type but we don't display\n        // it since it is \"ugly\", users generally aren't aware what it\n        // means and the type of the attachment can usually be inferred\n        // from the file extension.\n        text += \" (\" + fileSize(content.info.size, { base: 2, standard: \"jedec\" }) + \")\";\n    }\n    return text;\n}\n\n/**\n * wrapper function to set default values for filesize function\n *\n * @param byteCount size of file\n * @param options options to customize the response type or size type conversion e.g. 12kB, 12KB\n * @returns {string | number | any[] | {\n *  value: any;\n *  symbol: any;\n *  exponent: number;\n *  unit: string;}} formatted file size with unit e.g. 12kB, 12KB\n */\nexport function fileSize<O extends FilesizeOptions>(byteCount: number, options?: O): FilesizeReturn<O> {\n    const defaultOption = { base: 2, standard: \"jedec\", ...options } as O;\n    return filesize<O>(byteCount, defaultOption);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ReactElement, type ReactNode } from \"react\";\nimport { useIdColorHash } from \"@vector-im/compound-web\";\n\nimport { _t, getCurrentLanguage, getUserLanguage } from \"../languageHandler\";\nimport { jsxJoin } from \"./ReactUtils\";\n\nexport { formatBytes } from \"@element-hq/web-shared-components\";\n\nconst locale = getCurrentLanguage();\n\n// It's quite costly to instanciate `Intl.NumberFormat`, hence why we do not do\n// it in every function call\nconst compactFormatter = new Intl.NumberFormat(locale, {\n    notation: \"compact\",\n});\n\n/**\n * formats and rounds numbers to fit into ~3 characters, suitable for badge counts\n * e.g: 999, 10K, 99K, 1M, 10M, 99M, 1B, 10B, ...\n */\nexport function formatCount(count: number): string {\n    return compactFormatter.format(count);\n}\n\n// It's quite costly to instanciate `Intl.NumberFormat`, hence why we do not do\n// it in every function call\nconst formatter = new Intl.NumberFormat(locale);\n\n/**\n * Format a count showing the whole number but making it a bit more readable.\n * e.g: 1000 => 1,000\n */\nexport function formatCountLong(count: number): string {\n    return formatter.format(count);\n}\n\nexport function getUserNameColorClass(userId: string): string {\n    // eslint-disable-next-line react-hooks/rules-of-hooks\n    const number = useIdColorHash(userId);\n    return `mx_Username_color${number}`;\n}\n\n/**\n * Constructs a written English string representing `items`, with an optional\n * limit on the number of items included in the result. If specified and if the\n * length of `items` is greater than the limit, the string \"and n others\" will\n * be appended onto the result. If `items` is empty, returns the empty string.\n * If there is only one item, return it.\n * @param {string[]} items the items to construct a string from.\n * @param {number?} itemLimit the number by which to limit the list.\n * @returns {string} a string constructed by joining `items` with a comma\n * between each item, but with the last item appended as \" and [lastItem]\".\n */\nexport function formatList(items: string[], itemLimit?: number, includeCount?: boolean): string;\nexport function formatList(items: ReactElement[], itemLimit?: number, includeCount?: boolean): ReactElement;\nexport function formatList(items: ReactNode[], itemLimit?: number, includeCount?: boolean): ReactNode;\nexport function formatList(items: ReactNode[], itemLimit = items.length, includeCount = false): ReactNode {\n    let remaining = Math.max(items.length - itemLimit, 0);\n    if (items.length <= 1) {\n        return items[0] ?? \"\";\n    }\n\n    const formatter = new Intl.ListFormat(getUserLanguage(), { style: \"long\", type: \"conjunction\" });\n    if (remaining > 0) {\n        if (includeCount) {\n            itemLimit--;\n            remaining++;\n        }\n\n        items = items.slice(0, itemLimit);\n        let joinedItems: ReactNode;\n        if (items.every((e) => typeof e === \"string\")) {\n            joinedItems = items.join(\", \");\n        } else {\n            joinedItems = jsxJoin(items, \", \");\n        }\n\n        return _t(\"items_and_n_others\", { count: remaining }, { Items: () => joinedItems });\n    }\n\n    if (items.every((e) => typeof e === \"string\")) {\n        return formatter.format(items as string[]);\n    }\n\n    const parts = formatter.formatToParts(items.map((_, i) => `${i}`));\n    return jsxJoin(\n        parts.map((part) => {\n            if (part.type === \"literal\") return part.value;\n            return items[parseInt(part.value, 10)];\n        }),\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { SERVICE_TYPES, HTTPError, type MatrixClient, type Terms } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport SdkConfig from \"../SdkConfig\";\n\nexport function getDefaultIdentityServerUrl(): string | undefined {\n    return SdkConfig.get(\"validated_server_config\")?.isUrl;\n}\n\nexport function setToDefaultIdentityServer(matrixClient: MatrixClient): void {\n    const url = getDefaultIdentityServerUrl();\n    // Account data change will update localstorage, client, etc through dispatcher\n    matrixClient.setAccountData(\"m.identity_server\", {\n        base_url: url ?? null,\n    });\n}\n\nexport async function doesIdentityServerHaveTerms(matrixClient: MatrixClient, fullUrl: string): Promise<boolean> {\n    let terms: Partial<Terms> | null;\n    try {\n        terms = await matrixClient.getTerms(SERVICE_TYPES.IS, fullUrl);\n    } catch (e) {\n        logger.error(e);\n        if (e instanceof HTTPError && e.httpStatus === 404) {\n            terms = null;\n        } else {\n            throw e;\n        }\n    }\n\n    return !!terms?.[\"policies\"] && Object.keys(terms[\"policies\"]).length > 0;\n}\n\nexport function doesAccountDataHaveIdentityServer(matrixClient: MatrixClient): boolean {\n    const event = matrixClient.getAccountData(\"m.identity_server\");\n    return event?.getContent()[\"base_url\"];\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2022 The Matrix.org Foundation C.I.C.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { arrayHasDiff } from \"./arrays\";\n\nexport function mayBeAnimated(mimeType?: string): boolean {\n    return [\"image/gif\", \"image/webp\", \"image/png\", \"image/apng\", \"image/avif\"].includes(mimeType!);\n}\n\nfunction arrayBufferRead(arr: ArrayBuffer, start: number, len: number): Uint8Array {\n    return new Uint8Array(arr.slice(start, start + len));\n}\n\nfunction arrayBufferReadInt(arr: ArrayBuffer, start: number): number {\n    const dv = new DataView(arr, start, 4);\n    return dv.getUint32(0);\n}\n\nfunction arrayBufferReadStr(arr: ArrayBuffer, start: number, len: number): string {\n    return String.fromCharCode.apply(null, Array.from(arrayBufferRead(arr, start, len)));\n}\n\n/**\n * Check if a Blob contains an animated image.\n * @param blob The Blob to check.\n * @returns True if the image is animated, false if not, or undefined if it could not be determined.\n */\nexport async function blobIsAnimated(blob: Blob): Promise<boolean | undefined> {\n    try {\n        // Try parse the image using ImageDecoder as this is the most coherent way of asserting whether a piece of media\n        // is or is not animated. Limited availability at time of writing, notably Safari lacks support.\n        // https://developer.mozilla.org/en-US/docs/Web/API/ImageDecoder\n        const data = await blob.arrayBuffer();\n        const decoder = new ImageDecoder({ data, type: blob.type });\n        await decoder.tracks.ready;\n        if ([...decoder.tracks].some((track) => track.animated)) {\n            return true;\n        }\n    } catch (e) {\n        console.warn(\"ImageDecoder not supported or failed to decode image\", e);\n        // Not supported by this browser, fall through to manual checks\n    }\n\n    switch (blob.type) {\n        case \"image/webp\": {\n            // Only extended file format WEBP images support animation, so grab the expected data range and verify header.\n            // Based on https://developers.google.com/speed/webp/docs/riff_container#extended_file_format\n            const arr = await blob.slice(0, 21).arrayBuffer();\n            if (\n                arrayBufferReadStr(arr, 0, 4) === \"RIFF\" &&\n                arrayBufferReadStr(arr, 8, 4) === \"WEBP\" &&\n                arrayBufferReadStr(arr, 12, 4) === \"VP8X\"\n            ) {\n                const [flags] = arrayBufferRead(arr, 20, 1);\n                // Flags: R R I L E X _A_ R (reversed)\n                const animationFlagMask = 1 << 1;\n                return (flags & animationFlagMask) != 0;\n            }\n            return false;\n        }\n\n        case \"image/gif\": {\n            // Based on https://gist.github.com/zakirt/faa4a58cec5a7505b10e3686a226f285\n            // More info at http://www.matthewflickinger.com/lab/whatsinagif/bits_and_bytes.asp\n            const dv = new DataView(await blob.arrayBuffer(), 10);\n\n            const globalColorTable = dv.getUint8(0);\n            let globalColorTableSize = 0;\n            // check first bit, if 0, then we don't have a Global Color Table\n            if (globalColorTable & 0x80) {\n                // grab the last 3 bits, to calculate the global color table size -> RGB * 2^(N+1)\n                // N is the value in the last 3 bits.\n                globalColorTableSize = 3 * Math.pow(2, (globalColorTable & 0x7) + 1);\n            }\n\n            // move on to the Graphics Control Extension\n            const offset = 3 + globalColorTableSize;\n\n            const extensionIntroducer = dv.getUint8(offset);\n            const graphicsControlLabel = dv.getUint8(offset + 1);\n            let delayTime = 0;\n\n            // Graphics Control Extension section is where GIF animation data is stored\n            // First 2 bytes must be 0x21 and 0xF9\n            if (extensionIntroducer & 0x21 && graphicsControlLabel & 0xf9) {\n                // skip to the 2 bytes with the delay time\n                delayTime = dv.getUint16(offset + 4);\n            }\n\n            return !!delayTime;\n        }\n\n        case \"image/png\":\n        case \"image/apng\": {\n            // Based on https://stackoverflow.com/a/68618296\n            const arr = await blob.arrayBuffer();\n            if (\n                arrayHasDiff([0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a], Array.from(arrayBufferRead(arr, 0, 8)))\n            ) {\n                return false;\n            }\n\n            for (let i = 8; i < blob.size; ) {\n                const length = arrayBufferReadInt(arr, i);\n                i += 4;\n                const type = arrayBufferReadStr(arr, i, 4);\n                i += 4;\n\n                switch (type) {\n                    case \"acTL\":\n                        return true;\n                    case \"IDAT\":\n                        return false;\n                }\n                i += length + 4;\n            }\n            return false;\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../languageHandler\";\n\nexport function getNameForEventRoom(matrixClient: MatrixClient, userId: string, roomId: string): string {\n    const room = matrixClient.getRoom(roomId);\n    const member = room && room.getMember(userId);\n    return member ? member.name : userId;\n}\n\nexport function userLabelForEventRoom(matrixClient: MatrixClient, userId: string, roomId: string): string {\n    const name = getNameForEventRoom(matrixClient, userId, roomId);\n    if (name !== userId) {\n        return _t(\"name_and_id\", { name, userId });\n    } else {\n        return userId;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\n * A utility to ensure that a function is only called once triggered with\n * a mark applied. Multiple marks can be applied to the function, however\n * the function will only be called once upon trigger().\n *\n * The function starts unmarked.\n */\nexport class MarkedExecution {\n    private marked = false;\n\n    /**\n     * Creates a MarkedExecution for the provided function.\n     * @param {Function} fn The function to be called upon trigger if marked.\n     * @param {Function} onMarkCallback A function that is called when a new mark is made. Not\n     * called if a mark is already flagged.\n     */\n    public constructor(\n        private fn: () => void,\n        private onMarkCallback?: () => void,\n    ) {}\n\n    /**\n     * Resets the mark without calling the function.\n     */\n    public reset(): void {\n        this.marked = false;\n    }\n\n    /**\n     * Marks the function to be called upon trigger().\n     */\n    public mark(): void {\n        if (!this.marked) this.onMarkCallback?.();\n        this.marked = true;\n    }\n\n    /**\n     * If marked, the function will be called, otherwise this does nothing.\n     */\n    public trigger(): void {\n        if (!this.marked) return;\n        this.reset(); // reset first just in case the fn() causes a trigger()\n        this.fn();\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\n * Utility class for lazily getting a variable.\n */\nexport class LazyValue<T> {\n    private val?: T;\n    private prom?: Promise<T>;\n    private done = false;\n\n    public constructor(private getFn: () => Promise<T>) {}\n\n    /**\n     * Whether or not a cached value is present.\n     */\n    public get present(): boolean {\n        // we use a tracking variable just in case the final value is falsy\n        return this.done;\n    }\n\n    /**\n     * Gets the value without invoking a get. May be undefined until the\n     * value is fetched properly.\n     */\n    public get cachedValue(): T | undefined {\n        return this.val;\n    }\n\n    /**\n     * Gets a promise which resolves to the value, eventually.\n     */\n    public get value(): Promise<T> {\n        if (this.prom) return this.prom;\n        this.prom = this.getFn();\n\n        return this.prom.then((v) => {\n            this.val = v;\n            this.done = true;\n            return v;\n        });\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, EventType, MsgType } from \"matrix-js-sdk/src/matrix\";\nimport { type FileContent, type ImageContent, type MediaEventContent } from \"matrix-js-sdk/src/types\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { LazyValue } from \"./LazyValue\";\nimport { type Media, mediaFromContent } from \"../customisations/Media\";\nimport { decryptFile } from \"./DecryptFile\";\nimport { type IDestroyable } from \"./IDestroyable\";\nimport { getBlobSafeMimeType } from \"./blobs.ts\";\n\n// TODO: We should consider caching the blobs. https://github.com/vector-im/element-web/issues/17192\n\nexport class MediaEventHelper implements IDestroyable {\n    // Either an HTTP or Object URL (when encrypted) to the media.\n    public readonly sourceUrl: LazyValue<string | null>;\n    public readonly thumbnailUrl: LazyValue<string | null>;\n\n    // Either the raw or decrypted (when encrypted) contents of the file.\n    public readonly sourceBlob: LazyValue<Blob>;\n    public readonly thumbnailBlob: LazyValue<Blob | null>;\n\n    public readonly media: Media;\n\n    public constructor(private event: MatrixEvent) {\n        this.sourceUrl = new LazyValue(this.prepareSourceUrl);\n        this.thumbnailUrl = new LazyValue(this.prepareThumbnailUrl);\n        this.sourceBlob = new LazyValue(this.fetchSource);\n        this.thumbnailBlob = new LazyValue(this.fetchThumbnail);\n\n        this.media = mediaFromContent(this.event.getContent());\n    }\n\n    public get fileName(): string {\n        return (\n            this.event.getContent<FileContent>().filename ||\n            this.event.getContent<MediaEventContent>().body ||\n            \"download\"\n        );\n    }\n\n    public destroy(): void {\n        if (this.media.isEncrypted) {\n            if (this.sourceUrl.cachedValue) URL.revokeObjectURL(this.sourceUrl.cachedValue);\n            if (this.thumbnailUrl.cachedValue) URL.revokeObjectURL(this.thumbnailUrl.cachedValue);\n        }\n    }\n\n    private prepareSourceUrl = async (): Promise<string | null> => {\n        if (this.media.isEncrypted) {\n            const blob = await this.sourceBlob.value;\n            return URL.createObjectURL(blob);\n        } else {\n            return this.media.srcHttp;\n        }\n    };\n\n    private prepareThumbnailUrl = async (): Promise<string | null> => {\n        if (this.media.isEncrypted) {\n            const blob = await this.thumbnailBlob.value;\n            if (blob === null) return null;\n            return URL.createObjectURL(blob);\n        } else {\n            return this.media.thumbnailHttp;\n        }\n    };\n\n    private fetchSource = (): Promise<Blob> => {\n        const content = this.event.getContent<MediaEventContent>();\n        if (this.media.isEncrypted) {\n            return decryptFile(content.file!, content.info);\n        }\n\n        return (\n            this.media\n                .downloadSource()\n                .then((r) => r.blob())\n                // Set the mime type from the event info on the blob\n                .then((blob) => blob.slice(0, blob.size, getBlobSafeMimeType(content.info?.mimetype ?? blob.type)))\n        );\n    };\n\n    private fetchThumbnail = (): Promise<Blob | null> => {\n        if (!this.media.hasThumbnail) return Promise.resolve(null);\n\n        const content = this.event.getContent<ImageContent>();\n        if (this.media.isEncrypted) {\n            if (content.info?.thumbnail_file) {\n                return decryptFile(content.info.thumbnail_file, content.info.thumbnail_info);\n            } else {\n                // \"Should never happen\"\n                logger.warn(\"Media claims to have thumbnail and is encrypted, but no thumbnail_file found\");\n                return Promise.resolve(null);\n            }\n        }\n\n        const thumbnailHttp = this.media.thumbnailHttp;\n        if (!thumbnailHttp) return Promise.resolve(null);\n\n        return (\n            fetch(thumbnailHttp)\n                .then((r) => r.blob())\n                // Set the mime type from the event info on the blob\n                .then((blob) =>\n                    blob.slice(0, blob.size, getBlobSafeMimeType(content.info?.thumbnail_info?.mimetype ?? blob.type)),\n                )\n        );\n    };\n\n    public static isEligible(event: MatrixEvent): boolean {\n        if (!event) return false;\n        if (event.isRedacted()) return false;\n        if (event.getType() === EventType.Sticker) return true;\n        if (event.getType() !== EventType.RoomMessage) return false;\n\n        const content = event.getContent();\n        const mediaMsgTypes: string[] = [MsgType.Video, MsgType.Audio, MsgType.Image, MsgType.File];\n        if (mediaMsgTypes.includes(content.msgtype!)) return true;\n        if (typeof content.url === \"string\") return true;\n\n        // Finally, it's probably not media\n        return false;\n    }\n\n    /**\n     * Determine if the media event in question supports being hidden in the timeline.\n     * @param event Any matrix event.\n     * @returns `true` if the media can be hidden, otherwise `false`.\n     */\n    public static canHide(event: MatrixEvent): boolean {\n        if (!event) return false;\n        if (event.isRedacted()) return false;\n        const content = event.getContent();\n        const hideTypes: string[] = [MsgType.Video, MsgType.Image];\n        if (hideTypes.includes(content.msgtype!)) return true;\n        return false;\n    }\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport Modal from \"../../../Modal.tsx\";\nimport InviteProgressBody from \"./InviteProgressBody.tsx\";\n\n/** A Modal dialog that pops up while room invites are being sent. */\nconst InviteProgressDialog: React.FC = (_) => {\n    return <InviteProgressBody />;\n};\n\n/**\n * Open the invite progress dialog.\n *\n * Returns a callback which will close the dialog again.\n */\nexport function openInviteProgressDialog(): () => void {\n    const onBeforeClose = async (reason?: string): Promise<boolean> => {\n        // Inhibit closing via background click\n        return reason != \"backgroundClick\";\n    };\n\n    const { close } = Modal.createDialog(\n        InviteProgressDialog,\n        /* props */ {},\n        /* className */ undefined,\n        /* isPriorityModal */ false,\n        /* isStaticModal */ false,\n        { onBeforeClose },\n    );\n    return close;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2016-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { MatrixError, type MatrixClient, EventType, type EmptyObject, type InviteOpts } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { AddressType, getAddressType } from \"../UserAddress\";\nimport { _t } from \"../languageHandler\";\nimport Modal from \"../Modal\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport AskInviteAnywayDialog from \"../components/views/dialogs/AskInviteAnywayDialog\";\nimport ConfirmUserActionDialog from \"../components/views/dialogs/ConfirmUserActionDialog\";\nimport { openInviteProgressDialog } from \"../components/views/dialogs/InviteProgressDialog.tsx\";\n\nexport enum InviteState {\n    Invited = \"invited\",\n    Error = \"error\",\n}\n\ninterface IError {\n    errorText: string;\n    errcode: string;\n}\n\nexport const UNKNOWN_PROFILE_ERRORS = [\n    \"M_NOT_FOUND\",\n    \"M_USER_NOT_FOUND\",\n    \"M_PROFILE_UNDISCLOSED\",\n    \"M_PROFILE_NOT_FOUND\",\n];\n\nexport type CompletionStates = Record<string, InviteState>;\n\nconst USER_ALREADY_JOINED = \"IO.ELEMENT.ALREADY_JOINED\";\nconst USER_ALREADY_INVITED = \"IO.ELEMENT.ALREADY_INVITED\";\nconst USER_BANNED = \"IO.ELEMENT.BANNED\";\n\n/** Options interface for {@link MultiInviter} */\nexport interface MultiInviterOptions {\n    /** Optional callback, fired after each invite */\n    progressCallback?: () => void;\n\n    /**\n     * By default, we will pop up a \"Preparing invitations...\" dialog while the invites are being sent. Set this to\n     * `true` to inhibit it (in which case, you probably want to implement another bit of feedback UI).\n     */\n    inhibitProgressDialog?: boolean;\n}\n\n/**\n * Invites multiple addresses to a room, handling rate limiting from the server\n */\nexport default class MultiInviter {\n    private addresses: string[] = [];\n    private _fatal = false;\n    private completionStates: CompletionStates = {}; // State of each address (invited or error)\n    private errors: Record<string, IError> = {}; // { address: {errorText, errcode} }\n    private reason: string | undefined;\n\n    /**\n     * @param matrixClient the client of the logged in user\n     * @param {string} roomId The ID of the room to invite to\n     * @param options Options object\n     */\n    public constructor(\n        private readonly matrixClient: MatrixClient,\n        private roomId: string,\n        private readonly options: MultiInviterOptions = {},\n    ) {}\n\n    public get fatal(): boolean {\n        return this._fatal;\n    }\n\n    /**\n     * Invite users to this room. This may only be called once per\n     * instance of the class.\n     *\n     * Any failures are returned via the {@link CompletionStates} in the result.\n     *\n     * @param {array} addresses Array of addresses to invite\n     * @param {string} reason Reason for inviting (optional)\n     * @returns {Promise} Resolved when all invitations in the queue are complete.\n     */\n    public async invite(addresses: string[], reason?: string): Promise<CompletionStates> {\n        if (this.addresses.length > 0) {\n            throw new Error(\"Already inviting/invited\");\n        }\n        this.addresses.push(...addresses);\n        this.reason = reason;\n\n        let closeDialog: (() => void) | undefined;\n        if (!this.options.inhibitProgressDialog) {\n            closeDialog = openInviteProgressDialog();\n        }\n\n        try {\n            for (const addr of this.addresses) {\n                if (getAddressType(addr) === null) {\n                    this.completionStates[addr] = InviteState.Error;\n                    this.errors[addr] = {\n                        errcode: \"M_INVALID\",\n                        errorText: _t(\"invite|invalid_address\"),\n                    };\n                }\n            }\n\n            for (const addr of this.addresses) {\n                // don't try to invite it if it's an invalid address\n                // (it will already be marked as an error though,\n                // so no need to do so again)\n                if (getAddressType(addr) === null) {\n                    continue;\n                }\n\n                // don't re-invite (there's no way in the UI to do this, but\n                // for sanity's sake)\n                if (this.completionStates[addr] === InviteState.Invited) {\n                    continue;\n                }\n\n                await this.doInvite(addr, false);\n\n                if (this._fatal) {\n                    // `doInvite` suffered a fatal error. The error should have been recorded in `errors`; it's up\n                    // to the caller to report back to the user.\n                    return this.completionStates;\n                }\n            }\n\n            if (Object.keys(this.errors).length > 0) {\n                // There were problems inviting some people - see if we can invite them\n                // without caring if they exist or not.\n                const unknownProfileUsers = Object.keys(this.errors).filter((a) =>\n                    UNKNOWN_PROFILE_ERRORS.includes(this.errors[a].errcode),\n                );\n\n                if (unknownProfileUsers.length > 0) {\n                    await this.handleUnknownProfileUsers(unknownProfileUsers);\n                }\n            }\n        } finally {\n            // Remember to close the progress dialog, if we opened one.\n            closeDialog?.();\n        }\n\n        return this.completionStates;\n    }\n\n    public getCompletionState(addr: string): InviteState {\n        return this.completionStates[addr];\n    }\n\n    public getErrorText(addr: string): string | null {\n        return this.errors[addr]?.errorText ?? null;\n    }\n\n    private async inviteToRoom(roomId: string, addr: string, ignoreProfile = false): Promise<EmptyObject> {\n        const addrType = getAddressType(addr);\n\n        if (addrType === AddressType.Email) {\n            return this.matrixClient.inviteByEmail(roomId, addr);\n        } else if (addrType === AddressType.MatrixUserId) {\n            const room = this.matrixClient.getRoom(roomId);\n            if (!room) throw new Error(\"Room not found\");\n\n            const member = room.getMember(addr);\n            if (member?.membership === KnownMembership.Join) {\n                throw new MatrixError({\n                    errcode: USER_ALREADY_JOINED,\n                    error: \"Member already joined\",\n                });\n            } else if (member?.membership === KnownMembership.Invite) {\n                throw new MatrixError({\n                    errcode: USER_ALREADY_INVITED,\n                    error: \"Member already invited\",\n                });\n            } else if (member?.membership === KnownMembership.Ban) {\n                let proceed = false;\n                // Check if we can unban the invitee.\n                // See https://spec.matrix.org/v1.7/rooms/v10/#authorization-rules, particularly 4.5.3 and 4.5.4.\n                const ourMember = room.getMember(this.matrixClient.getSafeUserId());\n                if (\n                    !!ourMember &&\n                    member.powerLevel < ourMember.powerLevel &&\n                    room.currentState.hasSufficientPowerLevelFor(\"ban\", ourMember.powerLevel) &&\n                    room.currentState.hasSufficientPowerLevelFor(\"kick\", ourMember.powerLevel)\n                ) {\n                    const { finished } = Modal.createDialog(ConfirmUserActionDialog, {\n                        member,\n                        action: _t(\"action|unban\"),\n                        title: _t(\"invite|unban_first_title\"),\n                    });\n                    [proceed = false] = await finished;\n                    if (proceed) {\n                        await this.matrixClient.unban(roomId, member.userId);\n                    }\n                }\n\n                if (!proceed) {\n                    throw new MatrixError({\n                        errcode: USER_BANNED,\n                        error: \"Member is banned\",\n                    });\n                }\n            }\n\n            if (!ignoreProfile && SettingsStore.getValue(\"promptBeforeInviteUnknownUsers\", this.roomId)) {\n                try {\n                    await this.matrixClient.getProfileInfo(addr);\n                } catch (err) {\n                    // The error handling during the invitation process covers any API.\n                    // Some errors must to me mapped from profile API errors to more specific ones to avoid collisions.\n                    switch (err instanceof MatrixError ? err.errcode : err) {\n                        case \"M_FORBIDDEN\":\n                            throw new MatrixError({ errcode: \"M_PROFILE_UNDISCLOSED\" });\n                        case \"M_NOT_FOUND\":\n                            throw new MatrixError({ errcode: \"M_USER_NOT_FOUND\" });\n                        default:\n                            throw err;\n                    }\n                }\n            }\n\n            const opts: InviteOpts = {};\n            if (this.reason !== undefined) opts.reason = this.reason;\n            if (SettingsStore.getValue(\"feature_share_history_on_invite\")) opts.shareEncryptedHistory = true;\n\n            return this.matrixClient.invite(roomId, addr, opts);\n        } else {\n            throw new Error(\"Unsupported address\");\n        }\n    }\n\n    /**\n     * Attempt to invite a user.\n     *\n     * Does not normally throw exceptions. If there was an error, this is reflected in {@link errors}.\n     * If the error was fatal and should prevent further invites from being done, {@link _fatal} is set.\n     */\n    private doInvite(address: string, ignoreProfile: boolean): Promise<void> {\n        return new Promise<void>((resolve, reject) => {\n            logger.log(`Inviting ${address}`);\n\n            const doInvite = this.inviteToRoom(this.roomId, address, ignoreProfile);\n            doInvite\n                .then(() => {\n                    this.completionStates[address] = InviteState.Invited;\n                    delete this.errors[address];\n\n                    resolve();\n                    this.options.progressCallback?.();\n                })\n                .catch((err) => {\n                    logger.error(err);\n\n                    const room = this.roomId ? this.matrixClient.getRoom(this.roomId) : null;\n                    const isSpace = room?.isSpaceRoom();\n                    const isFederated = room?.currentState.getStateEvents(EventType.RoomCreate, \"\")?.getContent()[\n                        \"m.federate\"\n                    ];\n\n                    let errorText: string | undefined;\n                    switch (err.errcode) {\n                        case \"M_FORBIDDEN\":\n                            if (isSpace) {\n                                errorText =\n                                    isFederated === false\n                                        ? _t(\"invite|error_unfederated_space\")\n                                        : _t(\"invite|error_permissions_space\");\n                            } else {\n                                errorText =\n                                    isFederated === false\n                                        ? _t(\"invite|error_unfederated_room\")\n                                        : _t(\"invite|error_permissions_room\");\n                            }\n                            // No point doing further invites.\n                            this._fatal = true;\n                            break;\n                        case USER_ALREADY_INVITED:\n                            if (isSpace) {\n                                errorText = _t(\"invite|error_already_invited_space\");\n                            } else {\n                                errorText = _t(\"invite|error_already_invited_room\");\n                            }\n                            break;\n                        case USER_ALREADY_JOINED:\n                            if (isSpace) {\n                                errorText = _t(\"invite|error_already_joined_space\");\n                            } else {\n                                errorText = _t(\"invite|error_already_joined_room\");\n                            }\n                            break;\n                        case \"M_LIMIT_EXCEEDED\":\n                            // we're being throttled so wait a bit & try again\n                            window.setTimeout(() => {\n                                this.doInvite(address, ignoreProfile).then(resolve, reject);\n                            }, 5000);\n                            return;\n                        case \"M_NOT_FOUND\":\n                        case \"M_USER_NOT_FOUND\":\n                            errorText = _t(\"invite|error_user_not_found\");\n                            break;\n                        case \"M_PROFILE_UNDISCLOSED\":\n                            errorText = _t(\"invite|error_profile_undisclosed\");\n                            break;\n                        case \"M_PROFILE_NOT_FOUND\":\n                            if (!ignoreProfile) {\n                                // Invite without the profile check\n                                logger.warn(`User ${address} does not have a profile - inviting anyways automatically`);\n                                this.doInvite(address, true).then(resolve, reject);\n                                return;\n                            }\n                            break;\n                        case \"M_BAD_STATE\":\n                        case USER_BANNED:\n                            errorText = _t(\"invite|error_bad_state\");\n                            break;\n                        case \"M_UNSUPPORTED_ROOM_VERSION\":\n                            if (isSpace) {\n                                errorText = _t(\"invite|error_version_unsupported_space\");\n                            } else {\n                                errorText = _t(\"invite|error_version_unsupported_room\");\n                            }\n                            break;\n                        case \"ORG.MATRIX.JSSDK_MISSING_PARAM\":\n                            if (getAddressType(address) === AddressType.Email) {\n                                errorText = _t(\"cannot_invite_without_identity_server\");\n                            }\n                    }\n\n                    if (!errorText) {\n                        errorText = _t(\"invite|error_unknown\");\n                    }\n\n                    this.completionStates[address] = InviteState.Error;\n                    this.errors[address] = { errorText, errcode: err.errcode };\n\n                    resolve();\n                });\n        });\n    }\n\n    /** Handle users which failed with an error code which indicated that their profile was unknown.\n     *\n     * Depending on the `promptBeforeInviteUnknownUsers` setting, we either prompt the user for how to proceed, or\n     * send the invites anyway.\n     */\n    private handleUnknownProfileUsers(unknownProfileUsers: string[]): Promise<void> {\n        return new Promise<void>((resolve) => {\n            const inviteUnknowns = (): void => {\n                const promises = unknownProfileUsers.map((u) => this.doInvite(u, true));\n                Promise.all(promises).then(() => resolve());\n            };\n\n            if (!SettingsStore.getValue(\"promptBeforeInviteUnknownUsers\", this.roomId)) {\n                inviteUnknowns();\n                return;\n            }\n\n            logger.log(\"Showing failed to invite dialog...\");\n            Modal.createDialog(AskInviteAnywayDialog, {\n                unknownProfileUsers: unknownProfileUsers.map((u) => ({\n                    userId: u,\n                    errorText: this.errors[u].errorText,\n                })),\n                onInviteAnyways: () => inviteUnknowns(),\n                onGiveUp: () => {\n                    // Fake all the completion states because we already warned the user\n                    for (const addr of unknownProfileUsers) {\n                        this.completionStates[addr] = InviteState.Invited;\n                    }\n                    resolve();\n                },\n            });\n        });\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type React from \"react\";\n\n// Wrap DOM event handlers with stopPropagation and preventDefault\nexport const preventDefaultWrapper =\n    <T extends React.BaseSyntheticEvent = React.BaseSyntheticEvent>(callback: () => void) =>\n    (e?: T) => {\n        e?.stopPropagation();\n        e?.preventDefault();\n        callback();\n    };\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type MatrixEvent,\n    EventType,\n    M_POLL_START,\n    type MatrixClient,\n    EventTimeline,\n    type Room,\n    type EmptyObject,\n} from \"matrix-js-sdk/src/matrix\";\n\nimport { isContentActionable } from \"./EventUtils\";\nimport { ReadPinsEventId } from \"../components/views/right_panel/types\";\n\nexport default class PinningUtils {\n    /**\n     * Event types that may be pinned.\n     */\n    public static readonly PINNABLE_EVENT_TYPES: (EventType | string)[] = [\n        EventType.RoomMessage,\n        M_POLL_START.name,\n        M_POLL_START.altName,\n    ];\n\n    /**\n     * Determines if the given event can be pinned.\n     * This is a simple check to see if the event is of a type that can be pinned.\n     * @param {MatrixEvent} event The event to check.\n     * @return {boolean} True if the event may be pinned, false otherwise.\n     */\n    public static isPinnable(event: MatrixEvent): boolean {\n        if (event.isRedacted()) return false;\n        return PinningUtils.isUnpinnable(event);\n    }\n\n    /**\n     * Determines if the given event may be unpinned.\n     * @param {MatrixEvent} event The event to check.\n     * @return {boolean} True if the event may be unpinned, false otherwise.\n     */\n    public static isUnpinnable(event: MatrixEvent): boolean {\n        if (!event) return false;\n        if (event.isRedacted()) return true;\n        return this.PINNABLE_EVENT_TYPES.includes(event.getType());\n    }\n\n    /**\n     * Determines if the given event is pinned.\n     * @param matrixClient\n     * @param mxEvent\n     */\n    public static isPinned(matrixClient: MatrixClient, mxEvent: MatrixEvent): boolean {\n        const room = matrixClient.getRoom(mxEvent.getRoomId());\n        if (!room) return false;\n\n        const pinnedEvent = room\n            .getLiveTimeline()\n            .getState(EventTimeline.FORWARDS)\n            ?.getStateEvents(EventType.RoomPinnedEvents, \"\");\n        if (!pinnedEvent) return false;\n        const content = pinnedEvent.getContent();\n        return content.pinned && Array.isArray(content.pinned) && content.pinned.includes(mxEvent.getId());\n    }\n\n    /**\n     * Determines if the given event may be pinned by the current user.\n     * This checks if the user has the necessary permissions to pin or unpin the event, and if the event is pinnable.\n     * @param matrixClient\n     * @param mxEvent\n     */\n    public static canPin(matrixClient: MatrixClient, mxEvent: MatrixEvent): boolean {\n        if (!isContentActionable(mxEvent)) return false;\n\n        const room = matrixClient.getRoom(mxEvent.getRoomId());\n        if (!room) return false;\n\n        // Should have a non-local event id\n        if (mxEvent.status !== null) return false;\n\n        return PinningUtils.userHasPinOrUnpinPermission(matrixClient, room) && PinningUtils.isPinnable(mxEvent);\n    }\n\n    /**\n     * Determines if the given event may be unpinned by the current user.\n     * This checks if the user has the necessary permissions to pin or unpin the event, and if the event is unpinnable.\n     * @param matrixClient\n     * @param mxEvent\n     */\n    public static canUnpin(matrixClient: MatrixClient, mxEvent: MatrixEvent): boolean {\n        const room = matrixClient.getRoom(mxEvent.getRoomId());\n        if (!room) return false;\n\n        // Should have a non-local event id\n        if (mxEvent.status !== null) return false;\n\n        return PinningUtils.userHasPinOrUnpinPermission(matrixClient, room) && PinningUtils.isUnpinnable(mxEvent);\n    }\n\n    /**\n     * Determines if the current user has permission to pin or unpin events in the given room.\n     * @param matrixClient\n     * @param room\n     */\n    public static userHasPinOrUnpinPermission(matrixClient: MatrixClient, room: Room): boolean {\n        return Boolean(\n            room\n                .getLiveTimeline()\n                .getState(EventTimeline.FORWARDS)\n                ?.mayClientSendStateEvent(EventType.RoomPinnedEvents, matrixClient),\n        );\n    }\n\n    /**\n     * Pin or unpin the given event.\n     * @param matrixClient\n     * @param mxEvent\n     */\n    public static async pinOrUnpinEvent(matrixClient: MatrixClient, mxEvent: MatrixEvent): Promise<void> {\n        const room = matrixClient.getRoom(mxEvent.getRoomId());\n        if (!room) return;\n\n        const eventId = mxEvent.getId();\n        if (!eventId) return;\n\n        // Should have a non-local event id\n        if (mxEvent.status !== null) return;\n\n        // Get the current pinned events of the room\n        const pinnedIds: Array<string> =\n            room\n                .getLiveTimeline()\n                .getState(EventTimeline.FORWARDS)\n                ?.getStateEvents(EventType.RoomPinnedEvents, \"\")\n                ?.getContent().pinned || [];\n\n        let roomAccountDataPromise: Promise<EmptyObject | void> = Promise.resolve();\n        // If the event is already pinned, unpin it\n        if (pinnedIds.includes(eventId)) {\n            pinnedIds.splice(pinnedIds.indexOf(eventId), 1);\n        } else {\n            // Otherwise, pin it\n            pinnedIds.push(eventId);\n            // We don't want to wait for the roomAccountDataPromise to resolve before sending the state event\n            roomAccountDataPromise = matrixClient.setRoomAccountData(room.roomId, ReadPinsEventId, {\n                event_ids: [...(room.getAccountData(ReadPinsEventId)?.getContent()?.event_ids || []), eventId],\n            });\n        }\n        await Promise.all([\n            matrixClient.sendStateEvent(room.roomId, EventType.RoomPinnedEvents, { pinned: pinnedIds }, \"\"),\n            roomAccountDataPromise,\n        ]);\n    }\n\n    /**\n     * Unpin all events in the given room.\n     * @param matrixClient\n     * @param roomId\n     */\n    public static async unpinAllEvents(matrixClient: MatrixClient, roomId: string): Promise<void> {\n        await matrixClient.sendStateEvent(roomId, EventType.RoomPinnedEvents, { pinned: [] }, \"\");\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\n * The preferred room versions for various features within the app. The\n * room versions here are selected based on the client's support for the\n * possible room versions in combination with server support in the\n * ecosystem.\n *\n * Loosely follows https://spec.matrix.org/latest/rooms/#feature-matrix\n */\nexport class PreferredRoomVersions {\n    /**\n     * The room version to use when creating \"knock\" rooms.\n     */\n    public static readonly KnockRooms = \"7\";\n\n    /**\n     * The room version to use when creating \"restricted\" rooms.\n     */\n    public static readonly RestrictedRooms = \"9\";\n\n    private constructor() {\n        // readonly, static, class\n    }\n}\n\n/**\n * Determines if a room version supports the given feature using heuristics\n * for how Matrix works.\n * @param roomVer The room version to check support within.\n * @param featureVer The room version of the feature. Should be from PreferredRoomVersions.\n * @see PreferredRoomVersions\n */\nexport function doesRoomVersionSupport(roomVer: string, featureVer: string): boolean {\n    // Assumption: all unstable room versions don't support the feature. Calling code can check for unstable\n    // room versions explicitly if it wants to. The spec reserves [0-9] and `.` for its room versions.\n    if (!roomVer.match(/[\\d.]+/)) {\n        return false;\n    }\n\n    // Dev note: While the spec says room versions are not linear, we can make reasonable assumptions\n    // until the room versions prove themselves to be non-linear in the spec. We should see this coming\n    // from a mile away and can course-correct this function if needed.\n    return Number(roomVer) >= Number(featureVer);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, type ReactNode } from \"react\";\n\n/**\n * Joins an array into one value with a joiner. E.g. join([\"hello\", \"world\"], \" \") -> <>hello world</>\n * @param array the array of element to join\n * @param joiner the string/JSX.Element to join with\n * @returns the joined array\n */\nexport function jsxJoin(array: ReactNode[], joiner?: string | JSX.Element): JSX.Element {\n    return (\n        <>\n            {array.map((element, index) => (\n                <React.Fragment key={index}>\n                    {element}\n                    {index === array.length - 1 ? null : joiner}\n                </React.Fragment>\n            ))}\n        </>\n    );\n}\n","/*\n * Copyright 2024 New Vector Ltd.\n * Copyright 2023 The Matrix.org Foundation C.I.C.\n * Copyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { type IContent, type IEventRelation, type MatrixEvent, THREAD_RELATION_TYPE } from \"matrix-js-sdk/src/matrix\";\nimport sanitizeHtml from \"sanitize-html\";\n\nimport { PERMITTED_URL_SCHEMES } from \"./UrlUtils\";\n\nexport function getParentEventId(ev?: MatrixEvent): string | undefined {\n    if (!ev || ev.isRedacted()) return;\n    if (ev.replyEventId) {\n        return ev.replyEventId;\n    }\n}\n\n// Part of Replies fallback support\nexport function stripPlainReply(body: string): string {\n    // Removes lines beginning with `> ` until you reach one that doesn't.\n    const lines = body.split(\"\\n\");\n    while (lines.length && lines[0].startsWith(\"> \")) lines.shift();\n    // Reply fallback has a blank line after it, so remove it to prevent leading newline\n    if (lines[0] === \"\") lines.shift();\n    return lines.join(\"\\n\");\n}\n\n// Part of Replies fallback support - MUST NOT BE RENDERED DIRECTLY - UNSAFE HTML\nexport function stripHTMLReply(html: string): string {\n    // Sanitize the original HTML for inclusion in <mx-reply>.  We allow\n    // any HTML, since the original sender could use special tags that we\n    // don't recognize, but want to pass along to any recipients who do\n    // recognize them -- recipients should be sanitizing before displaying\n    // anyways.  However, we sanitize to 1) remove any mx-reply, so that we\n    // don't generate a nested mx-reply, and 2) make sure that the HTML is\n    // properly formatted (e.g. tags are closed where necessary)\n    return sanitizeHtml(html, {\n        allowedTags: false, // false means allow everything\n        allowedAttributes: false,\n        allowVulnerableTags: true, // silence xss warning, we won't be rendering directly this, so it is safe to do\n        // we somehow can't allow all schemes, so we allow all that we\n        // know of and mxc (for img tags)\n        allowedSchemes: [...PERMITTED_URL_SCHEMES, \"mxc\"],\n        exclusiveFilter: (frame) => frame.tag === \"mx-reply\",\n    });\n}\n\nexport function makeReplyMixIn(ev?: MatrixEvent): IEventRelation {\n    if (!ev) return {};\n\n    const mixin: IEventRelation = {\n        \"m.in_reply_to\": {\n            event_id: ev.getId(),\n        },\n    };\n\n    if (ev.threadRootId) {\n        mixin.is_falling_back = false;\n    }\n\n    return mixin;\n}\n\nexport function shouldDisplayReply(event: MatrixEvent): boolean {\n    if (event.isRedacted()) {\n        return false;\n    }\n\n    const inReplyTo = event.getWireContent()?.[\"m.relates_to\"]?.[\"m.in_reply_to\"];\n    if (!inReplyTo) {\n        return false;\n    }\n\n    const relation = event.getRelation();\n    if (relation?.rel_type === THREAD_RELATION_TYPE.name && relation?.is_falling_back) {\n        return false;\n    }\n\n    return !!inReplyTo.event_id;\n}\n\nexport function addReplyToMessageContent(content: IContent, replyToEvent: MatrixEvent): void {\n    content[\"m.relates_to\"] = {\n        ...(content[\"m.relates_to\"] || {}),\n        ...makeReplyMixIn(replyToEvent),\n    };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { ClientEvent, EventType, type MatrixClient, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { inviteMultipleToRoom, showAnyInviteErrors } from \"../RoomInvite\";\nimport Modal, { type IHandle } from \"../Modal\";\nimport { _t } from \"../languageHandler\";\nimport ErrorDialog from \"../components/views/dialogs/ErrorDialog\";\nimport SpaceStore from \"../stores/spaces/SpaceStore\";\nimport Spinner from \"../components/views/elements/Spinner\";\nimport type { MultiInviterOptions } from \"./MultiInviter\";\n\nexport interface RoomUpgradeProgress {\n    roomUpgraded: boolean;\n    roomSynced?: boolean;\n    inviteUsersProgress?: number;\n    inviteUsersTotal: number;\n    updateSpacesProgress?: number;\n    updateSpacesTotal: number;\n}\n\nexport async function awaitRoomDownSync(cli: MatrixClient, roomId: string): Promise<Room> {\n    const room = cli.getRoom(roomId);\n    if (room) return room; // already have the room\n\n    return new Promise<Room>((resolve) => {\n        // We have to wait for the js-sdk to give us the room back so\n        // we can more effectively abuse the MultiInviter behaviour\n        // which heavily relies on the Room object being available.\n        const checkForRoomFn = (room: Room): void => {\n            if (room.roomId !== roomId) return;\n            resolve(room);\n            cli.off(ClientEvent.Room, checkForRoomFn);\n        };\n        cli.on(ClientEvent.Room, checkForRoomFn);\n    });\n}\n\nexport async function upgradeRoom(\n    room: Room,\n    targetVersion: string,\n    inviteUsers = false,\n    handleError = true,\n    updateSpaces = true,\n    awaitRoom = false,\n    progressCallback?: (progress: RoomUpgradeProgress) => void,\n    inhibitInviteProgressDialog = false,\n    additionalCreators?: string[],\n): Promise<string> {\n    const cli = room.client;\n    let spinnerModal: IHandle<any> | undefined;\n    if (!progressCallback) {\n        spinnerModal = Modal.createDialog(Spinner, undefined, \"mx_Dialog_spinner\");\n    }\n\n    let toInvite: string[] = [];\n    if (inviteUsers) {\n        toInvite = [\n            ...room.getMembersWithMembership(KnownMembership.Join),\n            ...room.getMembersWithMembership(KnownMembership.Invite),\n        ]\n            .map((m) => m.userId)\n            .filter((m) => m !== cli.getUserId());\n    }\n\n    let parentsToRelink: Room[] = [];\n    if (updateSpaces) {\n        parentsToRelink = Array.from(SpaceStore.instance.getKnownParents(room.roomId))\n            .map((roomId) => cli.getRoom(roomId))\n            .filter((parent) =>\n                parent?.currentState.maySendStateEvent(EventType.SpaceChild, cli.getUserId()!),\n            ) as Room[];\n    }\n\n    const progress: RoomUpgradeProgress = {\n        roomUpgraded: false,\n        roomSynced: awaitRoom || inviteUsers ? false : undefined,\n        inviteUsersProgress: inviteUsers ? 0 : undefined,\n        inviteUsersTotal: toInvite.length,\n        updateSpacesProgress: updateSpaces ? 0 : undefined,\n        updateSpacesTotal: parentsToRelink.length,\n    };\n    progressCallback?.(progress);\n\n    let newRoomId: string;\n    try {\n        ({ replacement_room: newRoomId } = await cli.upgradeRoom(room.roomId, targetVersion, additionalCreators));\n    } catch (e) {\n        if (!handleError) throw e;\n        logger.error(e);\n\n        Modal.createDialog(ErrorDialog, {\n            title: _t(\"room|upgrade_error_title\"),\n            description: _t(\"room|upgrade_error_description\"),\n        });\n        throw e;\n    }\n\n    progress.roomUpgraded = true;\n    progressCallback?.(progress);\n\n    if (awaitRoom || inviteUsers) {\n        await awaitRoomDownSync(room.client, newRoomId);\n        progress.roomSynced = true;\n        progressCallback?.(progress);\n    }\n\n    if (toInvite.length > 0) {\n        // Errors are handled internally to this function\n        await inviteUsersToRoom(cli, newRoomId, toInvite, {\n            progressCallback: () => {\n                progress.inviteUsersProgress!++;\n                progressCallback?.(progress);\n            },\n            inhibitProgressDialog: inhibitInviteProgressDialog,\n        });\n    }\n\n    if (parentsToRelink.length > 0) {\n        try {\n            for (const parent of parentsToRelink) {\n                const currentEv = parent.currentState.getStateEvents(EventType.SpaceChild, room.roomId);\n                await cli.sendStateEvent(\n                    parent.roomId,\n                    EventType.SpaceChild,\n                    {\n                        ...(currentEv?.getContent() || {}), // copy existing attributes like suggested\n                        via: [cli.getDomain()!],\n                    },\n                    newRoomId,\n                );\n                await cli.sendStateEvent(parent.roomId, EventType.SpaceChild, {}, room.roomId);\n\n                progress.updateSpacesProgress!++;\n                progressCallback?.(progress);\n            }\n        } catch (e) {\n            // These errors are not critical to the room upgrade itself\n            logger.warn(\"Failed to update parent spaces during room upgrade\", e);\n        }\n    }\n\n    spinnerModal?.close();\n    return newRoomId;\n}\n\nasync function inviteUsersToRoom(\n    client: MatrixClient,\n    roomId: string,\n    userIds: string[],\n    inviteOptions: MultiInviterOptions,\n): Promise<void> {\n    const result = await inviteMultipleToRoom(client, roomId, userIds, inviteOptions);\n    const room = client.getRoom(roomId)!;\n    showAnyInviteErrors(result.states, room, result.inviter);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { ClientStoppedError, type MatrixClient, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport DMRoomMap from \"./DMRoomMap\";\nimport { asyncSome } from \"./arrays\";\n\nexport enum E2EStatus {\n    Warning = \"warning\",\n    Verified = \"verified\",\n    Normal = \"normal\",\n}\n\nexport async function shieldStatusForRoom(client: MatrixClient, room: Room): Promise<E2EStatus> {\n    const crypto = client.getCrypto();\n    if (!crypto) {\n        return E2EStatus.Warning;\n    }\n\n    try {\n        const members = (await room.getEncryptionTargetMembers()).map(({ userId }) => userId);\n        const inDMMap = !!DMRoomMap.shared().getUserIdForRoomId(room.roomId);\n\n        const verified: string[] = [];\n        const unverified: string[] = [];\n        for (const userId of members) {\n            if (userId === client.getUserId()) continue;\n            const userTrust = await crypto.getUserVerificationStatus(userId);\n\n            /* Alarm if any unverified users were verified before. */\n            if (userTrust.wasCrossSigningVerified() && !userTrust.isCrossSigningVerified()) {\n                return E2EStatus.Warning;\n            }\n            (userTrust.isCrossSigningVerified() ? verified : unverified).push(userId);\n        }\n\n        /* Check all verified user devices. */\n        /* Don't alarm if no other users are verified  */\n        const includeUser =\n            (verified.length > 0 && // Don't alarm for self in rooms where nobody else is verified\n                !inDMMap && // Don't alarm for self in DMs with other users\n                members.length !== 2) || // Don't alarm for self in 1:1 chats with other users\n            members.length === 1; // Do alarm for self if we're alone in a room\n        const targets = includeUser ? [...verified, client.getUserId()!] : verified;\n        const devicesByUser = await crypto.getUserDeviceInfo(targets);\n        for (const userId of targets) {\n            const devices = devicesByUser.get(userId);\n            if (!devices) {\n                // getUserDeviceInfo returned nothing about this user, which means we know nothing about their device list.\n                // That seems odd, so treat it as a warning.\n                logger.warn(`No device info for user ${userId}`);\n                return E2EStatus.Warning;\n            }\n\n            const anyDeviceNotVerified = await asyncSome(devices.keys(), async (deviceId) => {\n                const verificationStatus = await crypto.getDeviceVerificationStatus(userId, deviceId);\n                return !verificationStatus?.isVerified();\n            });\n            if (anyDeviceNotVerified) {\n                return E2EStatus.Warning;\n            }\n        }\n\n        return unverified.length === 0 ? E2EStatus.Verified : E2EStatus.Normal;\n    } catch (e) {\n        if (!(e instanceof ClientStoppedError)) {\n            throw e;\n        }\n\n        // The client has been stopped while we were figuring out what to do. Catch the exception to stop it being\n        // logged. It probably doesn't really matter what we return.\n        logger.warn(\"shieldStatusForRoom: client stopped\");\n        return E2EStatus.Normal;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EnhancedMap } from \"./maps\";\n\n// Inspired by https://pkg.go.dev/golang.org/x/sync/singleflight\n\nconst keyMap = new EnhancedMap<object, EnhancedMap<string, unknown>>();\n\n/**\n * Access class to get a singleflight context. Singleflights execute a\n * function exactly once, unless instructed to forget about a result.\n *\n * Typically this is used to de-duplicate an action, such as a save button\n * being pressed, without having to track state internally for an operation\n * already being in progress. This doesn't expose a flag which can be used\n * to disable a button, however it would be capable of returning a Promise\n * from the first call.\n *\n * The result of the function call is cached indefinitely, just in case a\n * second call comes through late. There are various functions named \"forget\"\n * to have the cache be cleared of a result.\n *\n * Singleflights in our use case are tied to an instance of something, combined\n * with a string key to differentiate between multiple possible actions. This\n * means that a \"save\" key will be scoped to the instance which defined it and\n * not leak between other instances. This is done to avoid having to concatenate\n * variables to strings to essentially namespace the field, for most cases.\n */\nexport class Singleflight {\n    private constructor() {}\n\n    /**\n     * A void marker to help with returning a value in a singleflight context.\n     * If your code doesn't return anything, return this instead.\n     */\n    public static Void = Symbol(\"void\");\n\n    /**\n     * Acquire a singleflight context.\n     * @param {Object} instance An instance to associate the context with. Can be any object.\n     * @param {string} key A string key relevant to that instance to namespace under.\n     * @returns {SingleflightContext} Returns the context to execute the function.\n     */\n    public static for(instance?: object | null, key?: string | null): SingleflightContext {\n        if (!instance || !key) throw new Error(\"An instance and key must be supplied\");\n        return new SingleflightContext(instance, key);\n    }\n\n    /**\n     * Forgets all results for a given instance.\n     * @param {Object} instance The instance to forget about.\n     */\n    public static forgetAllFor(instance: object): void {\n        keyMap.delete(instance);\n    }\n\n    /**\n     * Forgets all cached results for all instances. Intended for use by tests.\n     */\n    public static forgetAll(): void {\n        for (const k of keyMap.keys()) {\n            keyMap.remove(k);\n        }\n    }\n}\n\nclass SingleflightContext {\n    public constructor(\n        private instance: object,\n        private key: string,\n    ) {}\n\n    /**\n     * Forget this particular instance and key combination, discarding the result.\n     */\n    public forget(): void {\n        const map = keyMap.get(this.instance);\n        if (!map) return;\n        map.remove(this.key);\n        if (!map.size) keyMap.remove(this.instance);\n    }\n\n    /**\n     * Execute a function. If a result is already known, that will be returned instead\n     * of executing the provided function. However, if no result is known then the function\n     * will be called, with its return value cached. The function must return a value\n     * other than `undefined` - take a look at Singleflight.Void if you don't have a return\n     * to make.\n     *\n     * Note that this technically allows the caller to provide a different function each time:\n     * this is largely considered a bad idea and should not be done. Singleflights work off the\n     * premise that something needs to happen once, so duplicate executions will be ignored.\n     *\n     * For ideal performance and behaviour, functions which return promises are preferred. If\n     * a function is not returning a promise, it should return as soon as possible to avoid a\n     * second call potentially racing it. The promise returned by this function will be that\n     * of the first execution of the function, even on duplicate calls.\n     * @param {Function} fn The function to execute.\n     * @returns The recorded value.\n     */\n    public do<T>(fn: () => T): T {\n        const map = keyMap.getOrCreate(this.instance, new EnhancedMap<string, unknown>());\n\n        // We have to manually getOrCreate() because we need to execute the fn\n        let val = <T>map.get(this.key);\n        if (val === undefined) {\n            val = fn();\n            map.set(this.key, val);\n        }\n\n        return val;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport function snakeToCamel(s: string): string {\n    return s.replace(/._./g, (v) => `${v[0]}${v[2].toUpperCase()}`);\n}\n\nexport class SnakedObject<T = Record<string, any>> {\n    private fallbackWarnings = new Set<string>();\n\n    public constructor(private obj: T) {}\n\n    public get<K extends string & keyof T>(key: K, altCaseName?: string): T[K] {\n        const val = this.obj[key];\n        if (val !== undefined) return val;\n\n        const fallbackKey = altCaseName ?? snakeToCamel(key);\n        const fallback = this.obj[<K>fallbackKey];\n        if (!!fallback && !this.fallbackWarnings.has(fallbackKey)) {\n            this.fallbackWarnings.add(fallbackKey);\n            console.warn(`Using deprecated camelCase config ${fallbackKey}`);\n            console.warn(\n                \"See https://github.com/vector-im/element-web/blob/develop/docs/config.md#-deprecation-notice\",\n            );\n        }\n        return fallback;\n    }\n\n    // Make JSON.stringify() pretend that everything is fine\n    public toJSON(): T {\n        return this.obj;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { groupBy, mapValues, maxBy, minBy, sumBy, takeRight } from \"lodash\";\nimport { type MatrixClient, type Room, type RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport { type Member } from \"./direct-messages\";\nimport DMRoomMap from \"./DMRoomMap\";\n\nexport const compareMembers =\n    (\n        activityScores: Record<string, IActivityScore | undefined>,\n        memberScores: Record<string, IMemberScore | undefined>,\n    ) =>\n    (a: Member | RoomMember, b: Member | RoomMember): number => {\n        const aActivityScore = activityScores[a.userId]?.score ?? 0;\n        const aMemberScore = memberScores[a.userId]?.score ?? 0;\n        const aScore = aActivityScore + aMemberScore;\n        const aNumRooms = memberScores[a.userId]?.numRooms ?? 0;\n\n        const bActivityScore = activityScores[b.userId]?.score ?? 0;\n        const bMemberScore = memberScores[b.userId]?.score ?? 0;\n        const bScore = bActivityScore + bMemberScore;\n        const bNumRooms = memberScores[b.userId]?.numRooms ?? 0;\n\n        if (aScore === bScore) {\n            if (aNumRooms === bNumRooms) {\n                // If there is no activity between members,\n                // keep the order received from the user directory search results\n                return 0;\n            }\n\n            return bNumRooms - aNumRooms;\n        }\n        return bScore - aScore;\n    };\n\nfunction joinedRooms(cli: MatrixClient): Room[] {\n    return (\n        cli\n            .getRooms()\n            .filter((r) => r.getMyMembership() === KnownMembership.Join)\n            // Skip low priority rooms and DMs\n            .filter((r) => !DMRoomMap.shared().getUserIdForRoomId(r.roomId))\n            .filter((r) => !Object.keys(r.tags).includes(\"m.lowpriority\"))\n    );\n}\n\ninterface IActivityScore {\n    lastSpoke: number;\n    score: number;\n}\n\n// Score people based on who have sent messages recently, as a way to improve the quality of suggestions.\n// We do this by checking every room to see who has sent a message in the last few hours, and giving them\n// a score which correlates to the freshness of their message. In theory, this results in suggestions\n// which are closer to \"continue this conversation\" rather than \"this person exists\".\nexport function buildActivityScores(cli: MatrixClient): { [userId: string]: IActivityScore } {\n    const now = new Date().getTime();\n    const earliestAgeConsidered = now - 60 * 60 * 1000; // 1 hour ago\n    const maxMessagesConsidered = 50; // so we don't iterate over a huge amount of traffic\n    const events = joinedRooms(cli)\n        .flatMap((room) => takeRight(room.getLiveTimeline().getEvents(), maxMessagesConsidered))\n        .filter((ev) => ev.getTs() > earliestAgeConsidered);\n    const senderEvents = groupBy(events, (ev) => ev.getSender());\n    // If the iteratee in mapValues returns undefined that key will be removed from the resultant object\n    return mapValues(senderEvents, (events) => {\n        if (!events.length) return;\n        const lastEvent = maxBy(events, (ev) => ev.getTs())!;\n        const distanceFromNow = Math.abs(now - lastEvent.getTs()); // abs to account for slight future messages\n        const inverseTime = now - earliestAgeConsidered - distanceFromNow;\n        return {\n            lastSpoke: lastEvent.getTs(),\n            // Scores from being in a room give a 'good' score of about 1.0-1.5, so for our\n            // score we'll try and award at least 1.0 for making the list, with 4.0 being\n            // an approximate maximum for being selected.\n            score: Math.max(1, inverseTime / (15 * 60 * 1000)), // 15min segments to keep scores sane\n        };\n    }) as { [key: string]: IActivityScore };\n}\n\ninterface IMemberScore {\n    member: RoomMember;\n    score: number;\n    numRooms: number;\n}\n\nexport function buildMemberScores(cli: MatrixClient): { [userId: string]: IMemberScore } {\n    const maxConsideredMembers = 200;\n    const consideredRooms = joinedRooms(cli).filter((room) => room.getJoinedMemberCount() < maxConsideredMembers);\n    const memberPeerEntries = consideredRooms.flatMap((room) =>\n        room.getJoinedMembers().map((member) => ({ member, roomSize: room.getJoinedMemberCount() })),\n    );\n    const userMeta = groupBy(memberPeerEntries, ({ member }) => member.userId);\n    // If the iteratee in mapValues returns undefined that key will be removed from the resultant object\n    return mapValues(userMeta, (roomMemberships) => {\n        if (!roomMemberships.length) return;\n        const maximumPeers = maxConsideredMembers * roomMemberships.length;\n        const totalPeers = sumBy(roomMemberships, (entry) => entry.roomSize);\n        return {\n            member: minBy(roomMemberships, (entry) => entry.roomSize)!.member,\n            numRooms: roomMemberships.length,\n            score: Math.max(0, Math.pow(1 - totalPeers / maximumPeers, 5)),\n        };\n    }) as { [userId: string]: IMemberScore };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 , 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\n * Retrieves the IndexedDB factory object.\n *\n * @returns {IDBFactory | undefined} The IndexedDB factory object if available, or undefined if it is not supported.\n */\nexport function getIDBFactory(): IDBFactory | undefined {\n    // IndexedDB loading is lazy for easier testing.\n\n    // just *accessing* _indexedDB throws an exception in firefox with\n    // indexeddb disabled.\n    try {\n        // `self` is preferred for service workers, which access this file's functions.\n        // We check `self` first because `window` returns something which doesn't work for service workers.\n        // Note: `self?.indexedDB ?? window.indexedDB` breaks in service workers for unknown reasons.\n        return self?.indexedDB ? self.indexedDB : window.indexedDB;\n    } catch {}\n}\n\nlet idb: IDBDatabase | null = null;\n\nasync function idbInit(): Promise<void> {\n    if (!getIDBFactory()) {\n        throw new Error(\"IndexedDB not available\");\n    }\n    idb = await new Promise((resolve, reject) => {\n        const request = getIDBFactory()!.open(\"matrix-react-sdk\", 1);\n        request.onerror = reject;\n        request.onsuccess = (): void => {\n            resolve(request.result);\n        };\n        request.onupgradeneeded = (): void => {\n            const db = request.result;\n            db.createObjectStore(\"pickleKey\");\n            db.createObjectStore(\"account\");\n        };\n    });\n}\n\nasync function idbTransaction(\n    table: string,\n    mode: IDBTransactionMode,\n    fn: (objectStore: IDBObjectStore) => IDBRequest<any>,\n): Promise<any> {\n    if (!idb) {\n        await idbInit();\n    }\n    return new Promise((resolve, reject) => {\n        const txn = idb!.transaction([table], mode);\n        txn.onerror = reject;\n\n        const objectStore = txn.objectStore(table);\n        const request = fn(objectStore);\n        request.onerror = reject;\n        request.onsuccess = (): void => {\n            resolve(request.result);\n        };\n    });\n}\n\n/**\n * Loads an item from an IndexedDB table within the underlying `matrix-react-sdk` database.\n *\n * If IndexedDB access is not supported in the environment, an error is thrown.\n *\n * @param {string} table The name of the object store in IndexedDB.\n * @param {string | string[]} key The key where the data is stored.\n * @returns {Promise<any>} A promise that resolves with the retrieved item from the table.\n */\nexport async function idbLoad(table: string, key: string | string[]): Promise<any> {\n    if (!idb) {\n        await idbInit();\n    }\n    return idbTransaction(table, \"readonly\", (objectStore) => objectStore.get(key));\n}\n\n/**\n * Saves data to an IndexedDB table within the underlying `matrix-react-sdk` database.\n *\n * If IndexedDB access is not supported in the environment, an error is thrown.\n *\n * @param {string} table The name of the object store in the IndexedDB.\n * @param {string|string[]} key The key to use for storing the data.\n * @param {*} data The data to be saved.\n * @returns {Promise<void>} A promise that resolves when the data is saved successfully.\n */\nexport async function idbSave(table: string, key: string | string[], data: any): Promise<void> {\n    if (!idb) {\n        await idbInit();\n    }\n    return idbTransaction(table, \"readwrite\", (objectStore) => objectStore.put(data, key));\n}\n\n/**\n * Deletes a record from an IndexedDB table within the underlying `matrix-react-sdk` database.\n *\n * If IndexedDB access is not supported in the environment, an error is thrown.\n *\n * @param {string} table The name of the object store where the record is stored.\n * @param {string|string[]} key The key of the record to be deleted.\n * @returns {Promise<void>} A Promise that resolves when the record(s) have been successfully deleted.\n */\nexport async function idbDelete(table: string, key: string | string[]): Promise<void> {\n    if (!idb) {\n        await idbInit();\n    }\n    return idbTransaction(table, \"readwrite\", (objectStore) => objectStore.delete(key));\n}\n\n/**\n * Clears all records from an IndexedDB table within the underlying `matrix-react-sdk` database.\n *\n * If IndexedDB access is not supported in the environment, an error is thrown.\n *\n * @param {string} table The name of the object store where the records are stored.\n * @returns {Promise<void>} A Promise that resolves when the record(s) have been successfully deleted.\n */\nexport async function idbClear(table: string): Promise<void> {\n    if (!idb) {\n        await idbInit();\n    }\n    return idbTransaction(table, \"readwrite\", (objectStore) => objectStore.clear());\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { IndexedDBStore, IndexedDBCryptoStore } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { getIDBFactory } from \"./StorageAccess\";\n\nconst localStorage = window.localStorage;\n\n// The JS SDK will add a prefix of \"matrix-js-sdk:\" to the sync store name.\nconst SYNC_STORE_NAME = \"riot-web-sync\";\nconst LEGACY_CRYPTO_STORE_NAME = \"matrix-js-sdk:crypto\";\nconst RUST_CRYPTO_STORE_NAME = \"matrix-js-sdk::matrix-sdk-crypto\";\n\nfunction log(msg: string): void {\n    logger.log(`StorageManager: ${msg}`);\n}\n\nfunction error(msg: string, ...args: any[]): void {\n    logger.error(`StorageManager: ${msg}`, ...args);\n}\n\nexport function tryPersistStorage(): void {\n    if (navigator.storage && navigator.storage.persist) {\n        navigator.storage.persist().then((persistent) => {\n            logger.log(\"StorageManager: Persistent?\", persistent);\n        });\n    } else if (document.requestStorageAccess) {\n        // Safari\n        document.requestStorageAccess().then(\n            () => logger.log(\"StorageManager: Persistent?\", true),\n            () => logger.log(\"StorageManager: Persistent?\", false),\n        );\n    } else {\n        logger.log(\"StorageManager: Persistence unsupported\");\n    }\n}\n\nexport async function checkConsistency(): Promise<{\n    healthy: boolean;\n    cryptoInited: boolean;\n    dataInCryptoStore: boolean;\n    dataInLocalStorage: boolean;\n}> {\n    log(\"Checking storage consistency\");\n    log(`Local storage supported? ${!!localStorage}`);\n    log(`IndexedDB supported? ${!!getIDBFactory()}`);\n\n    let dataInLocalStorage = false;\n    let dataInCryptoStore = false;\n    let cryptoInited = false;\n    let healthy = true;\n\n    if (localStorage) {\n        dataInLocalStorage = localStorage.length > 0;\n        log(`Local storage contains data? ${dataInLocalStorage}`);\n\n        cryptoInited = !!localStorage.getItem(\"mx_crypto_initialised\");\n        log(`Crypto initialised? ${cryptoInited}`);\n    } else {\n        healthy = false;\n        error(\"Local storage cannot be used on this browser\");\n    }\n\n    if (getIDBFactory() && localStorage) {\n        const results = await checkSyncStore();\n        if (!results.healthy) {\n            healthy = false;\n        }\n    } else {\n        healthy = false;\n        error(\"Sync store cannot be used on this browser\");\n    }\n\n    if (getIDBFactory()) {\n        const results = await checkCryptoStore();\n        dataInCryptoStore = results.exists;\n        if (!results.healthy) {\n            healthy = false;\n        }\n    } else {\n        healthy = false;\n        error(\"Crypto store cannot be used on this browser\");\n    }\n\n    if (dataInLocalStorage && cryptoInited && !dataInCryptoStore) {\n        healthy = false;\n        error(\n            \"Data exists in local storage and crypto is marked as initialised but no data found in crypto store. \" +\n                \"IndexedDB storage has likely been evicted by the browser!\",\n        );\n    }\n\n    if (healthy) {\n        log(\"Storage consistency checks passed\");\n    } else {\n        error(\"Storage consistency checks failed\");\n    }\n\n    return {\n        dataInLocalStorage,\n        dataInCryptoStore,\n        cryptoInited,\n        healthy,\n    };\n}\n\ninterface StoreCheck {\n    exists: boolean;\n    healthy: boolean;\n}\n\nasync function checkSyncStore(): Promise<StoreCheck> {\n    let exists = false;\n    try {\n        exists = await IndexedDBStore.exists(getIDBFactory()!, SYNC_STORE_NAME);\n        log(`Sync store using IndexedDB contains data? ${exists}`);\n        return { exists, healthy: true };\n    } catch (e) {\n        error(\"Sync store using IndexedDB inaccessible\", e);\n    }\n    log(\"Sync store using memory only\");\n    return { exists, healthy: false };\n}\n\nasync function checkCryptoStore(): Promise<StoreCheck> {\n    // check first if there is a rust crypto store\n    try {\n        const rustDbExists = await IndexedDBCryptoStore.exists(getIDBFactory()!, RUST_CRYPTO_STORE_NAME);\n        log(`Rust Crypto store using IndexedDB contains data? ${rustDbExists}`);\n\n        if (rustDbExists) {\n            // There was an existing rust database, so consider it healthy.\n            return { exists: true, healthy: true };\n        } else {\n            // No rust store, so let's check if there is a legacy store not yet migrated.\n            try {\n                const legacyIdbExists = await IndexedDBCryptoStore.existsAndIsNotMigrated(\n                    getIDBFactory()!,\n                    LEGACY_CRYPTO_STORE_NAME,\n                );\n                log(`Legacy Crypto store using IndexedDB contains non migrated data? ${legacyIdbExists}`);\n                return { exists: legacyIdbExists, healthy: true };\n            } catch (e) {\n                error(\"Legacy crypto store using IndexedDB inaccessible\", e);\n            }\n\n            // No need to check local storage or memory as rust stack doesn't support them.\n            // Given that rust stack requires indexeddb, set healthy to false.\n            return { exists: false, healthy: false };\n        }\n    } catch (e) {\n        error(\"Rust crypto store using IndexedDB inaccessible\", e);\n        return { exists: false, healthy: false };\n    }\n}\n\n/**\n * Sets whether crypto has ever been successfully\n * initialised on this client.\n * StorageManager uses this to determine whether indexeddb\n * has been wiped by the browser: this flag is saved to localStorage\n * and if it is true and not crypto data is found, an error is\n * presented to the user.\n *\n * @param {boolean} cryptoInited True if crypto has been set up\n */\nexport function setCryptoInitialised(cryptoInited: boolean): void {\n    localStorage.setItem(\"mx_crypto_initialised\", String(cryptoInited));\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2018-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\nA countdown timer, exposing a promise api.\nA timer starts in a non-started state,\nand needs to be started by calling `start()`` on it first.\n\nTimers can be `abort()`-ed which makes the promise reject prematurely.\n\nOnce a timer is finished or aborted, it can't be started again\n(because the promise should not be replaced). Instead, create\na new one through `clone()` or `cloneIfRun()`.\n*/\nexport default class Timer {\n    private timerHandle?: number;\n    private startTs?: number;\n    private deferred!: PromiseWithResolvers<void>;\n\n    public constructor(private timeout: number) {\n        this.setNotStarted();\n    }\n\n    private setNotStarted(): void {\n        this.timerHandle = undefined;\n        this.startTs = undefined;\n        this.deferred = Promise.withResolvers();\n        this.deferred.promise = this.deferred.promise.finally(() => {\n            this.timerHandle = undefined;\n        });\n    }\n\n    private onTimeout = (): void => {\n        const now = Date.now();\n        const elapsed = now - this.startTs!;\n        if (elapsed >= this.timeout) {\n            this.deferred.resolve();\n            this.setNotStarted();\n        } else {\n            const delta = this.timeout - elapsed;\n            this.timerHandle = window.setTimeout(this.onTimeout, delta);\n        }\n    };\n\n    public changeTimeout(timeout: number): void {\n        if (timeout === this.timeout) {\n            return;\n        }\n        const isSmallerTimeout = timeout < this.timeout;\n        this.timeout = timeout;\n        if (this.isRunning() && isSmallerTimeout) {\n            clearTimeout(this.timerHandle);\n            this.onTimeout();\n        }\n    }\n\n    /**\n     * if not started before, starts the timer.\n     * @returns {Timer} the same timer\n     */\n    public start(): Timer {\n        if (!this.isRunning()) {\n            this.startTs = Date.now();\n            this.timerHandle = window.setTimeout(this.onTimeout, this.timeout);\n        }\n        return this;\n    }\n\n    /**\n     * (re)start the timer. If it's running, reset the timeout. If not, start it.\n     * @returns {Timer} the same timer\n     */\n    public restart(): Timer {\n        if (this.isRunning()) {\n            // don't clearTimeout here as this method\n            // can be called in fast succession,\n            // instead just take note and compare\n            // when the already running timeout expires\n            this.startTs = Date.now();\n            return this;\n        } else {\n            return this.start();\n        }\n    }\n\n    /**\n     * if the timer is running, abort it,\n     * and reject the promise for this timer.\n     * @returns {Timer} the same timer\n     */\n    public abort(): Timer {\n        if (this.isRunning()) {\n            clearTimeout(this.timerHandle);\n            this.deferred.reject(new Error(\"Timer was aborted.\"));\n            this.setNotStarted();\n        }\n        return this;\n    }\n\n    /**\n     *promise that will resolve when the timer elapses,\n     *or is rejected when abort is called\n     *@return {Promise}\n     */\n    public finished(): Promise<void> {\n        return this.deferred.promise;\n    }\n\n    public isRunning(): boolean {\n        return this.timerHandle !== undefined;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\n * If a url has no path component, etc. abbreviate it to just the hostname\n *\n * @param {string} u The url to be abbreviated\n * @returns {string} The abbreviated url\n */\nexport function abbreviateUrl(u?: string): string {\n    if (!u) return \"\";\n\n    let parsedUrl: URL;\n    try {\n        parsedUrl = parseUrl(u);\n    } catch (e) {\n        console.error(e);\n        // if it's something we can't parse as a url then just return it\n        return u;\n    }\n\n    if (parsedUrl.pathname === \"/\") {\n        // we ignore query / hash parts: these aren't relevant for IS server URLs\n        return parsedUrl.host || \"\";\n    }\n\n    return u;\n}\n\nexport function unabbreviateUrl(u?: string): string {\n    if (!u) return \"\";\n\n    let longUrl = u;\n    if (!u.startsWith(\"https://\")) longUrl = \"https://\" + u;\n    const parsed = parseUrl(longUrl);\n    if (!parsed.hostname) return u;\n\n    return longUrl;\n}\n\nexport function parseUrl(u: string): URL {\n    if (!u.includes(\":\")) {\n        u = window.location.protocol + u;\n    }\n    return new URL(u);\n}\n\nexport const PERMITTED_URL_SCHEMES = [\n    \"bitcoin\",\n    \"ftp\",\n    \"geo\",\n    \"http\",\n    \"https\",\n    \"im\",\n    \"irc\",\n    \"ircs\",\n    \"magnet\",\n    \"mailto\",\n    \"matrix\",\n    \"mms\",\n    \"news\",\n    \"nntp\",\n    \"openpgp4fpr\",\n    \"sip\",\n    \"sftp\",\n    \"sms\",\n    \"smsto\",\n    \"ssh\",\n    \"tel\",\n    \"urn\",\n    \"webcal\",\n    \"wtai\",\n    \"xmpp\",\n];\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type IClientWellKnown, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { UnstableValue } from \"matrix-js-sdk/src/NamespacedValue\";\n\nconst CALL_BEHAVIOUR_WK_KEY = \"io.element.call_behaviour\";\nconst E2EE_WK_KEY = \"io.element.e2ee\";\nconst E2EE_WK_KEY_DEPRECATED = \"im.vector.riot.e2ee\";\nexport const TILE_SERVER_WK_KEY = new UnstableValue(\"m.tile_server\", \"org.matrix.msc3488.tile_server\");\nconst EMBEDDED_PAGES_WK_PROPERTY = \"io.element.embedded_pages\";\n\n/* eslint-disable camelcase */\nexport interface ICallBehaviourWellKnown {\n    widget_build_url?: string;\n    ignore_dm?: boolean;\n}\n\nexport interface IE2EEWellKnown {\n    default?: boolean;\n    /**\n     * Forces the encryption to disabled for all new rooms\n     * When true, overrides configured 'default' behaviour\n     * Hides the option to enable encryption on room creation\n     * Disables the option to enable encryption in room settings for all new and existing rooms\n     */\n    force_disable?: boolean;\n}\n\nexport interface ITileServerWellKnown {\n    map_style_url?: string;\n}\n\nexport interface IEmbeddedPagesWellKnown {\n    home_url?: string;\n}\n/* eslint-enable camelcase */\n\nexport function getCallBehaviourWellKnown(matrixClient: MatrixClient): ICallBehaviourWellKnown {\n    const clientWellKnown = matrixClient.getClientWellKnown();\n    return clientWellKnown?.[CALL_BEHAVIOUR_WK_KEY];\n}\n\nexport function getE2EEWellKnown(matrixClient: MatrixClient): IE2EEWellKnown | null {\n    const clientWellKnown = matrixClient.getClientWellKnown();\n    if (clientWellKnown?.[E2EE_WK_KEY]) {\n        return clientWellKnown[E2EE_WK_KEY];\n    }\n    if (clientWellKnown?.[E2EE_WK_KEY_DEPRECATED]) {\n        return clientWellKnown[E2EE_WK_KEY_DEPRECATED];\n    }\n    return null;\n}\n\nexport function getTileServerWellKnown(matrixClient: MatrixClient): ITileServerWellKnown | undefined {\n    return tileServerFromWellKnown(matrixClient.getClientWellKnown());\n}\n\nexport function tileServerFromWellKnown(clientWellKnown?: IClientWellKnown | undefined): ITileServerWellKnown {\n    return clientWellKnown?.[TILE_SERVER_WK_KEY.name] ?? clientWellKnown?.[TILE_SERVER_WK_KEY.altName];\n}\n\nexport function getEmbeddedPagesWellKnown(matrixClient: MatrixClient | undefined): IEmbeddedPagesWellKnown | undefined {\n    return embeddedPagesFromWellKnown(matrixClient?.getClientWellKnown());\n}\n\nexport function embeddedPagesFromWellKnown(clientWellKnown?: IClientWellKnown): IEmbeddedPagesWellKnown {\n    return clientWellKnown?.[EMBEDDED_PAGES_WK_PROPERTY];\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { type IDestroyable } from \"./IDestroyable\";\nimport { arrayFastClone } from \"./arrays\";\n\nexport type WhenFn<T extends string | number> = (w: Whenable<T>) => void;\n\n/**\n * Whenables are a cheap way to have Observable patterns mixed with typical\n * usage of Promises, without having to tear down listeners or calls. Whenables\n * are intended to be used when a condition will be met multiple times and\n * the consumer needs to know *when* that happens.\n */\nexport abstract class Whenable<T extends string | number> implements IDestroyable {\n    private listeners: { condition: T | null; fn: WhenFn<T> }[] = [];\n\n    /**\n     * Sets up a call to `fn` *when* the `condition` is met.\n     * @param condition The condition to match.\n     * @param fn The function to call.\n     * @returns This.\n     */\n    public when(condition: T, fn: WhenFn<T>): Whenable<T> {\n        this.listeners.push({ condition, fn });\n        return this;\n    }\n\n    /**\n     * Sets up a call to `fn` *when* any of the `conditions` are met.\n     * @param conditions The conditions to match.\n     * @param fn The function to call.\n     * @returns This.\n     */\n    public whenAnyOf(conditions: T[], fn: WhenFn<T>): Whenable<T> {\n        for (const condition of conditions) {\n            this.when(condition, fn);\n        }\n        return this;\n    }\n\n    /**\n     * Sets up a call to `fn` *when* any condition is met.\n     * @param fn The function to call.\n     * @returns This.\n     */\n    public whenAnything(fn: WhenFn<T>): Whenable<T> {\n        this.listeners.push({ condition: null, fn });\n        return this;\n    }\n\n    /**\n     * Notifies all the listeners of a given condition.\n     * @param condition The new condition that has been met.\n     */\n    protected notifyCondition(condition: T): void {\n        const listeners = arrayFastClone(this.listeners); // clone just in case the handler modifies us\n        for (const listener of listeners) {\n            if (listener.condition === null || listener.condition === condition) {\n                try {\n                    listener.fn(this);\n                } catch (e) {\n                    logger.error(`Error calling whenable listener for ${condition}:`, e);\n                }\n            }\n        }\n    }\n\n    public destroy(): void {\n        this.listeners = [];\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017-2020 The Matrix.org Foundation C.I.C.\nCopyright 2019 Travis Ralston\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useCallback, useEffect, useState } from \"react\";\nimport { base32 } from \"rfc4648\";\nimport { capitalize } from \"lodash\";\nimport { type IWidget, type IWidgetData } from \"matrix-widget-api\";\nimport { type Room, ClientEvent, type MatrixClient, RoomStateEvent, type MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { CallType } from \"matrix-js-sdk/src/webrtc/call\";\nimport { LOWERCASE, secureRandomString, secureRandomStringFrom } from \"matrix-js-sdk/src/randomstring\";\n\nimport PlatformPeg from \"../PlatformPeg\";\nimport SdkConfig from \"../SdkConfig\";\nimport dis from \"../dispatcher/dispatcher\";\nimport WidgetEchoStore from \"../stores/WidgetEchoStore\";\nimport { IntegrationManagers } from \"../integrations/IntegrationManagers\";\nimport { WidgetType } from \"../widgets/WidgetType\";\nimport { Jitsi } from \"../widgets/Jitsi\";\nimport { objectClone } from \"./objects\";\nimport { _t } from \"../languageHandler\";\nimport WidgetStore, { type IApp, isAppWidget } from \"../stores/WidgetStore\";\nimport { parseUrl } from \"./UrlUtils\";\nimport { useEventEmitter } from \"../hooks/useEventEmitter\";\nimport { WidgetLayoutStore } from \"../stores/widgets/WidgetLayoutStore\";\nimport { type IWidgetEvent, type UserWidget } from \"./WidgetUtils-types\";\n\n// How long we wait for the state event echo to come back from the server\n// before waitFor[Room/User]Widget rejects its promise\nconst WIDGET_WAIT_TIME = 20000;\n\nexport type { IWidgetEvent, UserWidget };\n\nexport default class WidgetUtils {\n    /**\n     * Returns true if user is able to send state events to modify widgets in this room\n     * (Does not apply to non-room-based / user widgets)\n     * @param client The matrix client of the logged-in user\n     * @param roomId -- The ID of the room to check\n     * @return Boolean -- true if the user can modify widgets in this room\n     * @throws Error -- specifies the error reason\n     */\n    public static canUserModifyWidgets(client: MatrixClient, roomId?: string): boolean {\n        if (!roomId) {\n            logger.warn(\"No room ID specified\");\n            return false;\n        }\n\n        if (!client) {\n            logger.warn(\"User must be be logged in\");\n            return false;\n        }\n\n        const room = client.getRoom(roomId);\n        if (!room) {\n            logger.warn(`Room ID ${roomId} is not recognised`);\n            return false;\n        }\n\n        const me = client.getUserId();\n        if (!me) {\n            logger.warn(\"Failed to get user ID\");\n            return false;\n        }\n\n        if (room.getMyMembership() !== KnownMembership.Join) {\n            logger.warn(`User ${me} is not in room ${roomId}`);\n            return false;\n        }\n\n        // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n        return room.currentState.maySendStateEvent(\"im.vector.modular.widgets\", me);\n    }\n\n    // TODO: Generify the name of this function. It's not just scalar.\n    /**\n     * Returns true if specified url is a scalar URL, typically https://scalar.vector.im/api\n     * @param matrixClient The matrix client of the logged-in user\n     * @param  {[type]}  testUrlString URL to check\n     * @return {Boolean} True if specified URL is a scalar URL\n     */\n    public static isScalarUrl(testUrlString?: string): boolean {\n        if (!testUrlString) {\n            logger.error(\"Scalar URL check failed. No URL specified\");\n            return false;\n        }\n\n        const testUrl = parseUrl(testUrlString);\n        let scalarUrls = SdkConfig.get().integrations_widgets_urls;\n        if (!scalarUrls || scalarUrls.length === 0) {\n            const defaultManager = IntegrationManagers.sharedInstance().getPrimaryManager();\n            if (defaultManager) {\n                scalarUrls = [defaultManager.apiUrl];\n            } else {\n                scalarUrls = [];\n            }\n        }\n\n        for (let i = 0; i < scalarUrls.length; i++) {\n            const scalarUrl = parseUrl(scalarUrls[i]);\n            if (testUrl && scalarUrl) {\n                if (\n                    testUrl.protocol === scalarUrl.protocol &&\n                    testUrl.host === scalarUrl.host &&\n                    scalarUrl.pathname &&\n                    testUrl.pathname?.startsWith(scalarUrl.pathname)\n                ) {\n                    return true;\n                }\n            }\n        }\n        return false;\n    }\n\n    /**\n     * Returns a promise that resolves when a widget with the given\n     * ID has been added as a user widget (ie. the accountData event\n     * arrives) or rejects after a timeout\n     *\n     * @param client The matrix client of the logged-in user\n     * @param widgetId The ID of the widget to wait for\n     * @param add True to wait for the widget to be added,\n     *     false to wait for it to be deleted.\n     * @returns {Promise} that resolves when the widget is in the\n     *     requested state according to the `add` param\n     */\n    public static waitForUserWidget(client: MatrixClient, widgetId: string, add: boolean): Promise<void> {\n        return new Promise((resolve, reject) => {\n            // Tests an account data event, returning true if it's in the state\n            // we're waiting for it to be in\n            function eventInIntendedState(ev?: MatrixEvent): boolean {\n                if (!ev) return false;\n                if (add) {\n                    return ev.getContent()[widgetId] !== undefined;\n                } else {\n                    return ev.getContent()[widgetId] === undefined;\n                }\n            }\n\n            const startingAccountDataEvent = client.getAccountData(\"m.widgets\");\n            if (eventInIntendedState(startingAccountDataEvent)) {\n                resolve();\n                return;\n            }\n\n            function onAccountData(ev: MatrixEvent): void {\n                const currentAccountDataEvent = client.getAccountData(\"m.widgets\");\n                if (eventInIntendedState(currentAccountDataEvent)) {\n                    client.removeListener(ClientEvent.AccountData, onAccountData);\n                    clearTimeout(timerId);\n                    resolve();\n                }\n            }\n            const timerId = window.setTimeout(() => {\n                client.removeListener(ClientEvent.AccountData, onAccountData);\n                reject(new Error(\"Timed out waiting for widget ID \" + widgetId + \" to appear\"));\n            }, WIDGET_WAIT_TIME);\n            client.on(ClientEvent.AccountData, onAccountData);\n        });\n    }\n\n    /**\n     * Returns a promise that resolves when a widget with the given\n     * ID has been added as a room widget in the given room (ie. the\n     * room state event arrives) or rejects after a timeout\n     *\n     * @param client The matrix client of the logged-in user\n     * @param {string} widgetId The ID of the widget to wait for\n     * @param {string} roomId The ID of the room to wait for the widget in\n     * @param {boolean} add True to wait for the widget to be added,\n     *     false to wait for it to be deleted.\n     * @returns {Promise} that resolves when the widget is in the\n     *     requested state according to the `add` param\n     */\n    public static waitForRoomWidget(\n        client: MatrixClient,\n        widgetId: string,\n        roomId: string,\n        add: boolean,\n    ): Promise<void> {\n        return new Promise((resolve, reject) => {\n            // Tests a list of state events, returning true if it's in the state\n            // we're waiting for it to be in\n            function eventsInIntendedState(evList?: MatrixEvent[]): boolean {\n                const widgetPresent = evList?.some((ev) => {\n                    return ev.getContent() && ev.getContent()[\"id\"] === widgetId;\n                });\n                if (add) {\n                    return !!widgetPresent;\n                } else {\n                    return !widgetPresent;\n                }\n            }\n\n            const room = client.getRoom(roomId);\n            // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n            const startingWidgetEvents = room?.currentState.getStateEvents(\"im.vector.modular.widgets\");\n            if (eventsInIntendedState(startingWidgetEvents)) {\n                resolve();\n                return;\n            }\n\n            function onRoomStateEvents(ev: MatrixEvent): void {\n                if (ev.getRoomId() !== roomId || ev.getType() !== \"im.vector.modular.widgets\") return;\n\n                // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n                const currentWidgetEvents = room?.currentState.getStateEvents(\"im.vector.modular.widgets\");\n\n                if (eventsInIntendedState(currentWidgetEvents)) {\n                    client.removeListener(RoomStateEvent.Events, onRoomStateEvents);\n                    clearTimeout(timerId);\n                    resolve();\n                }\n            }\n            const timerId = window.setTimeout(() => {\n                client.removeListener(RoomStateEvent.Events, onRoomStateEvents);\n                reject(new Error(\"Timed out waiting for widget ID \" + widgetId + \" to appear\"));\n            }, WIDGET_WAIT_TIME);\n            client.on(RoomStateEvent.Events, onRoomStateEvents);\n        });\n    }\n\n    public static setUserWidget(\n        client: MatrixClient,\n        widgetId: string,\n        widgetType: WidgetType,\n        widgetUrl: string,\n        widgetName: string,\n        widgetData: IWidgetData,\n    ): Promise<void> {\n        // Get the current widgets and clone them before we modify them, otherwise\n        // we'll modify the content of the old event.\n        const userWidgets = objectClone(WidgetUtils.getUserWidgets(client));\n\n        // Delete existing widget with ID\n        try {\n            delete userWidgets[widgetId];\n        } catch {\n            logger.error(`$widgetId is non-configurable`);\n        }\n\n        const addingWidget = Boolean(widgetUrl);\n\n        const userId = client.getSafeUserId();\n\n        const content = {\n            id: widgetId,\n            type: widgetType.preferred,\n            url: widgetUrl,\n            name: widgetName,\n            data: widgetData,\n            creatorUserId: userId,\n        };\n\n        // Add new widget / update\n        if (addingWidget) {\n            userWidgets[widgetId] = {\n                content: content,\n                sender: userId,\n                state_key: widgetId,\n                type: \"m.widget\",\n                id: widgetId,\n            };\n        }\n\n        // This starts listening for when the echo comes back from the server\n        // since the widget won't appear added until this happens. If we don't\n        // wait for this, the action will complete but if the user is fast enough,\n        // the widget still won't actually be there.\n        return client\n            .setAccountData(\"m.widgets\", userWidgets)\n            .then(() => {\n                return WidgetUtils.waitForUserWidget(client, widgetId, addingWidget);\n            })\n            .then(() => {\n                dis.dispatch({ action: \"user_widget_updated\" });\n            });\n    }\n\n    public static setRoomWidget(\n        client: MatrixClient,\n        roomId: string,\n        widgetId: string,\n        widgetType?: WidgetType,\n        widgetUrl?: string,\n        widgetName?: string,\n        widgetData?: IWidgetData,\n        widgetAvatarUrl?: string,\n    ): Promise<void> {\n        let content: Partial<IWidget> & { avatar_url?: string };\n\n        const addingWidget = Boolean(widgetUrl);\n\n        if (addingWidget) {\n            content = {\n                // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n                // For now we'll send the legacy event type for compatibility with older apps/elements\n                type: widgetType?.legacy,\n                url: widgetUrl,\n                name: widgetName,\n                data: widgetData,\n                avatar_url: widgetAvatarUrl,\n            };\n        } else {\n            content = {};\n        }\n\n        return WidgetUtils.setRoomWidgetContent(client, roomId, widgetId, content as IWidget);\n    }\n\n    public static setRoomWidgetContent(\n        client: MatrixClient,\n        roomId: string,\n        widgetId: string,\n        content: IWidget & Record<string, any>,\n    ): Promise<void> {\n        const addingWidget = !!content.url;\n\n        WidgetEchoStore.setRoomWidgetEcho(roomId, widgetId, content);\n\n        // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n        return client\n            .sendStateEvent(roomId, \"im.vector.modular.widgets\", content, widgetId)\n            .then(() => {\n                return WidgetUtils.waitForRoomWidget(client, widgetId, roomId, addingWidget);\n            })\n            .finally(() => {\n                WidgetEchoStore.removeRoomWidgetEcho(roomId, widgetId);\n            });\n    }\n\n    /**\n     * Get room specific widgets\n     * @param  {Room} room The room to get widgets force\n     * @return {[object]} Array containing current / active room widgets\n     */\n    public static getRoomWidgets(room: Room): MatrixEvent[] {\n        // TODO: Enable support for m.widget event type (https://github.com/vector-im/element-web/issues/13111)\n        const appsStateEvents = room.currentState.getStateEvents(\"im.vector.modular.widgets\");\n        if (!appsStateEvents) {\n            return [];\n        }\n\n        return appsStateEvents.filter((ev) => {\n            return ev.getContent().type && ev.getContent().url;\n        });\n    }\n\n    /**\n     * Get user specific widgets (not linked to a specific room)\n     * @param client The matrix client of the logged-in user\n     * @return {object} Event content object containing current / active user widgets\n     */\n    public static getUserWidgets(client: MatrixClient | undefined): Record<string, UserWidget> {\n        if (!client) {\n            throw new Error(\"User not logged in\");\n        }\n        const userWidgets = client.getAccountData(\"m.widgets\");\n        if (userWidgets && userWidgets.getContent()) {\n            return userWidgets.getContent();\n        }\n        return {};\n    }\n\n    /**\n     * Get user specific widgets (not linked to a specific room) as an array\n     * @param client The matrix client of the logged-in user\n     * @return {[object]} Array containing current / active user widgets\n     */\n    public static getUserWidgetsArray(client: MatrixClient | undefined): UserWidget[] {\n        return Object.values(WidgetUtils.getUserWidgets(client));\n    }\n\n    /**\n     * Get active stickerpicker widgets (stickerpickers are user widgets by nature)\n     * @param client The matrix client of the logged-in user\n     * @return {[object]} Array containing current / active stickerpicker widgets\n     */\n    public static getStickerpickerWidgets(client: MatrixClient | undefined): UserWidget[] {\n        const widgets = WidgetUtils.getUserWidgetsArray(client);\n        return widgets.filter((widget) => widget.content?.type === \"m.stickerpicker\");\n    }\n\n    /**\n     * Get all integration manager widgets for this user.\n     * @param client The matrix client of the logged-in user\n     * @returns {Object[]} An array of integration manager user widgets.\n     */\n    public static getIntegrationManagerWidgets(client: MatrixClient | undefined): UserWidget[] {\n        const widgets = WidgetUtils.getUserWidgetsArray(client);\n        return widgets.filter((w) => w.content?.type === \"m.integration_manager\");\n    }\n\n    /**\n     * Remove all stickerpicker widgets (stickerpickers are user widgets by nature)\n     * @param client The matrix client of the logged-in user\n     * @return {Promise} Resolves on account data updated\n     */\n    public static async removeStickerpickerWidgets(client: MatrixClient | undefined): Promise<void> {\n        if (!client) {\n            throw new Error(\"User not logged in\");\n        }\n        const widgets = client.getAccountData(\"m.widgets\");\n        if (!widgets) return;\n        const userWidgets: Record<string, IWidgetEvent> = widgets.getContent() || {};\n        Object.entries(userWidgets).forEach(([key, widget]) => {\n            if (widget.content && widget.content.type === \"m.stickerpicker\") {\n                delete userWidgets[key];\n            }\n        });\n        await client.setAccountData(\"m.widgets\", userWidgets);\n    }\n\n    public static async addJitsiWidget(\n        client: MatrixClient,\n        roomId: string,\n        type: CallType,\n        name: string,\n        isVideoChannel: boolean,\n        oobRoomName?: string,\n    ): Promise<void> {\n        const domain = Jitsi.getInstance().preferredDomain;\n        const auth = (await Jitsi.getInstance().getJitsiAuth()) ?? undefined;\n\n        // Must be globally unique, although predicatablity is not important, the js-sdk has functions to generate\n        // secure ranom strings, and speed is not important here.\n        const widgetId = secureRandomString(24);\n\n        let confId: string;\n        if (auth === \"openidtoken-jwt\") {\n            // Create conference ID from room ID\n            // For compatibility with Jitsi, use base32 without padding.\n            // More details here:\n            // https://github.com/matrix-org/prosody-mod-auth-matrix-user-verification\n            confId = base32.stringify(new TextEncoder().encode(roomId), { pad: false });\n        } else {\n            // Create a random conference ID (capitalised so the name looks sensible in Jitsi)\n            confId = `Jitsi${capitalize(secureRandomStringFrom(24, LOWERCASE))}`;\n        }\n\n        // TODO: Remove URL hacks when the mobile clients eventually support v2 widgets\n        const widgetUrl = new URL(WidgetUtils.getLocalJitsiWrapperUrl({ auth }));\n        widgetUrl.search = \"\"; // Causes the URL class use searchParams instead\n        widgetUrl.searchParams.set(\"confId\", confId);\n\n        await WidgetUtils.setRoomWidget(client, roomId, widgetId, WidgetType.JITSI, widgetUrl.toString(), name, {\n            conferenceId: confId,\n            roomName: oobRoomName ?? client.getRoom(roomId)?.name,\n            isAudioOnly: type === CallType.Voice,\n            isVideoChannel,\n            domain,\n            auth,\n        });\n    }\n\n    public static makeAppConfig(\n        appId: string,\n        app: Partial<IApp>,\n        senderUserId: string,\n        roomId: string | undefined,\n        eventId: string | undefined,\n    ): IApp {\n        if (!senderUserId) {\n            throw new Error(\"Widgets must be created by someone - provide a senderUserId\");\n        }\n        app.creatorUserId = senderUserId;\n\n        app.id = appId;\n        app.roomId = roomId;\n        app.eventId = eventId;\n        app.name = app.name || app.type;\n\n        return app as IApp;\n    }\n\n    public static getLocalJitsiWrapperUrl(opts: { forLocalRender?: boolean; auth?: string } = {}): string {\n        // NB. we can't just encodeURIComponent all of these because the $ signs need to be there\n        const queryStringParts = [\n            \"conferenceDomain=$domain\",\n            \"conferenceId=$conferenceId\",\n            \"isAudioOnly=$isAudioOnly\",\n            \"startWithAudioMuted=$startWithAudioMuted\",\n            \"startWithVideoMuted=$startWithVideoMuted\",\n            \"isVideoChannel=$isVideoChannel\",\n            \"displayName=$matrix_display_name\",\n            \"avatarUrl=$matrix_avatar_url\",\n            \"userId=$matrix_user_id\",\n            \"roomId=$matrix_room_id\",\n            \"theme=$theme\",\n            \"roomName=$roomName\",\n            `supportsScreensharing=${PlatformPeg.get()?.supportsJitsiScreensharing()}`,\n            \"language=$org.matrix.msc2873.client_language\",\n        ];\n        if (opts.auth) {\n            queryStringParts.push(`auth=${opts.auth}`);\n        }\n        const queryString = queryStringParts.join(\"&\");\n\n        let baseUrl = window.location.href;\n        if (window.location.protocol !== \"https:\" && !opts.forLocalRender) {\n            // Use an external wrapper if we're not locally rendering the widget. This is usually\n            // the URL that will end up in the widget event, so we want to make sure it's relatively\n            // safe to send.\n            // We'll end up using a local render URL when we see a Jitsi widget anyways, so this is\n            // really just for backwards compatibility and to appease the spec.\n            baseUrl = PlatformPeg.get()!.baseUrl;\n        }\n        const url = new URL(\"jitsi.html#\" + queryString, baseUrl); // this strips hash fragment from baseUrl\n        return url.href;\n    }\n\n    public static getWidgetName(app?: IWidget): string {\n        return app?.name?.trim() || _t(\"widget|no_name\");\n    }\n\n    public static getWidgetDataTitle(app?: IWidget): string {\n        return app?.data?.title?.trim() || \"\";\n    }\n\n    public static getWidgetUid(app?: IApp | IWidget): string {\n        return app ? WidgetUtils.calcWidgetUid(app.id, isAppWidget(app) ? app.roomId : undefined) : \"\";\n    }\n\n    public static calcWidgetUid(widgetId: string, roomId?: string): string {\n        return roomId ? `room_${roomId}_${widgetId}` : `user_${widgetId}`;\n    }\n\n    public static editWidget(room: Room, app: IWidget): void {\n        // noinspection JSIgnoredPromiseFromCall\n        IntegrationManagers.sharedInstance()\n            .getPrimaryManager()\n            ?.open(room, \"type_\" + app.type, app.id);\n    }\n\n    public static isManagedByManager(app: IWidget): boolean {\n        if (WidgetUtils.isScalarUrl(app.url)) {\n            const managers = IntegrationManagers.sharedInstance();\n            if (managers.hasManager()) {\n                // TODO: Pick the right manager for the widget\n                const defaultManager = managers.getPrimaryManager();\n                return WidgetUtils.isScalarUrl(defaultManager?.apiUrl);\n            }\n        }\n        return false;\n    }\n}\n\n/**\n * Hook to get the widgets for a room and update when they change\n * @param room the room to get widgets for\n */\nexport const useWidgets = (room: Room): IApp[] => {\n    const [apps, setApps] = useState<IApp[]>(() => WidgetStore.instance.getApps(room.roomId));\n\n    const updateApps = useCallback(() => {\n        // Copy the array so that we always trigger a re-render, as some updates mutate the array of apps/settings\n        setApps([...WidgetStore.instance.getApps(room.roomId)]);\n    }, [room]);\n\n    useEffect(updateApps, [room, updateApps]);\n    useEventEmitter(WidgetStore.instance, room.roomId, updateApps);\n    useEventEmitter(WidgetLayoutStore.instance, WidgetLayoutStore.emissionForRoom(room), updateApps);\n\n    return apps;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { percentageOf, percentageWithin } from \"@element-hq/web-shared-components\";\n\n/**\n * Quickly resample an array to have less/more data points. If an input which is larger\n * than the desired size is provided, it will be downsampled. Similarly, if the input\n * is smaller than the desired size then it will be upsampled.\n * @param {number[]} input The input array to resample.\n * @param {number} points The number of samples to end up with.\n * @returns {number[]} The resampled array.\n */\nexport function arrayFastResample(input: number[], points: number): number[] {\n    if (input.length === points) return input; // short-circuit a complicated call\n\n    // Heavily inspired by matrix-media-repo (used with permission)\n    // https://github.com/turt2live/matrix-media-repo/blob/abe72c87d2e29/util/util_audio/fastsample.go#L10\n    const samples: number[] = [];\n    if (input.length > points) {\n        // Danger: this loop can cause out of memory conditions if the input is too small.\n        const everyNth = Math.round(input.length / points);\n        for (let i = 0; i < input.length; i += everyNth) {\n            samples.push(input[i]);\n        }\n    } else {\n        // Smaller inputs mean we have to spread the values over the desired length. We\n        // end up overshooting the target length in doing this, but we're not looking to\n        // be super accurate so we'll let the sanity trims do their job.\n        const spreadFactor = Math.ceil(points / input.length);\n        for (const val of input) {\n            samples.push(...arraySeed(val, spreadFactor));\n        }\n    }\n\n    // Trim to size & return\n    return arrayTrimFill(samples, points, arraySeed(input[input.length - 1], points));\n}\n\n/**\n * Attempts a smooth resample of the given array. This is functionally similar to arrayFastResample\n * though can take longer due to the smoothing of data.\n * @param {number[]} input The input array to resample.\n * @param {number} points The number of samples to end up with.\n * @returns {number[]} The resampled array.\n */\nexport function arraySmoothingResample(input: number[], points: number): number[] {\n    if (input.length === points) return input; // short-circuit a complicated call\n\n    let samples: number[] = [];\n    if (input.length > points) {\n        // We're downsampling. To preserve the curve we'll actually reduce our sample\n        // selection and average some points between them.\n\n        // All we're doing here is repeatedly averaging the waveform down to near our\n        // target value. We don't average down to exactly our target as the loop might\n        // never end, and we can over-average the data. Instead, we'll get as far as\n        // we can and do a followup fast resample (the neighbouring points will be close\n        // to the actual waveform, so we can get away with this safely).\n        while (samples.length > points * 2 || samples.length === 0) {\n            samples = [];\n            for (let i = 1; i < input.length - 1; i += 2) {\n                const prevPoint = input[i - 1];\n                const nextPoint = input[i + 1];\n                const currPoint = input[i];\n                const average = (prevPoint + nextPoint + currPoint) / 3;\n                samples.push(average);\n            }\n            input = samples;\n        }\n\n        return arrayFastResample(samples, points);\n    } else {\n        // In practice there's not much purpose in burning CPU for short arrays only to\n        // end up with a result that can't possibly look much different than the fast\n        // resample, so just skip ahead to the fast resample.\n        return arrayFastResample(input, points);\n    }\n}\n\n/**\n * Rescales the input array to have values that are inclusively within the provided\n * minimum and maximum.\n * @param {number[]} input The array to rescale.\n * @param {number} newMin The minimum value to scale to.\n * @param {number} newMax The maximum value to scale to.\n * @returns {number[]} The rescaled array.\n */\nexport function arrayRescale(input: number[], newMin: number, newMax: number): number[] {\n    const min: number = Math.min(...input);\n    const max: number = Math.max(...input);\n    return input.map((v) => percentageWithin(percentageOf(v, min, max), newMin, newMax));\n}\n\n/**\n * Creates an array of the given length, seeded with the given value.\n * @param {T} val The value to seed the array with.\n * @param {number} length The length of the array to create.\n * @returns {T[]} The array.\n */\nexport function arraySeed<T>(val: T, length: number): T[] {\n    // Size the array up front for performance, and use `fill` to let the browser\n    // optimize the operation better than we can with a `for` loop, if it wants.\n    return new Array<T>(length).fill(val);\n}\n\n/**\n * Trims or fills the array to ensure it meets the desired length. The seed array\n * given is pulled from to fill any missing slots - it is recommended that this be\n * at least `len` long. The resulting array will be exactly `len` long, either\n * trimmed from the source or filled with the some/all of the seed array.\n * @param {T[]} a The array to trim/fill.\n * @param {number} len The length to trim or fill to, as needed.\n * @param {T[]} seed Values to pull from if the array needs filling.\n * @returns {T[]} The resulting array of `len` length.\n */\nexport function arrayTrimFill<T>(a: T[], len: number, seed: T[]): T[] {\n    // Dev note: we do length checks because the spread operator can result in some\n    // performance penalties in more critical code paths. As a utility, it should be\n    // as fast as possible to not cause a problem for the call stack, no matter how\n    // critical that stack is.\n    if (a.length === len) return a;\n    if (a.length > len) return a.slice(0, len);\n    return a.concat(seed.slice(0, len - a.length));\n}\n\n/**\n * Clones an array as fast as possible, retaining references of the array's values.\n * @param a The array to clone. Must be defined.\n * @returns A copy of the array.\n */\nexport function arrayFastClone<T>(a: T[]): T[] {\n    return a.slice(0, a.length);\n}\n\n/**\n * Determines if the two arrays are different either in length, contents,\n * or order of those contents.\n * @param a The first array. Must be defined.\n * @param b The second array. Must be defined.\n * @returns True if they are different, false otherwise.\n */\nexport function arrayHasOrderChange(a: any[], b: any[]): boolean {\n    if (a.length === b.length) {\n        for (let i = 0; i < a.length; i++) {\n            if (a[i] !== b[i]) return true;\n        }\n        return false;\n    } else {\n        return true; // like arrayHasDiff, a difference in length is a natural change\n    }\n}\n\n/**\n * Determines if two arrays are different through a shallow comparison.\n * @param a The first array. Must be defined.\n * @param b The second array. Must be defined.\n * @returns True if they are different, false otherwise.\n */\nexport function arrayHasDiff(a: any[], b: any[]): boolean {\n    if (a.length === b.length) {\n        // When the lengths are equal, check to see if either array is missing\n        // an element from the other.\n        if (b.some((i) => !a.includes(i))) return true;\n        if (a.some((i) => !b.includes(i))) return true;\n\n        // if all the keys are common, say so\n        return false;\n    } else {\n        return true; // different lengths means they are naturally diverged\n    }\n}\n\nexport type Diff<T> = { added: T[]; removed: T[] };\n\n/**\n * Performs a diff on two arrays. The result is what is different with the\n * first array (`added` in the returned object means objects in B that aren't\n * in A). Shallow comparisons are used to perform the diff.\n * @param a The first array. Must be defined.\n * @param b The second array. Must be defined.\n * @returns The diff between the arrays.\n */\nexport function arrayDiff<T>(a: T[], b: T[]): Diff<T> {\n    return {\n        added: b.filter((i) => !a.includes(i)),\n        removed: a.filter((i) => !b.includes(i)),\n    };\n}\n\n/**\n * Returns the intersection of two arrays.\n * @param a The first array. Must be defined.\n * @param b The second array. Must be defined.\n * @returns The intersection of the arrays.\n */\nexport function arrayIntersection<T>(a: T[], b: T[]): T[] {\n    return a.filter((i) => b.includes(i));\n}\n\n/**\n * Unions arrays, deduping contents using a Set.\n * @param a The arrays to merge.\n * @returns The union of all given arrays.\n */\nexport function arrayUnion<T>(...a: T[][]): T[] {\n    return Array.from(\n        a.reduce((c, v) => {\n            v.forEach((i) => c.add(i));\n            return c;\n        }, new Set<T>()),\n    );\n}\n\n/**\n * Moves a single element from fromIndex to toIndex.\n * @param {array} list the list from which to construct the new list.\n * @param {number} fromIndex the index of the element to move.\n * @param {number} toIndex the index of where to put the element.\n * @returns {array} A new array with the requested value moved.\n */\nexport function moveElement<T>(list: T[], fromIndex: number, toIndex: number): T[] {\n    const result = Array.from(list);\n    const [removed] = result.splice(fromIndex, 1);\n    result.splice(toIndex, 0, removed);\n\n    return result;\n}\n\n/**\n * Helper functions to perform LINQ-like queries on arrays.\n */\nexport class ArrayUtil<T> {\n    /**\n     * Create a new array helper.\n     * @param a The array to help. Can be modified in-place.\n     */\n    public constructor(private a: T[]) {}\n\n    /**\n     * The value of this array, after all appropriate alterations.\n     */\n    public get value(): T[] {\n        return this.a;\n    }\n\n    /**\n     * Groups an array by keys.\n     * @param fn The key-finding function.\n     * @returns This.\n     */\n    public groupBy<K>(fn: (a: T) => K): GroupedArray<K, T> {\n        const obj = this.a.reduce((rv: Map<K, T[]>, val: T) => {\n            const k = fn(val);\n            if (!rv.has(k)) rv.set(k, []);\n            rv.get(k)!.push(val);\n            return rv;\n        }, new Map<K, T[]>());\n        return new GroupedArray(obj);\n    }\n}\n\n/**\n * Helper functions to perform LINQ-like queries on groups (maps).\n */\nexport class GroupedArray<K, T> {\n    /**\n     * Creates a new group helper.\n     * @param val The group to help. Can be modified in-place.\n     */\n    public constructor(private val: Map<K, T[]>) {}\n\n    /**\n     * The value of this group, after all applicable alterations.\n     */\n    public get value(): Map<K, T[]> {\n        return this.val;\n    }\n\n    /**\n     * Orders the grouping into an array using the provided key order.\n     * @param keyOrder The key order.\n     * @returns An array helper of the result.\n     */\n    public orderBy(keyOrder: K[]): ArrayUtil<T> {\n        const a: T[] = [];\n        for (const k of keyOrder) {\n            if (!this.val.has(k)) continue;\n            a.push(...this.val.get(k)!);\n        }\n        return new ArrayUtil(a);\n    }\n}\n\nexport const concat = (...arrays: Uint8Array<ArrayBuffer>[]): Uint8Array<ArrayBuffer> => {\n    return arrays.reduce((concatenatedSoFar: Uint8Array<ArrayBuffer>, toBeConcatenated: Uint8Array<ArrayBuffer>) => {\n        const concatenated = new Uint8Array(concatenatedSoFar.length + toBeConcatenated.length);\n        concatenated.set(concatenatedSoFar, 0);\n        concatenated.set(toBeConcatenated, concatenatedSoFar.length);\n        return concatenated;\n    }, new Uint8Array(0));\n};\n\n/**\n * Async version of Array.every.\n */\nexport async function asyncEvery<T>(values: Iterable<T>, predicate: (value: T) => Promise<boolean>): Promise<boolean> {\n    for (const value of values) {\n        if (!(await predicate(value))) return false;\n    }\n    return true;\n}\n\n/**\n * Async version of Array.some.\n */\nexport async function asyncSome<T>(values: Iterable<T>, predicate: (value: T) => Promise<boolean>): Promise<boolean> {\n    for (const value of values) {\n        if (await predicate(value)) return true;\n    }\n    return false;\n}\n\n/**\n * Async version of Array.some that runs all promises in parallel.\n * @param values\n * @param predicate\n */\nexport async function asyncSomeParallel<T>(\n    values: Array<T>,\n    predicate: (value: T) => Promise<boolean>,\n): Promise<boolean> {\n    try {\n        return await Promise.any<boolean>(\n            values.map((value) =>\n                predicate(value).then((result) => (result ? Promise.resolve(true) : Promise.reject(false))),\n            ),\n        );\n    } catch (e) {\n        // If the array is empty or all the promises are false, Promise.any will reject an AggregateError\n        if (e instanceof AggregateError) return false;\n        throw e;\n    }\n}\n\n/**\n * Async version of Array.filter.\n * If one of the promises rejects, the whole operation will reject.\n * @param values\n * @param predicate\n */\nexport async function asyncFilter<T>(values: Array<T>, predicate: (value: T) => Promise<boolean>): Promise<Array<T>> {\n    const results = await Promise.all(values.map(predicate));\n    return values.filter((_, i) => results[i]);\n}\n\nexport function filterBoolean<T>(values: Array<T | null | undefined>): T[] {\n    return values.filter(Boolean) as T[];\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient, type MatrixEvent, getBeaconInfoIdentifier } from \"matrix-js-sdk/src/matrix\";\n\n/**\n * Beacons should only have shareable locations (open in external mapping tool, forward)\n * when they are live and have a location\n * If not live, returns null\n */\nexport const getShareableLocationEventForBeacon = (event: MatrixEvent, cli: MatrixClient): MatrixEvent | null => {\n    const room = cli.getRoom(event.getRoomId());\n    const beacon = room?.currentState.beacons?.get(getBeaconInfoIdentifier(event));\n    const latestLocationEvent = beacon?.latestLocationEvent;\n\n    if (beacon?.isLive && latestLocationEvent) {\n        return latestLocationEvent;\n    }\n    return null;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Beacon, type ContentHelpers } from \"matrix-js-sdk/src/matrix\";\n\n/**\n * Get ms until expiry\n * Returns 0 when expiry is already passed\n * @param startTimestamp\n * @param durationMs\n * @returns remainingMs\n */\nexport const msUntilExpiry = (startTimestamp: number, durationMs: number): number =>\n    Math.max(0, startTimestamp + durationMs - Date.now());\n\nexport const getBeaconMsUntilExpiry = (beaconInfo: ContentHelpers.BeaconInfoState): number =>\n    msUntilExpiry(beaconInfo.timestamp || 0, beaconInfo.timeout);\n\nexport const getBeaconExpiryTimestamp = (beacon: Beacon): number =>\n    (beacon.beaconInfo.timestamp || 0) + beacon.beaconInfo.timeout;\n\nexport const sortBeaconsByLatestExpiry = (left: Beacon, right: Beacon): number =>\n    getBeaconExpiryTimestamp(right) - getBeaconExpiryTimestamp(left);\n\n// aka sort by timestamp descending\nexport const sortBeaconsByLatestCreation = (left: Beacon, right: Beacon): number =>\n    (right.beaconInfo.timestamp || 0) - (left.beaconInfo.timestamp || 0);\n\n// a beacon's starting timestamp can be in the future\n// (either from small deviations in system clock times, or on purpose from another client)\n// a beacon is only live between its start timestamp and expiry\n// detect when a beacon is waiting to become live\nexport const isBeaconWaitingToStart = (beacon: Beacon): boolean =>\n    !beacon.isLive &&\n    !!beacon.beaconInfo.timestamp &&\n    beacon.beaconInfo.timestamp > Date.now() &&\n    getBeaconExpiryTimestamp(beacon) > Date.now();\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\n// map GeolocationPositionError codes\n// https://developer.mozilla.org/en-US/docs/Web/API/GeolocationPositionError\nexport enum GeolocationError {\n    // no navigator.geolocation\n    Unavailable = \"Unavailable\",\n    // The acquisition of the geolocation information failed because the page didn't have the permission to do it.\n    PermissionDenied = \"PermissionDenied\",\n    // The acquisition of the geolocation failed because at least one internal source of position returned an internal error.\n    PositionUnavailable = \"PositionUnavailable\",\n    // The time allowed to acquire the geolocation was reached before the information was obtained.\n    Timeout = \"Timeout\",\n    // other unexpected failure\n    Default = \"Default\",\n}\n\nconst GeolocationOptions = {\n    timeout: 10000,\n    maximumAge: 60000,\n};\n\nconst isGeolocationPositionError = (error: unknown): error is GeolocationPositionError =>\n    typeof error === \"object\" && !!(error as GeolocationPositionError)[\"PERMISSION_DENIED\"];\n/**\n * Maps GeolocationPositionError to our GeolocationError enum\n */\nexport const mapGeolocationError = (error: GeolocationPositionError | Error | unknown): GeolocationError => {\n    logger.error(\"Geolocation failed\", error);\n\n    if (isGeolocationPositionError(error)) {\n        switch (error?.code) {\n            case error.PERMISSION_DENIED:\n                return GeolocationError.PermissionDenied;\n            case error.POSITION_UNAVAILABLE:\n                return GeolocationError.PositionUnavailable;\n            case error.TIMEOUT:\n                return GeolocationError.Timeout;\n            default:\n                return GeolocationError.Default;\n        }\n    } else if (error instanceof Error && error.message === GeolocationError.Unavailable) {\n        return GeolocationError.Unavailable;\n    } else {\n        return GeolocationError.Default;\n    }\n};\n\nconst getGeolocation = (): Geolocation => {\n    if (!navigator.geolocation) {\n        throw new Error(GeolocationError.Unavailable);\n    }\n    return navigator.geolocation;\n};\n\nexport type GenericPosition = {\n    latitude: number;\n    longitude: number;\n    altitude?: number;\n    accuracy?: number;\n    timestamp: number;\n};\n\nexport type TimedGeoUri = {\n    geoUri: string;\n    timestamp: number;\n};\n\nexport const genericPositionFromGeolocation = (geoPosition: GeolocationPosition): GenericPosition => {\n    const { latitude, longitude, altitude, accuracy } = geoPosition.coords;\n\n    return {\n        // safari reports geolocation timestamps as Apple Cocoa Core Data timestamp\n        // or ms since 1/1/2001 instead of the regular epoch\n        // they also use local time, not utc\n        // to simplify, just use Date.now()\n        timestamp: Date.now(),\n        latitude,\n        longitude,\n        altitude: altitude ?? undefined,\n        accuracy,\n    };\n};\n\nexport const getGeoUri = (position: GenericPosition): string => {\n    const lat = position.latitude;\n    const lon = position.longitude;\n    const alt = Number.isFinite(position.altitude) ? `,${position.altitude}` : \"\";\n    const acc = Number.isFinite(position.accuracy) ? `;u=${position.accuracy}` : \"\";\n    return `geo:${lat},${lon}${alt}${acc}`;\n};\n\nexport const mapGeolocationPositionToTimedGeo = (position: GeolocationPosition): TimedGeoUri => {\n    const genericPosition = genericPositionFromGeolocation(position);\n    return { timestamp: genericPosition.timestamp, geoUri: getGeoUri(genericPosition) };\n};\n\n/**\n * Gets current position, returns a promise\n * @returns Promise<GeolocationPosition>\n */\nexport const getCurrentPosition = async (): Promise<GeolocationPosition> => {\n    try {\n        const position = await new Promise((resolve: PositionCallback, reject) => {\n            getGeolocation().getCurrentPosition(resolve, reject, GeolocationOptions);\n        });\n        return position;\n    } catch (error) {\n        throw new Error(mapGeolocationError(error));\n    }\n};\n\nexport type ClearWatchCallback = () => void;\nexport const watchPosition = (\n    onWatchPosition: PositionCallback,\n    onWatchPositionError: (error: GeolocationError) => void,\n): ClearWatchCallback => {\n    try {\n        const onError = (error: GeolocationPositionError): void => onWatchPositionError(mapGeolocationError(error));\n        const watchId = getGeolocation().watchPosition(onWatchPosition, onError, GeolocationOptions);\n        const clearWatch = (): void => {\n            getGeolocation().clearWatch(watchId);\n        };\n        return clearWatch;\n    } catch (error) {\n        throw new Error(mapGeolocationError(error));\n    }\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useContext, useEffect, useState } from \"react\";\nimport { type Beacon, BeaconEvent, type MatrixEvent, getBeaconInfoIdentifier } from \"matrix-js-sdk/src/matrix\";\n\nimport MatrixClientContext from \"../../contexts/MatrixClientContext\";\nimport { useEventEmitterState } from \"../../hooks/useEventEmitter\";\n\nexport const useBeacon = (beaconInfoEvent: MatrixEvent): Beacon | undefined => {\n    const matrixClient = useContext(MatrixClientContext);\n    const [beacon, setBeacon] = useState<Beacon>();\n\n    useEffect(() => {\n        const roomId = beaconInfoEvent.getRoomId();\n        const beaconIdentifier = getBeaconInfoIdentifier(beaconInfoEvent);\n\n        const room = matrixClient?.getRoom(roomId);\n        const beaconInstance = room?.currentState.beacons.get(beaconIdentifier);\n\n        // TODO could this be less stupid?\n\n        // Beacons are identified by their `state_key`,\n        // where `state_key` is always owner mxid for access control.\n        // Thus, only one beacon is allowed per-user per-room.\n        // See https://github.com/matrix-org/matrix-spec-proposals/pull/3672\n        // When a user creates a new beacon any previous\n        // beacon is replaced and should assume a 'stopped' state\n        // Here we check that this event is the latest beacon for this user\n        // If it is not the beacon instance is set to undefined.\n        // Retired beacons don't get a beacon instance.\n        if (beaconInstance?.beaconInfoId === beaconInfoEvent.getId()) {\n            setBeacon(beaconInstance);\n        } else {\n            setBeacon(undefined);\n        }\n    }, [beaconInfoEvent, matrixClient]);\n\n    // beacon update will fire when this beacon is superseded\n    // check the updated event id for equality to the matrix event\n    const beaconInstanceEventId = useEventEmitterState(beacon, BeaconEvent.Update, () => beacon?.beaconInfoId);\n\n    useEffect(() => {\n        if (beaconInstanceEventId && beaconInstanceEventId !== beaconInfoEvent.getId()) {\n            setBeacon(undefined);\n        }\n    }, [beaconInstanceEventId, beaconInfoEvent]);\n\n    useEffect(() => {\n        if (beacon) {\n            beacon.monitorLiveness();\n        }\n    }, [beacon]);\n\n    return beacon;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { useEffect, useState } from \"react\";\nimport { type Beacon, type BeaconIdentifier } from \"matrix-js-sdk/src/matrix\";\n\nimport { useEventEmitterState } from \"../../hooks/useEventEmitter\";\nimport { OwnBeaconStore, OwnBeaconStoreEvent } from \"../../stores/OwnBeaconStore\";\nimport { sortBeaconsByLatestExpiry } from \"./duration\";\n\ntype LiveBeaconsState = {\n    beacon?: Beacon;\n    onStopSharing: () => void;\n    onResetLocationPublishError: () => void;\n    stoppingInProgress: boolean;\n    hasStopSharingError: boolean;\n    hasLocationPublishError: boolean;\n};\n\n/**\n * Monitor the current users own beacons\n * While current implementation only allows one live beacon per user per room\n * In future it will be possible to have multiple live beacons in one room\n * Select the latest expiry to display,\n * and kill all beacons on stop sharing\n */\nexport const useOwnLiveBeacons = (liveBeaconIds: BeaconIdentifier[]): LiveBeaconsState => {\n    const [stoppingInProgress, setStoppingInProgress] = useState(false);\n\n    const hasLocationPublishError = useEventEmitterState(\n        OwnBeaconStore.instance,\n        OwnBeaconStoreEvent.LocationPublishError,\n        () => liveBeaconIds.some(OwnBeaconStore.instance.beaconHasLocationPublishError),\n    );\n\n    const hasStopSharingError = useEventEmitterState(\n        OwnBeaconStore.instance,\n        OwnBeaconStoreEvent.BeaconUpdateError,\n        () => liveBeaconIds.some((id) => OwnBeaconStore.instance.beaconUpdateErrors.has(id)),\n    );\n\n    useEffect(() => {\n        if (hasStopSharingError) {\n            setStoppingInProgress(false);\n        }\n    }, [hasStopSharingError]);\n\n    // reset stopping in progress on change in live ids\n    useEffect(() => {\n        setStoppingInProgress(false);\n    }, [liveBeaconIds]);\n\n    // select the beacon with latest expiry to display expiry time\n    const beacon = liveBeaconIds\n        .map((beaconId) => OwnBeaconStore.instance.getBeaconById(beaconId)!)\n        .sort(sortBeaconsByLatestExpiry)\n        .shift();\n\n    const onStopSharing = async (): Promise<void> => {\n        setStoppingInProgress(true);\n        try {\n            await Promise.all(liveBeaconIds.map((beaconId) => OwnBeaconStore.instance.stopBeacon(beaconId)));\n        } catch {\n            setStoppingInProgress(false);\n        }\n    };\n\n    const onResetLocationPublishError = (): void => {\n        liveBeaconIds.forEach((beaconId) => {\n            OwnBeaconStore.instance.resetLocationPublishError(beaconId);\n        });\n    };\n\n    return {\n        onStopSharing,\n        onResetLocationPublishError,\n        beacon,\n        stoppingInProgress,\n        hasLocationPublishError,\n        hasStopSharingError,\n    };\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// WARNING: We have to be very careful about what mime-types we allow into blobs,\n// as for performance reasons these are now rendered via URL.createObjectURL()\n// rather than by converting into data: URIs.\n//\n// This means that the content is rendered using the origin of the script which\n// called createObjectURL(), and so if the content contains any scripting then it\n// will pose a XSS vulnerability when the browser renders it.  This is particularly\n// bad if the user right-clicks the URI and pastes it into a new window or tab,\n// as the blob will then execute with access to Element's full JS environment(!)\n//\n// See https://github.com/matrix-org/matrix-react-sdk/pull/1820#issuecomment-385210647\n// for details.\n//\n// We mitigate this by only allowing mime-types into blobs which we know don't\n// contain any scripting, and instantiate all others as application/octet-stream\n// regardless of what mime-type the event claimed.  Even if the payload itself\n// is some malicious HTML, the fact we instantiate it with a media mimetype or\n// application/octet-stream means the browser doesn't try to render it as such.\n//\n// One interesting edge case is image/svg+xml, which empirically *is* rendered\n// correctly if the blob is set to the src attribute of an img tag (for thumbnails)\n// *even if the mimetype is application/octet-stream*.  However, empirically JS\n// in the SVG isn't executed in this scenario, so we seem to be okay.\n//\n// Tested on Chrome 65 and Firefox 60\n//\n// The list below is taken mainly from\n// https://developer.mozilla.org/en-US/docs/Web/HTML/Supported_media_formats\n// N.B. Matrix doesn't currently specify which mimetypes are valid in given\n// events, so we pick the ones which HTML5 browsers should be able to display\n//\n// For the record, mime-types which must NEVER enter this list below include:\n//   text/html, text/xhtml, image/svg, image/svg+xml, image/pdf, and similar.\n\nconst ALLOWED_BLOB_MIMETYPES = [\n    \"image/jpeg\",\n    \"image/gif\",\n    \"image/png\",\n    \"image/apng\",\n    \"image/webp\",\n    \"image/avif\",\n\n    \"video/mp4\",\n    \"video/webm\",\n    \"video/ogg\",\n    \"video/quicktime\",\n\n    \"audio/mp4\",\n    \"audio/webm\",\n    \"audio/aac\",\n    \"audio/mpeg\",\n    \"audio/ogg\",\n    \"audio/wave\",\n    \"audio/wav\",\n    \"audio/x-wav\",\n    \"audio/x-pn-wav\",\n    \"audio/flac\",\n    \"audio/x-flac\",\n];\n\n/**\n * Checks whether the given mime type is in the allowed mimetype list\n * @param mimetype - the mimetype to check\n */\nexport function isMimeTypeAllowed(mimetype: string): boolean {\n    return ALLOWED_BLOB_MIMETYPES.includes(mimetype);\n}\n\n/**\n * Returns the input mimetype if it is allowed, `application/octet-stream` otherwise\n * @param mimetype - the mimetype to check\n */\nexport function getBlobSafeMimeType(mimetype: string): string {\n    if (!isMimeTypeAllowed(mimetype)) {\n        return \"application/octet-stream\";\n    }\n    return mimetype;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { split } from \"lodash\";\n\nexport function textToHtmlRainbow(str: string): string {\n    const frequency = (2 * Math.PI) / str.length;\n\n    return split(str, \"\")\n        .map((c, i) => {\n            if (c === \" \") {\n                return c;\n            }\n            const [a, b] = generateAB(i * frequency, 1);\n            const [red, green, blue] = labToRGB(75, a, b);\n            return (\n                '<span data-mx-color=\"#' +\n                red.toString(16).padStart(2, \"0\") +\n                green.toString(16).padStart(2, \"0\") +\n                blue.toString(16).padStart(2, \"0\") +\n                '\">' +\n                c +\n                \"</span>\"\n            );\n        })\n        .join(\"\");\n}\n\nfunction generateAB(hue: number, chroma: number): [number, number] {\n    const a = chroma * 127 * Math.cos(hue);\n    const b = chroma * 127 * Math.sin(hue);\n\n    return [a, b];\n}\n\nfunction labToRGB(l: number, a: number, b: number): [number, number, number] {\n    // https://en.wikipedia.org/wiki/CIELAB_color_space#Reverse_transformation\n    // https://en.wikipedia.org/wiki/SRGB#The_forward_transformation_(CIE_XYZ_to_sRGB)\n\n    // Convert CIELAB to CIEXYZ (D65)\n    let y = (l + 16) / 116;\n    const x = adjustXYZ(y + a / 500) * 0.9505;\n    const z = adjustXYZ(y - b / 200) * 1.089;\n\n    y = adjustXYZ(y);\n\n    // Linear transformation from CIEXYZ to RGB\n    const red = 3.24096994 * x - 1.53738318 * y - 0.49861076 * z;\n    const green = -0.96924364 * x + 1.8759675 * y + 0.04155506 * z;\n    const blue = 0.05563008 * x - 0.20397696 * y + 1.05697151 * z;\n\n    return [adjustRGB(red), adjustRGB(green), adjustRGB(blue)];\n}\n\nfunction adjustXYZ(v: number): number {\n    if (v > 0.2069) {\n        return Math.pow(v, 3);\n    }\n    return 0.1284 * v - 0.01771;\n}\n\nfunction gammaCorrection(v: number): number {\n    // Non-linear transformation to sRGB\n    if (v <= 0.0031308) {\n        return 12.92 * v;\n    }\n    return 1.055 * Math.pow(v, 1 / 2.4) - 0.055;\n}\n\nfunction adjustRGB(v: number): number {\n    const corrected = gammaCorrection(v);\n\n    // Limits number between 0 and 1\n    const limited = Math.min(Math.max(corrected, 0), 1);\n\n    return Math.round(limited * 255);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ClientEvent, type ClientEventHandlerMap, SyncState } from \"matrix-js-sdk/src/matrix\";\n\n/**\n * Creates a MatrixClient event listener function that can be used to get notified about reconnects.\n * @param callback The callback to be called on reconnect\n */\nexport const createReconnectedListener = (callback: () => void): ClientEventHandlerMap[ClientEvent.Sync] => {\n    return (syncState: SyncState, prevState: SyncState | null) => {\n        if (syncState !== SyncState.Error && prevState !== syncState) {\n            // Consider the client reconnected if there is no error with syncing.\n            // This means the state could be RECONNECTING, SYNCING, PREPARED or CATCHUP.\n            callback();\n        }\n    };\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport default function factory(options?: WorkerOptions | undefined): Worker {\n    return new Worker(\n        /* webpackChunkName: \"indexeddb.worker\" */ new URL(\"./indexeddb.worker.ts\", import.meta.url),\n        options,\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2017-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\nimport {\n    type MatrixClient,\n    createClient,\n    type ICreateClientOpts,\n    MemoryCryptoStore,\n    MemoryStore,\n    IndexedDBCryptoStore,\n    IndexedDBStore,\n    LocalStorageCryptoStore,\n} from \"matrix-js-sdk/src/matrix\";\n\nimport indexeddbWorkerFactory from \"../workers/indexeddbWorkerFactory\";\n\nconst localStorage = window.localStorage;\n\n// just *accessing* indexedDB throws an exception in firefox with\n// indexeddb disabled.\nlet indexedDB: IDBFactory;\ntry {\n    indexedDB = window.indexedDB;\n} catch {}\n\n/**\n * Create a new matrix client, with the persistent stores set up appropriately\n * (using localstorage/indexeddb, etc)\n *\n * @param {Object} opts  options to pass to Matrix.createClient. This will be\n *    extended with `sessionStore` and `store` members.\n *\n * @returns {MatrixClient} the newly-created MatrixClient\n */\nexport default function createMatrixClient(opts: ICreateClientOpts): MatrixClient {\n    const storeOpts: Partial<ICreateClientOpts> = {\n        useAuthorizationHeader: true,\n    };\n\n    if (indexedDB && localStorage) {\n        storeOpts.store = new IndexedDBStore({\n            indexedDB: indexedDB,\n            dbName: \"riot-web-sync\",\n            localStorage,\n            workerFactory: indexeddbWorkerFactory,\n        });\n    } else if (localStorage) {\n        storeOpts.store = new MemoryStore({ localStorage });\n    }\n\n    if (indexedDB) {\n        storeOpts.cryptoStore = new IndexedDBCryptoStore(indexedDB, \"matrix-js-sdk:crypto\");\n    } else if (localStorage) {\n        storeOpts.cryptoStore = new LocalStorageCryptoStore(localStorage);\n    } else {\n        storeOpts.cryptoStore = new MemoryCryptoStore();\n    }\n\n    return createClient({\n        ...storeOpts,\n        ...opts,\n    });\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Device, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\n/**\n * Get crypto information on a specific device.\n *\n * Only devices with Crypto support are returned. If the MatrixClient doesn't support cryptography, `undefined` is\n * returned.\n *\n * @param client  - Matrix Client.\n * @param userId  - ID of the user owning the device.\n * @param deviceId - ID of the device.\n * @param downloadUncached - If true, download the device list for users whose device list we are not\n *    currently tracking. Defaults to false.\n *\n * @returns Information on the device if it is known.\n */\nexport async function getDeviceCryptoInfo(\n    client: MatrixClient,\n    userId: string,\n    deviceId: string,\n    downloadUncached?: boolean,\n): Promise<Device | undefined> {\n    const crypto = client.getCrypto();\n    if (!crypto) {\n        // no crypto support, no device.\n        return undefined;\n    }\n\n    const deviceMap = await crypto.getUserDeviceInfo([userId], downloadUncached);\n    return deviceMap.get(userId)?.get(deviceId);\n}\n\n/**\n * Get the IDs of the given user's devices.\n *\n * Only devices with Crypto support are returned. If the MatrixClient doesn't support cryptography, an empty Set is\n * returned.\n *\n * @param client  - Matrix Client.\n * @param userId  - ID of the user to query.\n */\n\nexport async function getUserDeviceIds(client: MatrixClient, userId: string): Promise<Set<string>> {\n    const crypto = client.getCrypto();\n    if (!crypto) {\n        return new Set();\n    }\n\n    const deviceMap = await crypto.getUserDeviceInfo([userId]);\n    return new Set(deviceMap.get(userId)?.keys() ?? []);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/** The `algorithm` property used in `m.room.encrypted` state events for encrypted rooms.\n */\nexport const MEGOLM_ENCRYPTION_ALGORITHM = \"m.megolm.v1.aes-sha2\";\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { getE2EEWellKnown } from \"../WellKnownUtils\";\n\n/**\n * Check e2ee io.element.e2ee setting\n * Returns true when .well-known e2ee config force_disable is TRUE\n * When true all new rooms should be created with encryption disabled\n * Can be overriden by synapse option encryption_enabled_by_default_for_room_type ( :/ )\n * https://matrix-org.github.io/synapse/latest/usage/configuration/config_documentation.html#encryption_enabled_by_default_for_room_type\n *\n * @param client\n * @returns whether well-known config forces encryption to DISABLED\n */\nexport function shouldForceDisableEncryption(client: MatrixClient): boolean {\n    const e2eeWellKnown = getE2EEWellKnown(client);\n\n    if (e2eeWellKnown) {\n        const shouldForceDisable = e2eeWellKnown[\"force_disable\"] === true;\n        return shouldForceDisable;\n    }\n    return false;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2024 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type StartDehydrationOpts } from \"matrix-js-sdk/src/crypto-api\";\n\nimport type { MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\n/**\n * If dehydration is supported by the server, rehydrate a device (if available) and create\n * a new dehydrated device.\n *\n * @param client - MatrixClient to use for the operation\n * @param opts - options for the startDehydration operation, if one is performed.\n */\nexport async function initialiseDehydrationIfEnabled(\n    client: MatrixClient,\n    opts: StartDehydrationOpts = {},\n): Promise<void> {\n    const crypto = client.getCrypto();\n    if (crypto && (await crypto.isDehydrationSupported())) {\n        logger.debug(\"Starting device dehydration\");\n        await crypto.startDehydration(opts);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport UAParser from \"ua-parser-js\";\n\nexport enum DeviceType {\n    Desktop = \"Desktop\",\n    Mobile = \"Mobile\",\n    Web = \"Web\",\n    Unknown = \"Unknown\",\n}\nexport type ExtendedDeviceInformation = {\n    deviceType: DeviceType;\n    // eg Google Pixel 6\n    deviceModel?: string;\n    // eg Android 11\n    deviceOperatingSystem?: string;\n    // eg Firefox 1.1.0\n    client?: string;\n};\n\n// Element/1.8.21 (iPhone XS Max; iOS 15.2; Scale/3.00)\nconst IOS_KEYWORD = \"; iOS \";\nconst BROWSER_KEYWORD = \"Mozilla/\";\n\nconst getDeviceType = (\n    userAgent: string,\n    device: UAParser.IDevice,\n    browser: UAParser.IBrowser,\n    operatingSystem: UAParser.IOS,\n): DeviceType => {\n    if (device.type === \"mobile\" || operatingSystem.name?.includes(\"Android\") || userAgent.indexOf(IOS_KEYWORD) > -1) {\n        return DeviceType.Mobile;\n    }\n    if (browser.name === \"Electron\") {\n        return DeviceType.Desktop;\n    }\n    if (!!browser.name) {\n        return DeviceType.Web;\n    }\n    return DeviceType.Unknown;\n};\n\ninterface CustomValues {\n    customDeviceModel?: string;\n    customDeviceOS?: string;\n}\n/**\n * Some mobile model and OS strings are not recognised\n * by the UA parsing library\n * check they exist by hand\n */\nconst checkForCustomValues = (userAgent: string): CustomValues => {\n    if (userAgent.includes(BROWSER_KEYWORD)) {\n        return {};\n    }\n\n    const mightHaveDevice = userAgent.includes(\"(\");\n    if (!mightHaveDevice) {\n        return {};\n    }\n    const deviceInfoSegments = userAgent.substring(userAgent.indexOf(\"(\") + 1).split(\"; \");\n    const customDeviceModel = deviceInfoSegments[0] || undefined;\n    const customDeviceOS = deviceInfoSegments[1] || undefined;\n    return { customDeviceModel, customDeviceOS };\n};\n\nconst concatenateNameAndVersion = (name?: string, version?: string): string | undefined =>\n    name && [name, version].filter(Boolean).join(\" \");\n\nexport const parseUserAgent = (userAgent?: string): ExtendedDeviceInformation => {\n    if (!userAgent) {\n        return {\n            deviceType: DeviceType.Unknown,\n        };\n    }\n\n    const parser = new UAParser(userAgent);\n\n    const browser = parser.getBrowser();\n    const device = parser.getDevice();\n    const operatingSystem = parser.getOS();\n\n    const deviceType = getDeviceType(userAgent, device, browser, operatingSystem);\n\n    // OSX versions are frozen at 10.15.17 in UA strings https://chromestatus.com/feature/5452592194781184\n    // ignore OS version in browser based sessions\n    const shouldIgnoreOSVersion = deviceType === DeviceType.Web || deviceType === DeviceType.Desktop;\n    const deviceOperatingSystem = concatenateNameAndVersion(\n        operatingSystem.name,\n        shouldIgnoreOSVersion ? undefined : operatingSystem.version,\n    );\n    const deviceModel = concatenateNameAndVersion(device.vendor, device.model);\n    const client = concatenateNameAndVersion(browser.name, browser.version);\n\n    // only try to parse custom model and OS when device type is known\n    const { customDeviceModel, customDeviceOS } =\n        deviceType !== DeviceType.Unknown ? checkForCustomValues(userAgent) : ({} as CustomValues);\n\n    return {\n        deviceType,\n        deviceModel: deviceModel || customDeviceModel,\n        deviceOperatingSystem: deviceOperatingSystem || customDeviceOS,\n        client,\n    };\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type IInvite3PID, type MatrixClient, type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { Action } from \"../../dispatcher/actions\";\nimport { type ViewRoomPayload } from \"../../dispatcher/payloads/ViewRoomPayload\";\nimport { determineCreateRoomEncryptionOption, type Member } from \"../direct-messages\";\nimport DMRoomMap from \"../DMRoomMap\";\nimport { isLocalRoom } from \"../localRoom/isLocalRoom\";\nimport { findDMForUser } from \"./findDMForUser\";\nimport dis from \"../../dispatcher/dispatcher\";\nimport { getAddressType } from \"../../UserAddress\";\nimport createRoom, { type IOpts } from \"../../createRoom\";\n\n/**\n * Start a DM.\n *\n * @returns {Promise<string | null} Resolves to the room id.\n */\nexport async function startDm(client: MatrixClient, targets: Member[], showSpinner = true): Promise<string | null> {\n    const targetIds = targets.map((t) => t.userId);\n\n    // Check if there is already a DM with these people and reuse it if possible.\n    let existingRoom: Room | undefined;\n    if (targetIds.length === 1) {\n        existingRoom = findDMForUser(client, targetIds[0]);\n    } else {\n        existingRoom = DMRoomMap.shared().getDMRoomForIdentifiers(targetIds) ?? undefined;\n    }\n    if (existingRoom && !isLocalRoom(existingRoom)) {\n        dis.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            room_id: existingRoom.roomId,\n            should_peek: false,\n            joining: false,\n            metricsTrigger: \"MessageUser\",\n        });\n        return Promise.resolve(existingRoom.roomId);\n    }\n\n    const createRoomOptions: IOpts = { inlineErrors: true };\n\n    if (await determineCreateRoomEncryptionOption(client, targets)) {\n        createRoomOptions.encryption = true;\n    }\n\n    // Check if it's a traditional DM and create the room if required.\n    // TODO: [Canonical DMs] Remove this check and instead just create the multi-person DM\n    const isSelf = targetIds.length === 1 && targetIds[0] === client.getUserId();\n    if (targetIds.length === 1 && !isSelf) {\n        createRoomOptions.dmUserId = targetIds[0];\n    }\n\n    if (targetIds.length > 1) {\n        createRoomOptions.createOpts = targetIds.reduce<{\n            invite_3pid: IInvite3PID[];\n            invite: string[];\n        }>(\n            (roomOptions, address) => {\n                const type = getAddressType(address);\n                if (type === \"email\") {\n                    const invite: IInvite3PID = {\n                        id_server: client.getIdentityServerUrl(true)!,\n                        medium: \"email\",\n                        address,\n                    };\n                    roomOptions.invite_3pid.push(invite);\n                } else if (type === \"mx-user-id\") {\n                    roomOptions.invite.push(address);\n                }\n                return roomOptions;\n            },\n            { invite: [], invite_3pid: [] },\n        );\n    }\n\n    createRoomOptions.spinner = showSpinner;\n    return createRoom(client, createRoomOptions);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { DirectoryMember, type Member, ThreepidMember } from \"./direct-messages\";\n\n/**\n * Tries to resolve the ThreepidMembers to DirectoryMembers.\n *\n * @param members - List of members to resolve\n * @returns {Promise<Member[]>} Same list with ThreepidMembers replaced by DirectoryMembers if succesfully resolved\n */\nexport const resolveThreePids = async (members: Member[], client: MatrixClient): Promise<Member[]> => {\n    const threePidMembers = members.filter((m) => m instanceof ThreepidMember) as ThreepidMember[];\n\n    // Nothing to do here\n    if (threePidMembers.length === 0) return members;\n\n    const lookedUpProfiles = await lookupThreePidProfiles(threePidMembers, client);\n\n    return members.map((member: Member) => {\n        if (!(member instanceof ThreepidMember)) return member;\n\n        const lookedUpProfile = lookedUpProfiles.find((r) => r.threePidId === member.userId);\n\n        // No profile found for this member; use the ThreepidMember.\n        if (!lookedUpProfile) return member;\n\n        return new DirectoryMember({\n            user_id: lookedUpProfile.mxid,\n            avatar_url: lookedUpProfile?.profile?.avatar_url,\n            display_name: lookedUpProfile?.profile?.displayname,\n        });\n    });\n};\n\n/**\n * Tries to look up the ThreepidMembers.\n *\n * @param threePids - List of 3rd-party members to look up\n * @returns  List of resolved 3rd-party IDs with their MXIDs\n */\nexport const lookupThreePids = async (\n    threePids: ThreepidMember[],\n    client: MatrixClient,\n): Promise<{ threePidId: string; mxid: string }[]> => {\n    // No identity server configured. Unable to resolve any 3rd party member.\n    if (!client.identityServer) return [];\n\n    // Nothing we can search, return null\n    if (threePids.length === 0) return [];\n\n    const token = await client.identityServer.getAccessToken();\n\n    if (!token) return [];\n\n    const lookedUp = await client.bulkLookupThreePids(\n        threePids.map((t) => [t.isEmail ? \"email\" : \"msisdn\", t.userId]),\n        token,\n    );\n\n    return lookedUp.threepids.map(([_threePidType, threePidId, mxid]: [string, string, string]) => ({\n        threePidId,\n        mxid,\n    }));\n};\n\n/**\n * Tries to look up the MXIDs and profiles of the ThreepidMembers.\n *\n * @param threePids - List of 3rd-prty members to look up\n * @returns List of resolved 3rd-party members with their MXIDs and profile (if found)\n */\nexport const lookupThreePidProfiles = async (\n    threePids: ThreepidMember[],\n    client: MatrixClient,\n): Promise<{ threePidId: string; mxid: string; profile: null | { avatar_url?: string; displayname?: string } }[]> => {\n    const lookedUpThreePids = await lookupThreePids(threePids, client);\n    const promises = lookedUpThreePids.map(async (t) => {\n        let profile: null | { avatar_url?: string; display_name?: string } = null;\n\n        try {\n            profile = await client.getProfileInfo(t.mxid);\n        } catch {\n            // ignore any lookup error\n        }\n\n        return {\n            threePidId: t.threePidId,\n            mxid: t.mxid,\n            profile,\n        };\n    });\n    return Promise.all(promises);\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { ClientEvent, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { canEncryptToAllUsers } from \"../createRoom\";\nimport { Action } from \"../dispatcher/actions\";\nimport { type ViewRoomPayload } from \"../dispatcher/payloads/ViewRoomPayload\";\nimport dis from \"../dispatcher/dispatcher\";\nimport { type LocalRoom, LocalRoomState } from \"../models/LocalRoom\";\nimport { waitForRoomReadyAndApplyAfterCreateCallbacks } from \"./local-room\";\nimport { findDMRoom } from \"./dm/findDMRoom\";\nimport { privateShouldBeEncrypted } from \"./rooms\";\nimport { createDmLocalRoom } from \"./dm/createDmLocalRoom\";\nimport { startDm } from \"./dm/startDm\";\nimport { resolveThreePids } from \"./threepids\";\n\nexport async function startDmOnFirstMessage(client: MatrixClient, targets: Member[]): Promise<string | null> {\n    let resolvedTargets = targets;\n\n    try {\n        resolvedTargets = await resolveThreePids(targets, client);\n    } catch (e) {\n        logger.warn(\"Error resolving 3rd-party members\", e);\n    }\n\n    const existingRoom = findDMRoom(client, resolvedTargets);\n\n    if (existingRoom) {\n        dis.dispatch<ViewRoomPayload>({\n            action: Action.ViewRoom,\n            room_id: existingRoom.roomId,\n            should_peek: false,\n            joining: false,\n            metricsTrigger: \"MessageUser\",\n        });\n        return existingRoom.roomId;\n    }\n\n    if (targets.length === 1 && targets[0] instanceof ThreepidMember && privateShouldBeEncrypted(client)) {\n        // Single 3rd-party invite and well-known promotes encryption:\n        // Directly create a room and invite the other.\n        return await startDm(client, targets);\n    }\n\n    const room = await createDmLocalRoom(client, resolvedTargets);\n    dis.dispatch({\n        action: Action.ViewRoom,\n        room_id: room.roomId,\n        joining: false,\n        targets: resolvedTargets,\n    });\n    return room.roomId;\n}\n\n/**\n * Starts a DM based on a local room.\n *\n * @async\n * @param {MatrixClient} client\n * @param {LocalRoom} localRoom\n * @returns {Promise<string | void>} Resolves to the created room id\n */\nexport async function createRoomFromLocalRoom(client: MatrixClient, localRoom: LocalRoom): Promise<string | void> {\n    if (!localRoom.isNew) {\n        // This action only makes sense for new local rooms.\n        return;\n    }\n\n    localRoom.state = LocalRoomState.CREATING;\n    client.emit(ClientEvent.Room, localRoom);\n\n    return startDm(client, localRoom.targets, false).then(\n        (roomId) => {\n            if (!roomId) throw new Error(`startDm for local room ${localRoom.roomId} didn't return a room Id`);\n\n            localRoom.actualRoomId = roomId;\n            return waitForRoomReadyAndApplyAfterCreateCallbacks(client, localRoom, roomId);\n        },\n        () => {\n            logger.warn(`Error creating DM for local room ${localRoom.roomId}`);\n            localRoom.state = LocalRoomState.ERROR;\n            client.emit(ClientEvent.Room, localRoom);\n        },\n    );\n}\n\n// This is the interface that is expected by various components in the Invite Dialog and RoomInvite.\n// It is a bit awkward because it also matches the RoomMember class from the js-sdk with some extra support\n// for 3PIDs/email addresses.\nexport abstract class Member {\n    /**\n     * The display name of this Member. For users this should be their profile's display\n     * name or user ID if none set. For 3PIDs this should be the 3PID address (email).\n     */\n    public abstract get name(): string;\n\n    /**\n     * The ID of this Member. For users this should be their user ID. For 3PIDs this should\n     * be the 3PID address (email).\n     */\n    public abstract get userId(): string;\n\n    /**\n     * Gets the MXC URL of this Member's avatar. For users this should be their profile's\n     * avatar MXC URL or null if none set. For 3PIDs this should always be undefined.\n     */\n    public abstract getMxcAvatarUrl(): string | undefined;\n}\n\nexport class DirectoryMember extends Member {\n    private readonly _userId: string;\n    private readonly displayName?: string;\n    private readonly avatarUrl?: string;\n\n    // eslint-disable-next-line camelcase\n    public constructor(userDirResult: { user_id: string; display_name?: string; avatar_url?: string }) {\n        super();\n        this._userId = userDirResult.user_id;\n        this.displayName = userDirResult.display_name;\n        this.avatarUrl = userDirResult.avatar_url;\n    }\n\n    // These next class members are for the Member interface\n    public get name(): string {\n        return this.displayName || this._userId;\n    }\n\n    public get userId(): string {\n        return this._userId;\n    }\n\n    public getMxcAvatarUrl(): string | undefined {\n        return this.avatarUrl;\n    }\n}\n\nexport class ThreepidMember extends Member {\n    private readonly id: string;\n\n    public constructor(id: string) {\n        super();\n        this.id = id;\n    }\n\n    // This is a getter that would be falsy on all other implementations. Until we have\n    // better type support in the react-sdk we can use this trick to determine the kind\n    // of 3PID we're dealing with, if any.\n    public get isEmail(): boolean {\n        return this.id.includes(\"@\");\n    }\n\n    // These next class members are for the Member interface\n    public get name(): string {\n        return this.id;\n    }\n\n    public get userId(): string {\n        return this.id;\n    }\n\n    public getMxcAvatarUrl(): string | undefined {\n        return undefined;\n    }\n}\n\nexport interface IDMUserTileProps {\n    member: Member;\n    onRemove?(member: Member): void;\n}\n\n/**\n * Detects whether a room should be encrypted.\n *\n * @async\n * @param {MatrixClient} client\n * @param {Member[]} targets The members to which run the check against\n * @returns {Promise<boolean>}\n */\nexport async function determineCreateRoomEncryptionOption(client: MatrixClient, targets: Member[]): Promise<boolean> {\n    if (privateShouldBeEncrypted(client)) {\n        // Enable encryption for a single 3rd party invite.\n        if (targets.length === 1 && targets[0] instanceof ThreepidMember) return true;\n\n        // Check whether all users have uploaded device keys before.\n        // If so, enable encryption in the new room.\n        const has3PidMembers = targets.some((t) => t instanceof ThreepidMember);\n        if (!has3PidMembers) {\n            const targetIds = targets.map((t) => t.userId);\n            const allHaveDeviceKeys = await canEncryptToAllUsers(client, targetIds);\n            if (allHaveDeviceKeys) {\n                return true;\n            }\n        }\n    }\n\n    return false;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient, type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { type Member } from \"../direct-messages\";\nimport DMRoomMap from \"../DMRoomMap\";\nimport { findDMForUser } from \"./findDMForUser\";\n\n/**\n * Tries to find a DM room with some other users.\n *\n * @param {MatrixClient} client\n * @param {Member[]} targets The Members to try to find the room for\n * @returns {Room | null} Resolved so the room if found, else null\n */\nexport function findDMRoom(client: MatrixClient, targets: Member[]): Room | null {\n    const targetIds = targets.map((t) => t.userId);\n    let existingRoom: Room | null;\n    if (targetIds.length === 1) {\n        existingRoom = findDMForUser(client, targetIds[0]) ?? null;\n    } else {\n        existingRoom = DMRoomMap.shared().getDMRoomForIdentifiers(targetIds);\n    }\n    return existingRoom;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EventType, KNOWN_SAFE_ROOM_VERSION, type MatrixClient, MatrixEvent } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport { LOCAL_ROOM_ID_PREFIX, LocalRoom } from \"../../../src/models/LocalRoom\";\nimport { determineCreateRoomEncryptionOption, type Member } from \"../../../src/utils/direct-messages\";\nimport { MEGOLM_ENCRYPTION_ALGORITHM } from \"../crypto\";\n\n/**\n * Create a DM local room. This room will not be send to the server and only exists inside the client.\n * It sets up the local room with some artificial state events\n * so that can be used in most components instead of a „real“ room.\n *\n * @async\n * @param {MatrixClient} client\n * @param {Member[]} targets DM partners\n * @returns {Promise<LocalRoom>} Resolves to the new local room\n */\nexport async function createDmLocalRoom(client: MatrixClient, targets: Member[]): Promise<LocalRoom> {\n    const userId = client.getUserId()!;\n\n    const localRoom = new LocalRoom(LOCAL_ROOM_ID_PREFIX + client.makeTxnId(), client, userId);\n    const events: MatrixEvent[] = [];\n\n    events.push(\n        new MatrixEvent({\n            event_id: `~${localRoom.roomId}:${client.makeTxnId()}`,\n            type: EventType.RoomCreate,\n            content: {\n                creator: userId,\n                room_version: KNOWN_SAFE_ROOM_VERSION,\n            },\n            state_key: \"\",\n            sender: userId,\n            room_id: localRoom.roomId,\n            origin_server_ts: Date.now(),\n        }),\n    );\n\n    if (await determineCreateRoomEncryptionOption(client, targets)) {\n        localRoom.encrypted = true;\n        events.push(\n            new MatrixEvent({\n                event_id: `~${localRoom.roomId}:${client.makeTxnId()}`,\n                type: EventType.RoomEncryption,\n                content: {\n                    algorithm: MEGOLM_ENCRYPTION_ALGORITHM,\n                },\n                sender: userId,\n                state_key: \"\",\n                room_id: localRoom.roomId,\n                origin_server_ts: Date.now(),\n            }),\n        );\n    }\n\n    events.push(\n        new MatrixEvent({\n            event_id: `~${localRoom.roomId}:${client.makeTxnId()}`,\n            type: EventType.RoomMember,\n            content: {\n                displayname: userId,\n                membership: KnownMembership.Join,\n            },\n            state_key: userId,\n            sender: userId,\n            room_id: localRoom.roomId,\n        }),\n    );\n\n    targets.forEach((target: Member) => {\n        events.push(\n            new MatrixEvent({\n                event_id: `~${localRoom.roomId}:${client.makeTxnId()}`,\n                type: EventType.RoomMember,\n                content: {\n                    displayname: target.name,\n                    avatar_url: target.getMxcAvatarUrl() ?? undefined,\n                    membership: KnownMembership.Invite,\n                    isDirect: true,\n                },\n                state_key: target.userId,\n                sender: userId,\n                room_id: localRoom.roomId,\n            }),\n        );\n        events.push(\n            new MatrixEvent({\n                event_id: `~${localRoom.roomId}:${client.makeTxnId()}`,\n                type: EventType.RoomMember,\n                content: {\n                    displayname: target.name,\n                    avatar_url: target.getMxcAvatarUrl() ?? undefined,\n                    membership: KnownMembership.Join,\n                },\n                state_key: target.userId,\n                sender: target.userId,\n                room_id: localRoom.roomId,\n            }),\n        );\n    });\n\n    localRoom.targets = targets;\n    localRoom.updateMyMembership(KnownMembership.Join);\n    localRoom.addLiveEvents(events, { addToState: true });\n    localRoom.currentState.setStateEvents(events);\n    localRoom.name = localRoom.getDefaultRoomName(client.getUserId()!);\n    client.store.storeRoom(localRoom);\n\n    return localRoom;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\ninterface FilterValidMDirectResult {\n    /** Whether the entire content is valid */\n    valid: boolean;\n    /** Filtered content with only the valid parts */\n    filteredContent: Record<string, string[]>;\n}\n\n/**\n * Filter m.direct content to be compliant to https://spec.matrix.org/v1.6/client-server-api/#mdirect.\n *\n * @param content - Raw event content to be filerted\n * @returns value as a flag whether to content was valid.\n *          filteredContent with only values from the content that are spec compliant.\n */\nexport const filterValidMDirect = (content: unknown): FilterValidMDirectResult => {\n    if (content === null || typeof content !== \"object\") {\n        return {\n            valid: false,\n            filteredContent: {},\n        };\n    }\n\n    const filteredContent = new Map();\n    let valid = true;\n\n    for (const [userId, roomIds] of Object.entries(content)) {\n        if (typeof userId !== \"string\") {\n            valid = false;\n            continue;\n        }\n\n        if (!Array.isArray(roomIds)) {\n            valid = false;\n            continue;\n        }\n\n        const filteredRoomIds: string[] = [];\n        filteredContent.set(userId, filteredRoomIds);\n\n        for (const roomId of roomIds) {\n            if (typeof roomId === \"string\") {\n                filteredRoomIds.push(roomId);\n            } else {\n                valid = false;\n            }\n        }\n    }\n\n    return {\n        valid,\n        filteredContent: Object.fromEntries(filteredContent.entries()),\n    };\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient, type Room } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport DMRoomMap from \"../DMRoomMap\";\nimport { isLocalRoom } from \"../localRoom/isLocalRoom\";\nimport { isJoinedOrNearlyJoined } from \"../membership\";\nimport { getFunctionalMembers } from \"../room/getFunctionalMembers\";\n\n/**\n * Iterates the rooms and tries to find a DM room with the user identified by UserId.\n * A DM room is assumed if one of the following matches:\n * - Has two members and contains a membership for the user identified by userId\n * - findRoomWithThirdpartyInvites is true and has one member and a third pending third party invite\n *\n * If multiple rooms match it will return the one with the most recent event.\n *\n * @param rooms - Rooms to iterate\n * @param userId - User Id of the other user\n * @param [findRoomWithThirdpartyInvites] - Whether to find a DM for a pending thirdparty invite\n * @returns DM room if found or undefined if not\n */\nfunction extractSuitableRoom(rooms: Room[], userId: string, findRoomWithThirdpartyInvites: boolean): Room | undefined {\n    const suitableRooms = rooms\n        .filter((r) => {\n            // Validate that we are joined and the other person is also joined. We'll also make sure\n            // that the room also looks like a DM (until we have canonical DMs to tell us). For now,\n            // a DM is a room of two people that contains those two people exactly. This does mean\n            // that bots, assistants, etc will ruin a room's DM-ness, though this is a problem for\n            // canonical DMs to solve.\n            if (r && r.getMyMembership() === KnownMembership.Join) {\n                if (isLocalRoom(r)) return false;\n\n                const functionalUsers = getFunctionalMembers(r);\n                const members = r.currentState.getMembers();\n                const joinedMembers = members.filter(\n                    (m) => !functionalUsers.includes(m.userId) && m.membership && isJoinedOrNearlyJoined(m.membership),\n                );\n                const otherMember = joinedMembers.find((m) => m.userId === userId);\n\n                if (otherMember && joinedMembers.length === 2) {\n                    return true;\n                }\n\n                const thirdPartyInvites = r.currentState.getStateEvents(\"m.room.third_party_invite\") || [];\n\n                // match room with pending third-party invite\n                return findRoomWithThirdpartyInvites && joinedMembers.length === 1 && thirdPartyInvites.length === 1;\n            }\n            return false;\n        })\n        .sort((r1, r2) => {\n            return r2.getLastActiveTimestamp() - r1.getLastActiveTimestamp();\n        });\n\n    if (suitableRooms.length) {\n        return suitableRooms[0];\n    }\n\n    return undefined;\n}\n\n/**\n * Tries to find a DM room with a specific user.\n *\n * @param {MatrixClient} client\n * @param {string} userId ID of the user to find the DM for\n * @returns {Room | undefined} Room if found\n */\nexport function findDMForUser(client: MatrixClient, userId: string): Room | undefined {\n    const roomIdsForUserId = DMRoomMap.shared().getDMRoomsForUserId(userId);\n    const roomsForUserId = roomIdsForUserId.map((id) => client.getRoom(id)).filter((r): r is Room => r !== null);\n    // Call with findRoomWithThirdpartyInvites = true to also include rooms with pending thirdparty invites.\n    // roomsForUserId can only contain rooms with the other user here,\n    // because they have been queried by getDMRoomsForUserId().\n    const suitableRoomForUserId = extractSuitableRoom(roomsForUserId, userId, true);\n\n    if (suitableRoomForUserId) {\n        return suitableRoomForUserId;\n    }\n\n    // Try to find in all rooms as a fallback\n    const allRoomIds = DMRoomMap.shared().getRoomIds();\n    const allRooms = Array.from(allRoomIds)\n        .map((id) => client.getRoom(id))\n        .filter((r): r is Room => r !== null);\n    return extractSuitableRoom(allRooms, userId, false);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Request, type Response } from \"./workers/blurhash.worker.ts\";\nimport { WorkerManager } from \"./WorkerManager\";\nimport blurhashWorkerFactory from \"./workers/blurhashWorkerFactory\";\n\nexport class BlurhashEncoder {\n    private static internalInstance = new BlurhashEncoder();\n\n    public static get instance(): BlurhashEncoder {\n        return BlurhashEncoder.internalInstance;\n    }\n\n    private readonly worker = new WorkerManager<Request, Response>(blurhashWorkerFactory());\n\n    public getBlurhash(imageData: ImageData): Promise<string> {\n        return this.worker.call({ imageData }).then((resp) => resp.blurhash);\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport default function factory(options?: WorkerOptions | undefined): Worker {\n    return new Worker(\n        /* webpackChunkName: \"blurhash.worker\" */ new URL(\"./blurhash.worker.ts\", import.meta.url),\n        options,\n    );\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ImageInfo } from \"matrix-js-sdk/src/types\";\n\nimport { BlurhashEncoder } from \"../BlurhashEncoder\";\n\ntype ThumbnailableElement = HTMLImageElement | HTMLVideoElement;\n\nexport const BLURHASH_FIELD = \"xyz.amorgan.blurhash\"; // MSC2448\n\ninterface IThumbnail {\n    info: ImageInfo;\n    thumbnail: Blob;\n}\n\nconst MAX_WIDTH = 800;\nconst MAX_HEIGHT = 600;\n\n/**\n * Create a thumbnail for a image DOM element.\n * The image will be smaller than MAX_WIDTH and MAX_HEIGHT.\n * The thumbnail will have the same aspect ratio as the original.\n * Draws the element into a canvas using CanvasRenderingContext2D.drawImage\n * Then calls Canvas.toBlob to get a blob object for the image data.\n *\n * Since it needs to calculate the dimensions of the source image and the\n * thumbnailed image it returns an info object filled out with information\n * about the original image and the thumbnail.\n *\n * @param {HTMLElement} element The element to thumbnail.\n * @param {number} inputWidth The width of the image in the input element.\n * @param {number} inputHeight the width of the image in the input element.\n * @param {string} mimeType The mimeType to save the blob as.\n * @param {boolean} calculateBlurhash Whether to calculate a blurhash of the given image too.\n * @return {Promise} A promise that resolves with an object with an info key\n *  and a thumbnail key.\n */\nexport async function createThumbnail(\n    element: ThumbnailableElement,\n    inputWidth: number,\n    inputHeight: number,\n    mimeType: string,\n    calculateBlurhash = true,\n): Promise<IThumbnail> {\n    let targetWidth = inputWidth;\n    let targetHeight = inputHeight;\n    if (targetHeight > MAX_HEIGHT) {\n        targetWidth = Math.floor(targetWidth * (MAX_HEIGHT / targetHeight));\n        targetHeight = MAX_HEIGHT;\n    }\n    if (targetWidth > MAX_WIDTH) {\n        targetHeight = Math.floor(targetHeight * (MAX_WIDTH / targetWidth));\n        targetWidth = MAX_WIDTH;\n    }\n\n    let canvas: HTMLCanvasElement | OffscreenCanvas;\n    let context: CanvasRenderingContext2D | OffscreenCanvasRenderingContext2D;\n    try {\n        canvas = new window.OffscreenCanvas(targetWidth, targetHeight);\n        context = canvas.getContext(\"2d\") as OffscreenCanvasRenderingContext2D;\n    } catch {\n        // Fallback support for other browsers (Safari and Firefox for now)\n        canvas = document.createElement(\"canvas\");\n        canvas.width = targetWidth;\n        canvas.height = targetHeight;\n        context = canvas.getContext(\"2d\")!;\n    }\n\n    context.drawImage(element, 0, 0, targetWidth, targetHeight);\n\n    let thumbnailPromise: Promise<Blob>;\n    if (window.OffscreenCanvas && canvas instanceof OffscreenCanvas) {\n        thumbnailPromise = canvas.convertToBlob({ type: mimeType });\n    } else {\n        thumbnailPromise = new Promise<Blob>((resolve) =>\n            (canvas as HTMLCanvasElement).toBlob(resolve as BlobCallback, mimeType),\n        );\n    }\n\n    const imageData = context.getImageData(0, 0, targetWidth, targetHeight);\n    // thumbnailPromise and blurhash promise are being awaited concurrently\n    const blurhash = calculateBlurhash ? await BlurhashEncoder.instance.getBlurhash(imageData) : undefined;\n    const thumbnail = await thumbnailPromise;\n\n    return {\n        info: {\n            thumbnail_info: {\n                w: targetWidth,\n                h: targetHeight,\n                mimetype: thumbnail.type,\n                size: thumbnail.size,\n            },\n            w: inputWidth,\n            h: inputHeight,\n            [BLURHASH_FIELD]: blurhash,\n        },\n        thumbnail,\n    };\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useMemo, useState } from \"react\";\nimport { type Room, JoinRule } from \"matrix-js-sdk/src/matrix\";\nimport { InfoSolidIcon } from \"@vector-im/compound-design-tokens/assets/web/icons\";\n\nimport { _t } from \"../../../languageHandler\";\nimport DialogButtons from \"../elements/DialogButtons\";\nimport BaseDialog from \"../dialogs/BaseDialog\";\nimport SpaceStore from \"../../../stores/spaces/SpaceStore\";\nimport SpaceChildrenPicker from \"../spaces/SpaceChildrenPicker\";\nimport { filterBoolean } from \"../../../utils/arrays\";\nimport { isOnlyAdmin } from \"../../../utils/membership\";\n\ninterface IProps {\n    space: Room;\n    onFinished(leave: boolean, rooms?: Room[]): void;\n}\n\nconst LeaveSpaceDialog: React.FC<IProps> = ({ space, onFinished }) => {\n    const spaceChildren = useMemo(() => {\n        const roomSet = new Set(SpaceStore.instance.getSpaceFilteredRoomIds(space.roomId));\n        SpaceStore.instance.traverseSpace(\n            space.roomId,\n            (spaceId) => {\n                if (space.roomId === spaceId) return; // skip the root node\n                roomSet.add(spaceId);\n            },\n            false,\n        );\n        return filterBoolean(Array.from(roomSet).map((roomId) => space.client.getRoom(roomId)));\n    }, [space]);\n    const [roomsToLeave, setRoomsToLeave] = useState<Room[]>([]);\n    const selectedRooms = useMemo(() => new Set(roomsToLeave), [roomsToLeave]);\n\n    let rejoinWarning;\n    if (space.getJoinRule() !== JoinRule.Public) {\n        rejoinWarning = _t(\"space|leave_dialog_public_rejoin_warning\");\n    }\n\n    let onlyAdminWarning;\n    if (isOnlyAdmin(space)) {\n        onlyAdminWarning = _t(\"space|leave_dialog_only_admin_warning\");\n    } else {\n        const numChildrenOnlyAdminIn = roomsToLeave.filter(isOnlyAdmin).length;\n        if (numChildrenOnlyAdminIn > 0) {\n            onlyAdminWarning = _t(\"space|leave_dialog_only_admin_room_warning\");\n        }\n    }\n\n    return (\n        <BaseDialog\n            title={_t(\"space|leave_dialog_title\", { spaceName: space.name })}\n            className=\"mx_LeaveSpaceDialog\"\n            contentId=\"mx_LeaveSpaceDialog\"\n            onFinished={() => onFinished(false)}\n            fixedWidth={false}\n        >\n            <div className=\"mx_Dialog_content\" id=\"mx_LeaveSpaceDialog\">\n                <p>\n                    {_t(\n                        \"space|leave_dialog_description\",\n                        {},\n                        {\n                            spaceName: () => <strong>{space.name}</strong>,\n                        },\n                    )}\n                    &nbsp;\n                    {rejoinWarning}\n                    {rejoinWarning && <>&nbsp;</>}\n                    {spaceChildren.length > 0 && _t(\"space|leave_dialog_option_intro\")}\n                </p>\n\n                {spaceChildren.length > 0 && (\n                    <SpaceChildrenPicker\n                        space={space}\n                        spaceChildren={spaceChildren}\n                        selected={selectedRooms}\n                        onChange={setRoomsToLeave}\n                        noneLabel={_t(\"space|leave_dialog_option_none\")}\n                        allLabel={_t(\"space|leave_dialog_option_all\")}\n                        specificLabel={_t(\"space|leave_dialog_option_specific\")}\n                    />\n                )}\n\n                {onlyAdminWarning && (\n                    <div className=\"mx_LeaveSpaceDialog_section_warning\">\n                        <InfoSolidIcon />\n                        {onlyAdminWarning}\n                    </div>\n                )}\n            </div>\n            <DialogButtons\n                primaryButton={_t(\"space|leave_dialog_action\")}\n                primaryButtonClass=\"danger\"\n                onPrimaryButtonClick={() => onFinished(true, roomsToLeave)}\n                hasCancel={true}\n                onCancel={() => onFinished(false)}\n            />\n        </BaseDialog>\n    );\n};\n\nexport default LeaveSpaceDialog;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { sleep } from \"matrix-js-sdk/src/utils\";\nimport React, { type ReactNode } from \"react\";\nimport { EventStatus, MatrixEventEvent, type Room, type MatrixClient, MatrixError } from \"matrix-js-sdk/src/matrix\";\n\nimport Modal, { type IHandle } from \"../Modal\";\nimport Spinner from \"../components/views/elements/Spinner\";\nimport { _t } from \"../languageHandler\";\nimport ErrorDialog from \"../components/views/dialogs/ErrorDialog\";\nimport { isMetaSpace } from \"../stores/spaces\";\nimport SpaceStore from \"../stores/spaces/SpaceStore\";\nimport dis from \"../dispatcher/dispatcher\";\nimport { type ViewRoomPayload } from \"../dispatcher/payloads/ViewRoomPayload\";\nimport { Action } from \"../dispatcher/actions\";\nimport { type ViewHomePagePayload } from \"../dispatcher/payloads/ViewHomePagePayload\";\nimport LeaveSpaceDialog from \"../components/views/dialogs/LeaveSpaceDialog\";\nimport { type AfterLeaveRoomPayload } from \"../dispatcher/payloads/AfterLeaveRoomPayload\";\nimport { bulkSpaceBehaviour } from \"./space\";\nimport { SdkContextClass } from \"../contexts/SDKContext\";\nimport SettingsStore from \"../settings/SettingsStore\";\n\nexport async function leaveRoomBehaviour(\n    matrixClient: MatrixClient,\n    roomId: string,\n    retry = true,\n    spinner = true,\n): Promise<void> {\n    let spinnerModal: IHandle<any> | undefined;\n    if (spinner) {\n        spinnerModal = Modal.createDialog(Spinner, undefined, \"mx_Dialog_spinner\");\n    }\n\n    let leavingAllVersions = true;\n    const history = matrixClient.getRoomUpgradeHistory(\n        roomId,\n        true,\n        SettingsStore.getValue(\"feature_dynamic_room_predecessors\"),\n    );\n    if (history && history.length > 0) {\n        const currentRoom = history[history.length - 1];\n        if (currentRoom.roomId !== roomId) {\n            // The user is trying to leave an older version of the room. Let them through\n            // without making them leave the current version of the room.\n            leavingAllVersions = false;\n        }\n    }\n\n    const room = matrixClient.getRoom(roomId);\n\n    // should not encounter this\n    if (!room) {\n        throw new Error(`Expected to find room for id ${roomId}`);\n    }\n\n    // await any queued messages being sent so that they do not fail\n    await Promise.all(\n        room\n            .getPendingEvents()\n            .filter((ev) => {\n                return [EventStatus.QUEUED, EventStatus.ENCRYPTING, EventStatus.SENDING].includes(ev.status!);\n            })\n            .map(\n                (ev) =>\n                    new Promise<void>((resolve, reject) => {\n                        const handler = (): void => {\n                            if (ev.status === EventStatus.NOT_SENT) {\n                                spinnerModal?.close();\n                                reject(ev.error);\n                            }\n\n                            if (!ev.status || ev.status === EventStatus.SENT) {\n                                ev.off(MatrixEventEvent.Status, handler);\n                                resolve();\n                            }\n                        };\n\n                        ev.on(MatrixEventEvent.Status, handler);\n                    }),\n            ),\n    );\n\n    let results: { [roomId: string]: Error | MatrixError | null } = {};\n    if (!leavingAllVersions) {\n        try {\n            await matrixClient.leave(roomId);\n        } catch (e) {\n            if (e instanceof MatrixError) {\n                const message = e.data.error || _t(\"room|leave_unexpected_error\");\n                results[roomId] = Object.assign(new Error(message), { errcode: e.data.errcode, data: e.data });\n            } else if (e instanceof Error) {\n                results[roomId] = e;\n            } else {\n                results[roomId] = new Error(\"Failed to leave room for unknown causes\");\n            }\n        }\n    } else {\n        results = await matrixClient.leaveRoomChain(roomId, retry);\n    }\n\n    if (retry) {\n        const limitExceededError = Object.values(results).find(\n            (e) => (e as MatrixError)?.errcode === \"M_LIMIT_EXCEEDED\",\n        ) as MatrixError;\n        if (limitExceededError) {\n            await sleep(limitExceededError.data.retry_after_ms ?? 100);\n            return leaveRoomBehaviour(matrixClient, roomId, false, false);\n        }\n    }\n\n    spinnerModal?.close();\n\n    const errors = Object.entries(results).filter((r) => !!r[1]);\n    if (errors.length > 0) {\n        const messages: ReactNode[] = [];\n        for (const roomErr of errors) {\n            const err = roomErr[1] as MatrixError; // [0] is the roomId\n            let message = _t(\"room|leave_unexpected_error\");\n            if (err?.errcode && err.message) {\n                if (err.errcode === \"M_CANNOT_LEAVE_SERVER_NOTICE_ROOM\") {\n                    Modal.createDialog(ErrorDialog, {\n                        title: _t(\"room|leave_server_notices_title\"),\n                        description: _t(\"room|leave_server_notices_description\"),\n                    });\n                    return;\n                }\n                message = results[roomId]!.message;\n            }\n            messages.push(message, React.createElement(\"BR\")); // createElement to avoid using a tsx file in utils\n        }\n        Modal.createDialog(ErrorDialog, {\n            title: _t(\"room|leave_error_title\"),\n            description: messages,\n        });\n        return;\n    }\n\n    if (SdkContextClass.instance.roomViewStore.getRoomId() === roomId) {\n        // We were viewing the room that was just left. In order to avoid\n        // accidentally viewing the next room in the list and clearing its\n        // notifications, switch to a neutral ground such as the home page or\n        // space landing page.\n        if (isMetaSpace(SpaceStore.instance.activeSpace)) {\n            dis.dispatch<ViewHomePagePayload>({ action: Action.ViewHomePage });\n        } else if (SpaceStore.instance.activeSpace === roomId) {\n            // View the parent space, if there is one\n            const parent = SpaceStore.instance.getCanonicalParent(roomId);\n            if (parent !== null) {\n                dis.dispatch<ViewRoomPayload>({\n                    action: Action.ViewRoom,\n                    room_id: parent.roomId,\n                    metricsTrigger: undefined, // other\n                });\n            } else {\n                dis.dispatch<ViewHomePagePayload>({ action: Action.ViewHomePage });\n            }\n        } else {\n            dis.dispatch<ViewRoomPayload>({\n                action: Action.ViewRoom,\n                room_id: SpaceStore.instance.activeSpace,\n                metricsTrigger: undefined, // other\n            });\n        }\n    }\n}\n\nexport const leaveSpace = (space: Room): void => {\n    const { finished } = Modal.createDialog(\n        LeaveSpaceDialog,\n        {\n            space,\n        },\n        \"mx_LeaveSpaceDialog_wrapper\",\n    );\n    finished.then(async ([leave, rooms]) => {\n        if (!leave) return;\n        await bulkSpaceBehaviour(space, rooms!, (room) => leaveRoomBehaviour(space.client, room.roomId));\n\n        dis.dispatch<AfterLeaveRoomPayload>({\n            action: Action.AfterLeaveRoom,\n            room_id: space.roomId,\n        });\n    });\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { EventType, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { type LocalRoom } from \"../../models/LocalRoom\";\n\n/**\n * Tests whether a room created based on a local room is ready.\n */\nexport function isRoomReady(client: MatrixClient, localRoom: LocalRoom): boolean {\n    // not ready if no actual room id exists\n    if (!localRoom.actualRoomId) return false;\n\n    const room = client.getRoom(localRoom.actualRoomId);\n    // not ready if the room does not exist\n    if (!room) return false;\n\n    // not ready if not all members joined/invited\n    if (room.getInvitedAndJoinedMemberCount() !== 1 + localRoom.targets?.length) return false;\n\n    const roomHistoryVisibilityEvents = room.currentState.getStateEvents(EventType.RoomHistoryVisibility);\n    // not ready if the room history has not been configured\n    if (roomHistoryVisibilityEvents.length === 0) return false;\n\n    const roomEncryptionEvents = room.currentState.getStateEvents(EventType.RoomEncryption);\n    // not ready if encryption has not been configured (applies only to encrypted rooms)\n    if (localRoom.encrypted === true && roomEncryptionEvents.length === 0) return false;\n\n    return true;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { ClientEvent, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport { type LocalRoom, LocalRoomState } from \"../models/LocalRoom\";\nimport { isLocalRoom } from \"./localRoom/isLocalRoom\";\nimport { isRoomReady } from \"./localRoom/isRoomReady\";\n\nconst isActualRoomIdDefined = (actualRoomId: string | undefined): actualRoomId is string => {\n    if (actualRoomId === undefined) {\n        // should not happen\n        throw new Error(\"Local room in CREATED state without actual room Id occurred\");\n    }\n\n    return true;\n};\n\n/**\n * Does a room action:\n * For non-local rooms it calls fn directly.\n * For local rooms it adds the callback function to the room's afterCreateCallbacks and\n * dispatches a \"local_room_event\".\n *\n * @async\n * @template T\n * @param {string} roomId Room ID of the target room\n * @param {(actualRoomId: string) => Promise<T>} fn Callback to be called directly or collected at the local room\n * @param {MatrixClient} [client]\n * @returns {Promise<T>} Promise that gets resolved after the callback has finished\n */\nexport async function doMaybeLocalRoomAction<T>(\n    roomId: string,\n    fn: (actualRoomId: string) => Promise<T>,\n    client: MatrixClient,\n): Promise<T> {\n    if (isLocalRoom(roomId)) {\n        const room = client.getRoom(roomId) as LocalRoom;\n\n        if (room.isCreated && isActualRoomIdDefined(room.actualRoomId)) {\n            return fn(room.actualRoomId);\n        }\n\n        return new Promise<T>((resolve, reject) => {\n            room.afterCreateCallbacks.push((newRoomId: string) => {\n                fn(newRoomId).then(resolve).catch(reject);\n            });\n            defaultDispatcher.dispatch({\n                action: \"local_room_event\",\n                roomId: room.roomId,\n            });\n        });\n    }\n\n    return fn(roomId);\n}\n\n/**\n * Waits until a room is ready and then applies the after-create local room callbacks.\n * Also implements a stopgap timeout after that a room is assumed to be ready.\n *\n * @see isRoomReady\n * @async\n * @param {MatrixClient} client\n * @param {LocalRoom} localRoom\n * @param actualRoomId Id of the actual room\n * @returns {Promise<string>} Resolved to the actual room id\n */\nexport async function waitForRoomReadyAndApplyAfterCreateCallbacks(\n    client: MatrixClient,\n    localRoom: LocalRoom,\n    actualRoomId: string,\n): Promise<string> {\n    if (isRoomReady(client, localRoom)) {\n        return applyAfterCreateCallbacks(localRoom, actualRoomId).then(() => {\n            localRoom.state = LocalRoomState.CREATED;\n            client.emit(ClientEvent.Room, localRoom);\n            return Promise.resolve(actualRoomId);\n        });\n    }\n\n    return new Promise((resolve, reject) => {\n        const finish = (): void => {\n            if (checkRoomStateIntervalHandle) clearInterval(checkRoomStateIntervalHandle);\n            if (stopgapTimeoutHandle) clearTimeout(stopgapTimeoutHandle);\n\n            applyAfterCreateCallbacks(localRoom, actualRoomId)\n                .then(() => {\n                    localRoom.state = LocalRoomState.CREATED;\n                    client.emit(ClientEvent.Room, localRoom);\n                    resolve(actualRoomId);\n                })\n                .catch((err) => {\n                    reject(err);\n                });\n        };\n\n        const stopgapFinish = (): void => {\n            logger.warn(`Assuming local room ${localRoom.roomId} is ready after hitting timeout`);\n            finish();\n        };\n\n        const checkRoomStateIntervalHandle = window.setInterval(() => {\n            if (isRoomReady(client, localRoom)) finish();\n        }, 500);\n        const stopgapTimeoutHandle = window.setTimeout(stopgapFinish, 5000);\n    });\n}\n\n/**\n * Applies the after-create callback of a local room.\n *\n * @async\n * @param {LocalRoom} localRoom\n * @param {string} roomId\n * @returns {Promise<void>} Resolved after all callbacks have been called\n */\nasync function applyAfterCreateCallbacks(localRoom: LocalRoom, roomId: string): Promise<void> {\n    for (const afterCreateCallback of localRoom.afterCreateCallbacks) {\n        await afterCreateCallback(roomId);\n    }\n\n    localRoom.afterCreateCallbacks = [];\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { LocalRoom, LOCAL_ROOM_ID_PREFIX } from \"../../models/LocalRoom\";\n\nexport function isLocalRoom(roomOrID?: Room | string | null): boolean {\n    if (typeof roomOrID === \"string\") {\n        return roomOrID.startsWith(LOCAL_ROOM_ID_PREFIX);\n    }\n    return roomOrID instanceof LocalRoom;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { _t } from \"../../languageHandler\";\n\nexport enum LocationShareError {\n    MapStyleUrlNotConfigured = \"MapStyleUrlNotConfigured\",\n    MapStyleUrlNotReachable = \"MapStyleUrlNotReachable\",\n    WebGLNotEnabled = \"WebGLNotEnabled\",\n    Default = \"Default\",\n}\n\nexport const getLocationShareErrorMessage = (errorType?: LocationShareError): string => {\n    switch (errorType) {\n        case LocationShareError.MapStyleUrlNotConfigured:\n            return _t(\"location_sharing|MapStyleUrlNotConfigured\");\n        case LocationShareError.WebGLNotEnabled:\n            return _t(\"location_sharing|WebGLNotEnabled\");\n        case LocationShareError.MapStyleUrlNotReachable:\n        default:\n            return _t(\"location_sharing|MapStyleUrlNotReachable\");\n    }\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport SdkConfig from \"../../SdkConfig\";\nimport { getTileServerWellKnown } from \"../WellKnownUtils\";\nimport { LocationShareError } from \"./LocationShareErrors\";\n\n/**\n * Look up what map tile server style URL was provided in the homeserver's\n * .well-known location, or, failing that, in our local config, or, failing\n * that, defaults to the same tile server listed by matrix.org.\n */\nexport function findMapStyleUrl(matrixClient: MatrixClient): string {\n    const mapStyleUrl = getTileServerWellKnown(matrixClient)?.map_style_url ?? SdkConfig.get().map_style_url;\n\n    if (!mapStyleUrl) {\n        logger.error(\"'map_style_url' missing from homeserver .well-known area, and missing from from config.json.\");\n        throw new Error(LocationShareError.MapStyleUrlNotConfigured);\n    }\n\n    return mapStyleUrl;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type ILocationContent, LocationAssetType, M_ASSET } from \"matrix-js-sdk/src/matrix\";\n\nexport const isSelfLocation = (locationContent: ILocationContent): boolean => {\n    const asset = M_ASSET.findIn(locationContent) as { type: string };\n    const assetType = asset?.type ?? LocationAssetType.Self;\n    return assetType == LocationAssetType.Self;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, M_LOCATION, type MLocationEvent } from \"matrix-js-sdk/src/matrix\";\n\ntype LocationEvent = { geo_uri: string } & MLocationEvent;\n\n/**\n * Find the geo-URI contained within a location event.\n */\nexport const locationEventGeoUri = (mxEvent: MatrixEvent): string => {\n    // unfortunately we're stuck supporting legacy `content.geo_uri`\n    // events until the end of days, or until we figure out mutable\n    // events - so folks can read their old chat history correctly.\n    // https://github.com/matrix-org/matrix-doc/issues/3516\n    const content = mxEvent.getContent<LocationEvent>();\n    const loc = M_LOCATION.findIn(content);\n    return loc?.uri ?? content[\"geo_uri\"];\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport const parseGeoUri = (uri: string): GeolocationCoordinates | undefined => {\n    function parse(s: string): number | null {\n        const ret = parseFloat(s);\n        if (Number.isNaN(ret)) {\n            return null;\n        } else {\n            return ret;\n        }\n    }\n\n    const m = uri.match(/^\\s*geo:(.*?)\\s*$/);\n    if (!m) return;\n    const parts = m[1].split(\";\");\n    const coords = parts[0].split(\",\");\n    let uncertainty: number | null | undefined = undefined;\n    for (const param of parts.slice(1)) {\n        const m = param.match(/u=(.*)/);\n        if (m) uncertainty = parse(m[1]);\n    }\n    const latitude = parse(coords[0]);\n    const longitude = parse(coords[1]);\n\n    if (latitude === null || longitude === null) {\n        return;\n    }\n\n    const geoCoords = {\n        latitude: latitude!,\n        longitude: longitude!,\n        altitude: parse(coords[2]),\n        accuracy: uncertainty!,\n        altitudeAccuracy: null,\n        heading: null,\n        speed: null,\n    };\n\n    return {\n        toJSON: () => geoCoords,\n        ...geoCoords,\n    };\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, M_LOCATION } from \"matrix-js-sdk/src/matrix\";\n\nimport { parseGeoUri } from \"./parseGeoUri\";\n\nexport const makeMapSiteLink = (coords: GeolocationCoordinates): string => {\n    return (\n        \"https://www.openstreetmap.org/\" +\n        `?mlat=${coords.latitude}` +\n        `&mlon=${coords.longitude}` +\n        `#map=16/${coords.latitude}/${coords.longitude}`\n    );\n};\n\nexport const createMapSiteLinkFromEvent = (event: MatrixEvent): string | null => {\n    const content = event.getContent();\n    const mLocation = content[M_LOCATION.name];\n    if (mLocation !== undefined) {\n        const uri = mLocation[\"uri\"];\n        if (uri !== undefined) {\n            const geoCoords = parseGeoUri(uri);\n            return geoCoords ? makeMapSiteLink(geoCoords) : null;\n        }\n    } else {\n        const geoUri = content[\"geo_uri\"];\n        if (geoUri) {\n            const geoCoords = parseGeoUri(geoUri);\n            return geoCoords ? makeMapSiteLink(geoCoords) : null;\n        }\n    }\n    return null;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { _t } from \"../../languageHandler\";\nimport SdkConfig from \"../../SdkConfig\";\n\n/**\n * Get a localised error message for GeolocationPositionError error codes\n * @param code - error code from GeolocationPositionError\n * @returns\n */\nexport const positionFailureMessage = (code: number): string | undefined => {\n    const brand = SdkConfig.get().brand;\n    switch (code) {\n        case 1:\n            return _t(\"location_sharing|failed_permission\", { brand });\n        case 2:\n            return _t(\"location_sharing|failed_generic\");\n        case 3:\n            return _t(\"location_sharing|failed_timeout\");\n        case 4:\n            return _t(\"location_sharing|failed_unknown\");\n    }\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { arrayDiff, arrayIntersection } from \"./arrays\";\n\n/**\n * Determines the keys added, changed, and removed between two Maps.\n * For changes, simple triple equal comparisons are done, not in-depth tree checking.\n * @param a The first Map. Must be defined.\n * @param b The second Map. Must be defined.\n * @returns The difference between the keys of each Map.\n */\nexport function mapDiff<K, V>(a: Map<K, V>, b: Map<K, V>): { changed: K[]; added: K[]; removed: K[] } {\n    const aKeys = [...a.keys()];\n    const bKeys = [...b.keys()];\n    const keyDiff = arrayDiff(aKeys, bKeys);\n    const possibleChanges = arrayIntersection(aKeys, bKeys);\n    const changes = possibleChanges.filter((k) => a.get(k) !== b.get(k));\n\n    return { changed: changes, added: keyDiff.added, removed: keyDiff.removed };\n}\n\n/**\n * A Map<K, V> with added utility.\n */\nexport class EnhancedMap<K, V> extends Map<K, V> {\n    public constructor(entries?: Iterable<[K, V]>) {\n        super(entries);\n    }\n\n    public getOrCreate(key: K, def: V): V {\n        if (this.has(key)) {\n            return this.get(key)!;\n        }\n        this.set(key, def);\n        return def;\n    }\n\n    public remove(key: K): V | undefined {\n        const v = this.get(key);\n        this.delete(key);\n        return v;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020-2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type Room,\n    type RoomMember,\n    type RoomState,\n    RoomStateEvent,\n    type MatrixEvent,\n    type MatrixClient,\n} from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership, type Membership } from \"matrix-js-sdk/src/types\";\n\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\nimport SettingsStore from \"../settings/SettingsStore\";\n\n/**\n * Approximation of a membership status for a given room.\n */\nexport enum EffectiveMembership {\n    /**\n     * The user is effectively joined to the room. For example, actually joined\n     * or knocking on the room (when that becomes possible).\n     */\n    Join = \"JOIN\",\n\n    /**\n     * The user is effectively invited to the room. Currently this is a direct map\n     * to the invite membership as no other membership states are effectively\n     * invites.\n     */\n    Invite = \"INVITE\",\n\n    /**\n     * The user is effectively no longer in the room. For example, kicked,\n     * banned, or voluntarily left.\n     */\n    Leave = \"LEAVE\",\n}\n\nexport type MembershipSplit = {\n    [state in EffectiveMembership]: Room[];\n};\n\nexport function splitRoomsByMembership(rooms: Room[]): MembershipSplit {\n    const split: MembershipSplit = {\n        [EffectiveMembership.Invite]: [],\n        [EffectiveMembership.Join]: [],\n        [EffectiveMembership.Leave]: [],\n    };\n\n    for (const room of rooms) {\n        const membership = room.getMyMembership();\n        // Filter out falsey relationship as this will be peeked rooms\n        if (!!membership) {\n            split[getEffectiveMembershipTag(room)].push(room);\n        }\n    }\n\n    return split;\n}\n\nexport function getEffectiveMembership(membership: Membership): EffectiveMembership {\n    if (membership === KnownMembership.Invite) {\n        return EffectiveMembership.Invite;\n    } else if (\n        membership === KnownMembership.Join ||\n        (SettingsStore.getValue(\"feature_ask_to_join\") && membership === KnownMembership.Knock)\n    ) {\n        return EffectiveMembership.Join;\n    } else {\n        // Probably a leave, kick, or ban\n        return EffectiveMembership.Leave;\n    }\n}\n\nexport function isKnockDenied(room: Room): boolean | undefined {\n    const memberId = MatrixClientPeg.get()?.getSafeUserId();\n    const member = memberId ? room.getMember(memberId) : null;\n    const previousMembership = member?.events.member?.getPrevContent().membership;\n\n    return member?.isKicked() && previousMembership === KnownMembership.Knock;\n}\n\nexport function getEffectiveMembershipTag(room: Room, membership?: string): EffectiveMembership {\n    return isKnockDenied(room)\n        ? EffectiveMembership.Join\n        : getEffectiveMembership(membership ?? room.getMyMembership());\n}\n\nexport function isJoinedOrNearlyJoined(membership: Membership): boolean {\n    const effective = getEffectiveMembership(membership);\n    return effective === EffectiveMembership.Join || effective === EffectiveMembership.Invite;\n}\n\n/**\n * Try to ensure the user is in the room (invited or joined) before continuing\n */\nexport async function waitForMember(\n    client: MatrixClient,\n    roomId: string,\n    userId: string,\n    opts = { timeout: 1500 },\n): Promise<boolean> {\n    const { timeout } = opts;\n    let handler: (event: MatrixEvent, state: RoomState, member: RoomMember) => void;\n\n    // check if the user is in the room before we start -- in which case, no need to wait.\n    if ((client.getRoom(roomId)?.getMember(userId) ?? null) !== null) {\n        return true;\n    }\n\n    return new Promise<boolean>((resolve) => {\n        // eslint-disable-next-line @typescript-eslint/naming-convention\n        handler = function (_, __, member: RoomMember) {\n            if (member.userId !== userId) return;\n            if (member.roomId !== roomId) return;\n            resolve(true);\n        };\n        client.on(RoomStateEvent.NewMember, handler);\n\n        /* We don't want to hang if this goes wrong, so we proceed and hope the other\n           user is already in the room */\n        window.setTimeout(resolve, timeout, false);\n    }).finally(() => {\n        client.removeListener(RoomStateEvent.NewMember, handler);\n    });\n}\n\n/**\n * Check if the user is the only joined admin in the room\n * This function will *not* cause lazy loading of room members, so if these should be included then\n * the caller needs to make sure members have been loaded.\n * @param room The room to check if the user is the only admin.\n * @returns True if the user is the only user with the highest power level, false otherwise\n */\nexport function isOnlyAdmin(room: Room): boolean {\n    const currentUserLevel = room.getMember(room.client.getSafeUserId())?.powerLevel;\n\n    const userLevelValues = room.getJoinedMembers().map((m) => m.powerLevel);\n\n    const maxUserLevel = Math.max(...userLevelValues.filter((x) => typeof x === \"number\"));\n    // If the user is the only user with highest power level\n    return (\n        maxUserLevel === currentUserLevel &&\n        userLevelValues.lastIndexOf(maxUserLevel) == userLevelValues.indexOf(maxUserLevel)\n    );\n}\n","/*\nCopyright 2025 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, type IContent, type IMentions, type IEventRelation } from \"matrix-js-sdk/src/matrix\";\n\nimport type EditorModel from \"../editor/model\";\nimport { Type } from \"../editor/parts\";\n\n/**\n * Build the mentions information based on the editor model (and any related events):\n *\n * 1. Search the model parts for room or user pills and fill in the mentions object.\n * 2. If this is a reply to another event, include any user mentions from that\n *    (but do not include a room mention).\n *\n * @param sender - The Matrix ID of the user sending the event.\n * @param content - The event content.\n * @param model - The editor model to search for mentions, null if there is no editor.\n * @param replyToEvent - The event being replied to or undefined if it is not a reply.\n * @param editedContent - The content of the parent event being edited.\n */\nexport function attachMentions(\n    sender: string,\n    content: IContent,\n    model: EditorModel | null,\n    replyToEvent: MatrixEvent | undefined,\n    editedContent: IContent | null = null,\n): void {\n    // We always attach the mentions even if the home server doesn't yet support\n    // intentional mentions. This is safe because m.mentions is an additive change\n    // that should simply be ignored by incapable home servers.\n\n    // The mentions property *always* gets included to disable legacy push rules.\n    const mentions: IMentions = (content[\"m.mentions\"] = {});\n\n    const userMentions = new Set<string>();\n    let roomMention = false;\n\n    // If there's a reply, initialize the mentioned users as the sender of that event.\n    if (replyToEvent) {\n        userMentions.add(replyToEvent.sender!.userId);\n    }\n\n    // If user provided content is available, check to see if any users are mentioned.\n    if (model) {\n        // Add any mentioned users in the current content.\n        for (const part of model.parts) {\n            if (part.type === Type.UserPill) {\n                userMentions.add(part.resourceId);\n            } else if (part.type === Type.AtRoomPill) {\n                roomMention = true;\n            }\n        }\n    }\n\n    // Ensure the *current* user isn't listed in the mentioned users.\n    userMentions.delete(sender);\n\n    // Finally, if this event is editing a previous event, only include users who\n    // were not previously mentioned and a room mention if the previous event was\n    // not a room mention.\n    if (editedContent) {\n        // First, the new event content gets the *full* set of users.\n        const newContent = content[\"m.new_content\"];\n        const newMentions: IMentions = (newContent[\"m.mentions\"] = {});\n\n        // Only include the users/room if there is any content.\n        if (userMentions.size) {\n            newMentions.user_ids = [...userMentions];\n        }\n        if (roomMention) {\n            newMentions.room = true;\n        }\n\n        // Fetch the mentions from the original event and remove any previously\n        // mentioned users.\n        const prevMentions = editedContent[\"m.mentions\"];\n        if (Array.isArray(prevMentions?.user_ids)) {\n            prevMentions!.user_ids.forEach((userId) => userMentions.delete(userId));\n        }\n\n        // If the original event mentioned the room, nothing to do here.\n        if (prevMentions?.room) {\n            roomMention = false;\n        }\n    }\n\n    // Only include the users/room if there is any content.\n    if (userMentions.size) {\n        mentions.user_ids = [...userMentions];\n    }\n    if (roomMention) {\n        mentions.room = true;\n    }\n}\n\n// Merges favouring the given relation\nexport function attachRelation(content: IContent, relation?: IEventRelation): void {\n    if (relation) {\n        content[\"m.relates_to\"] = {\n            ...(content[\"m.relates_to\"] || {}),\n            ...relation,\n        };\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type MatrixClient,\n    LOCAL_NOTIFICATION_SETTINGS_PREFIX,\n    NotificationCountType,\n    type Room,\n    type LocalNotificationSettings,\n    ReceiptType,\n    type IMarkedUnreadEvent,\n    type EmptyObject,\n    EventType,\n} from \"matrix-js-sdk/src/matrix\";\nimport { type IndicatorIcon } from \"@vector-im/compound-web\";\n\nimport SettingsStore from \"../settings/SettingsStore\";\nimport { NotificationLevel } from \"../stores/notifications/NotificationLevel\";\nimport { doesRoomHaveUnreadMessages } from \"../Unread\";\nimport { type SettingKey } from \"../settings/Settings.tsx\";\n\n// MSC2867 is not yet spec at time of writing. We read from both stable\n// and unstable prefixes and accept the risk that the format may change,\n// since the stable prefix is not actually defined yet.\n\n/**\n * Unstable identifier for the marked_unread event, per MSC2867\n */\nexport const MARKED_UNREAD_TYPE_UNSTABLE = \"com.famedly.marked_unread\";\n/**\n * Stable identifier for the marked_unread event\n */\nexport const MARKED_UNREAD_TYPE_STABLE = EventType.MarkedUnread;\n\ndeclare module \"matrix-js-sdk/src/types\" {\n    interface RoomAccountDataEvents {\n        [MARKED_UNREAD_TYPE_UNSTABLE]: { [eventId: string]: boolean };\n    }\n}\n\nexport const deviceNotificationSettingsKeys: SettingKey[] = [\n    \"notificationsEnabled\",\n    \"notificationBodyEnabled\",\n    \"audioNotificationsEnabled\",\n];\n\nexport function getLocalNotificationAccountDataEventType(\n    deviceId: string | null,\n): `${typeof LOCAL_NOTIFICATION_SETTINGS_PREFIX.name}.${string}` {\n    return `${LOCAL_NOTIFICATION_SETTINGS_PREFIX.name}.${deviceId}`;\n}\n\nexport async function createLocalNotificationSettingsIfNeeded(cli: MatrixClient): Promise<void> {\n    if (cli.isGuest()) {\n        return;\n    }\n    const eventType = getLocalNotificationAccountDataEventType(cli.deviceId!);\n    const event = cli.getAccountData(eventType);\n    // New sessions will create an account data event to signify they support\n    // remote toggling of push notifications on this device. Default `is_silenced=true`\n    // For backwards compat purposes, older sessions will need to check settings value\n    // to determine what the state of `is_silenced`\n    if (!event) {\n        // If any of the above is true, we fall in the \"backwards compat\" case,\n        // and `is_silenced` will be set to `false`\n        const isSilenced = !deviceNotificationSettingsKeys.some((key) => SettingsStore.getValue(key));\n\n        await cli.setAccountData(eventType, {\n            is_silenced: isSilenced,\n        });\n    }\n}\n\nexport function localNotificationsAreSilenced(cli: MatrixClient): boolean {\n    const eventType = getLocalNotificationAccountDataEventType(cli.deviceId!);\n    const event = cli.getAccountData(eventType);\n    return event?.getContent<LocalNotificationSettings>()?.is_silenced ?? false;\n}\n\n/**\n * Mark a room as read\n * @param room\n * @param client\n * @returns a promise that resolves when the room has been marked as read\n */\nexport async function clearRoomNotification(room: Room, client: MatrixClient): Promise<EmptyObject | undefined> {\n    const lastEvent = room.getLastLiveEvent();\n\n    await setMarkedUnreadState(room, client, false);\n\n    try {\n        if (lastEvent) {\n            const receiptType = SettingsStore.getValue(\"sendReadReceipts\", room.roomId)\n                ? ReceiptType.Read\n                : ReceiptType.ReadPrivate;\n            return await client.sendReadReceipt(lastEvent, receiptType, true);\n        } else {\n            return {};\n        }\n    } finally {\n        // We've had a lot of stuck unread notifications that in e2ee rooms\n        // They occur on event decryption when clients try to replicate the logic\n        //\n        // This resets the notification on a room, even though no read receipt\n        // has been sent, particularly useful when the clients has incorrectly\n        // notified a user.\n        room.setUnreadNotificationCount(NotificationCountType.Highlight, 0);\n        room.setUnreadNotificationCount(NotificationCountType.Total, 0);\n        for (const thread of room.getThreads()) {\n            room.setThreadUnreadNotificationCount(thread.id, NotificationCountType.Highlight, 0);\n            room.setThreadUnreadNotificationCount(thread.id, NotificationCountType.Total, 0);\n        }\n    }\n}\n\n/**\n * Marks all rooms with an unread counter as read\n * @param client The matrix client\n * @returns a promise that resolves when all rooms have been marked as read\n */\nexport function clearAllNotifications(client: MatrixClient): Promise<Array<EmptyObject | undefined>> {\n    const receiptPromises = client\n        .getRooms()\n        .reduce((promises: Array<Promise<EmptyObject | undefined>>, room: Room) => {\n            if (doesRoomHaveUnreadMessages(room, true)) {\n                const promise = clearRoomNotification(room, client);\n                promises.push(promise);\n            }\n\n            return promises;\n        }, []);\n\n    return Promise.all(receiptPromises);\n}\n\n/**\n * Gives the marked_unread state of the given room\n * @param room The room to check\n * @returns - The marked_unread state of the room, or undefined if no explicit state is set.\n */\nexport function getMarkedUnreadState(room: Room): boolean | undefined {\n    const currentStateStable = room.getAccountData(MARKED_UNREAD_TYPE_STABLE)?.getContent<IMarkedUnreadEvent>()?.unread;\n    const currentStateUnstable = room\n        .getAccountData(MARKED_UNREAD_TYPE_UNSTABLE)\n        ?.getContent<IMarkedUnreadEvent>()?.unread;\n    return currentStateStable ?? currentStateUnstable;\n}\n\n/**\n * Sets the marked_unread state of the given room. This sets some room account data that indicates to\n * clients that the user considers this room to be 'unread', but without any actual notifications.\n *\n * @param room The room to set\n * @param client MatrixClient object to use\n * @param unread The new marked_unread state of the room\n */\nexport async function setMarkedUnreadState(room: Room, client: MatrixClient, unread: boolean): Promise<void> {\n    // if there's no event, treat this as false as we don't need to send the flag to clear it if the event isn't there\n    const currentState = getMarkedUnreadState(room);\n\n    if (Boolean(currentState) !== unread) {\n        await client.setRoomAccountData(room.roomId, EventType.MarkedUnread, { unread });\n    }\n}\n\n/**\n * A helper to transform a notification color to the what the Compound Icon Button\n * expects\n */\nexport function notificationLevelToIndicator(\n    level: NotificationLevel,\n): React.ComponentPropsWithRef<typeof IndicatorIcon>[\"indicator\"] {\n    if (level <= NotificationLevel.None) {\n        return undefined;\n    } else if (level <= NotificationLevel.Activity) {\n        return \"default\";\n    } else if (level <= NotificationLevel.Notification) {\n        return \"success\";\n    } else {\n        return \"critical\";\n    }\n}\n\n/**\n * Return the thread notification level for a room\n * @param room\n * @returns {NotificationLevel}\n */\nexport function getThreadNotificationLevel(room: Room): NotificationLevel {\n    const notificationCountType = room.threadsAggregateNotificationType;\n    switch (notificationCountType) {\n        case NotificationCountType.Highlight:\n            return NotificationLevel.Highlight;\n        case NotificationCountType.Total:\n            return NotificationLevel.Notification;\n        default:\n            return NotificationLevel.Activity;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020, 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { arrayDiff, arrayUnion, arrayIntersection } from \"./arrays\";\n\ntype ObjectExcluding<O extends object, P extends (keyof O)[]> = { [k in Exclude<keyof O, P[number]>]: O[k] };\n\n/**\n * Gets a new object which represents the provided object, excluding some properties.\n * @param a The object to strip properties of. Must be defined.\n * @param props The property names to remove.\n * @returns The new object without the provided properties.\n */\nexport function objectExcluding<O extends object, P extends Array<keyof O>>(a: O, props: P): ObjectExcluding<O, P> {\n    // We use a Map to avoid hammering the `delete` keyword, which is slow and painful.\n    const tempMap = new Map<keyof O, any>(Object.entries(a) as [keyof O, any][]);\n    for (const prop of props) {\n        tempMap.delete(prop);\n    }\n\n    // Convert the map to an object again\n    return Array.from(tempMap.entries()).reduce((c, [k, v]) => {\n        c[k] = v;\n        return c;\n    }, {} as O);\n}\n\n/**\n * Gets a new object which represents the provided object, with only some properties\n * included.\n * @param a The object to clone properties of. Must be defined.\n * @param props The property names to keep.\n * @returns The new object with only the provided properties.\n */\nexport function objectWithOnly<O extends object, P extends Array<keyof O>>(a: O, props: P): { [k in P[number]]: O[k] } {\n    const existingProps = Object.keys(a) as (keyof O)[];\n    const diff = arrayDiff(existingProps, props);\n    if (diff.removed.length === 0) {\n        return objectShallowClone(a);\n    } else {\n        return objectExcluding(a, diff.removed) as { [k in P[number]]: O[k] };\n    }\n}\n\n/**\n * Clones an object to a caller-controlled depth. When a propertyCloner is supplied, the\n * object's properties will be passed through it with the return value used as the new\n * object's type. This is intended to be used to deep clone a reference, but without\n * having to deep clone the entire object. This function is safe to call recursively within\n * the propertyCloner.\n * @param a The object to clone. Must be defined.\n * @param propertyCloner The function to clone the properties of the object with, optionally.\n * First argument is the property key with the second being the current value.\n * @returns A cloned object.\n */\nexport function objectShallowClone<O extends object>(a: O, propertyCloner?: (k: keyof O, v: O[keyof O]) => any): O {\n    const newObj = {} as O;\n    for (const [k, v] of Object.entries(a) as [keyof O, O[keyof O]][]) {\n        newObj[k] = v;\n        if (propertyCloner) {\n            newObj[k] = propertyCloner(k, v);\n        }\n    }\n    return newObj;\n}\n\n/**\n * Determines if any keys were added, removed, or changed between two objects.\n * For changes, simple triple equal comparisons are done, not in-depth\n * tree checking.\n * @param a The first object. Must be defined.\n * @param b The second object. Must be defined.\n * @returns True if there's a difference between the objects, false otherwise\n */\nexport function objectHasDiff<O extends object>(a: O, b: O): boolean {\n    if (a === b) return false;\n    const aKeys = Object.keys(a);\n    const bKeys = Object.keys(b);\n    if (aKeys.length !== bKeys.length) return true;\n    const possibleChanges = arrayIntersection(aKeys, bKeys) as Array<keyof O>;\n    // if the amalgamation of both sets of keys has the a different length to the inputs then there must be a change\n    if (possibleChanges.length !== aKeys.length) return true;\n\n    return possibleChanges.some((k) => a[k] !== b[k]);\n}\n\ntype Diff<K> = { changed: K[]; added: K[]; removed: K[] };\n\n/**\n * Determines the keys added, changed, and removed between two objects.\n * For changes, simple triple equal comparisons are done, not in-depth\n * tree checking.\n * @param a The first object. Must be defined.\n * @param b The second object. Must be defined.\n * @returns The difference between the keys of each object.\n */\nexport function objectDiff<O extends object>(a: O, b: O): Diff<keyof O> {\n    const aKeys = Object.keys(a) as (keyof O)[];\n    const bKeys = Object.keys(b) as (keyof O)[];\n    const keyDiff = arrayDiff(aKeys, bKeys);\n    const possibleChanges = arrayIntersection(aKeys, bKeys);\n    const changes = possibleChanges.filter((k) => a[k] !== b[k]);\n\n    return { changed: changes, added: keyDiff.added, removed: keyDiff.removed };\n}\n\n/**\n * Gets all the key changes (added, removed, or value difference) between\n * two objects. Triple equals is used to compare values, not in-depth tree\n * checking.\n * @param a The first object. Must be defined.\n * @param b The second object. Must be defined.\n * @returns The keys which have been added, removed, or changed between the\n * two objects.\n */\nexport function objectKeyChanges<O extends object>(a: O, b: O): (keyof O)[] {\n    const diff = objectDiff(a, b);\n    return arrayUnion(diff.removed, diff.added, diff.changed);\n}\n\n/**\n * Clones an object by running it through JSON parsing. Note that this\n * will destroy any complicated object types which do not translate to\n * JSON.\n * @param obj The object to clone.\n * @returns The cloned object\n */\nexport function objectClone<O extends object>(obj: O): O {\n    return JSON.parse(JSON.stringify(obj));\n}\n\n/**\n * Simple object check.\n * @param item\n * @returns {boolean}\n */\nexport function isObject(item: any): item is object {\n    return item && typeof item === \"object\" && !Array.isArray(item);\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type IdTokenClaims } from \"oidc-client-ts\";\nimport { decodeIdToken } from \"matrix-js-sdk/src/matrix\";\n\nconst clientIdStorageKey = \"mx_oidc_client_id\";\nconst tokenIssuerStorageKey = \"mx_oidc_token_issuer\";\nconst idTokenStorageKey = \"mx_oidc_id_token\";\n/**\n * @deprecated in favour of using idTokenStorageKey\n */\nconst idTokenClaimsStorageKey = \"mx_oidc_id_token_claims\";\n\n/**\n * Persists oidc clientId and issuer in local storage\n * Only set after successful authentication\n * @param clientId\n * @param issuer\n * @param idToken\n * @param idTokenClaims\n */\nexport const persistOidcAuthenticatedSettings = (clientId: string, issuer: string, idToken: string): void => {\n    localStorage.setItem(clientIdStorageKey, clientId);\n    localStorage.setItem(tokenIssuerStorageKey, issuer);\n    localStorage.setItem(idTokenStorageKey, idToken);\n};\n\n/**\n * Retrieve stored oidc issuer from local storage\n * When user has token from OIDC issuer, this will be set\n * @returns issuer or undefined\n */\nexport const getStoredOidcTokenIssuer = (): string | undefined => {\n    return localStorage.getItem(tokenIssuerStorageKey) ?? undefined;\n};\n\n/**\n * Retrieves stored oidc client id from local storage\n * @returns clientId\n * @throws when clientId is not found in local storage\n */\nexport const getStoredOidcClientId = (): string => {\n    const clientId = localStorage.getItem(clientIdStorageKey);\n    if (!clientId) {\n        throw new Error(\"Oidc client id not found in storage\");\n    }\n    return clientId;\n};\n\n/**\n * Retrieve stored id token claims from stored id token or local storage\n * @returns idTokenClaims or undefined\n */\nexport const getStoredOidcIdTokenClaims = (): IdTokenClaims | undefined => {\n    const idToken = getStoredOidcIdToken();\n    if (idToken) {\n        return decodeIdToken(idToken);\n    }\n\n    const idTokenClaims = localStorage.getItem(idTokenClaimsStorageKey);\n    if (!idTokenClaims) {\n        return;\n    }\n    return JSON.parse(idTokenClaims) as IdTokenClaims;\n};\n\n/**\n * Retrieve stored id token from local storage\n * @returns idToken or undefined\n */\nexport const getStoredOidcIdToken = (): string | undefined => {\n    return localStorage.getItem(idTokenStorageKey) ?? undefined;\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport PermalinkConstructor, { PermalinkParts } from \"./PermalinkConstructor\";\n\nexport const host = \"matrix.to\";\nexport const baseUrl = `https://${host}`;\nexport const baseUrlPattern = `^(?:https?://)?${host.replace(\".\", \"\\\\.\")}/#/(.*)`;\n\n/**\n * Generates matrix.to permalinks\n */\nexport default class MatrixToPermalinkConstructor extends PermalinkConstructor {\n    public constructor() {\n        super();\n    }\n\n    public forEvent(roomId: string, eventId: string, serverCandidates: string[]): string {\n        return `${baseUrl}/#/${roomId}/${eventId}${this.encodeServerCandidates(serverCandidates)}`;\n    }\n\n    public forRoom(roomIdOrAlias: string, serverCandidates: string[]): string {\n        return `${baseUrl}/#/${roomIdOrAlias}${this.encodeServerCandidates(serverCandidates)}`;\n    }\n\n    public forUser(userId: string): string {\n        return `${baseUrl}/#/${userId}`;\n    }\n\n    public forEntity(entityId: string): string {\n        return `${baseUrl}/#/${entityId}`;\n    }\n\n    public isPermalinkHost(testHost: string): boolean {\n        return testHost === host;\n    }\n\n    public encodeServerCandidates(candidates: string[]): string {\n        if (!candidates || candidates.length === 0) return \"\";\n        return `?via=${candidates.map((c) => encodeURIComponent(c)).join(\"&via=\")}`;\n    }\n\n    // Heavily inspired by/borrowed from the matrix-bot-sdk (with permission):\n    // https://github.com/turt2live/matrix-js-bot-sdk/blob/7c4665c9a25c2c8e0fe4e509f2616505b5b66a1c/src/Permalinks.ts#L33-L61\n    public parsePermalink(fullUrl: string): PermalinkParts {\n        if (!fullUrl) {\n            throw new Error(\"Does not appear to be a permalink\");\n        }\n\n        const matches = [...fullUrl.matchAll(new RegExp(baseUrlPattern, \"gi\"))][0];\n\n        if (!matches || matches.length < 2) {\n            throw new Error(\"Does not appear to be a permalink\");\n        }\n\n        const parts = matches[1].split(\"/\");\n\n        const entity = parts[0];\n        if (entity[0] === \"@\") {\n            // Probably a user, no further parsing needed.\n            return PermalinkParts.forUser(matches[1]);\n        } else if (entity[0] === \"#\" || entity[0] === \"!\") {\n            if (parts.length === 1) {\n                // room without event permalink\n                const [roomId, query = \"\"] = entity.split(\"?\");\n                const via = query.split(/&?via=/g).filter((p) => !!p);\n                return PermalinkParts.forRoom(roomId, via);\n            }\n\n            // rejoin the rest because v3 events can have slashes (annoyingly)\n            const eventIdAndQuery = parts.length > 1 ? parts.slice(1).join(\"/\") : \"\";\n            const [eventId, query = \"\"] = eventIdAndQuery.split(\"?\");\n            const via = query.split(/&?via=/g).filter((p) => !!p);\n\n            return PermalinkParts.forEvent(entity, eventId, via);\n        } else {\n            throw new Error(\"Unknown entity type in permalink\");\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/**\n * Interface for classes that actually produce permalinks (strings).\n * TODO: Convert this to a real TypeScript interface\n */\nexport default class PermalinkConstructor {\n    public forEvent(roomId: string, eventId: string, serverCandidates: string[] = []): string {\n        throw new Error(\"Not implemented\");\n    }\n\n    public forRoom(roomIdOrAlias: string, serverCandidates: string[] = []): string {\n        throw new Error(\"Not implemented\");\n    }\n\n    public forUser(userId: string): string {\n        throw new Error(\"Not implemented\");\n    }\n\n    public forEntity(entityId: string): string {\n        throw new Error(\"Not implemented\");\n    }\n\n    public isPermalinkHost(host: string): boolean {\n        throw new Error(\"Not implemented\");\n    }\n\n    public parsePermalink(fullUrl: string): PermalinkParts {\n        throw new Error(\"Not implemented\");\n    }\n}\n\n// Inspired by/Borrowed with permission from the matrix-bot-sdk:\n// https://github.com/turt2live/matrix-js-bot-sdk/blob/7c4665c9a25c2c8e0fe4e509f2616505b5b66a1c/src/Permalinks.ts#L1-L6\nexport class PermalinkParts {\n    public constructor(\n        public readonly roomIdOrAlias: string | null,\n        public readonly eventId: string | null,\n        public readonly userId: string | null,\n        public readonly viaServers: string[] | null,\n    ) {}\n\n    public static forUser(userId: string): PermalinkParts {\n        return new PermalinkParts(null, null, userId, null);\n    }\n\n    public static forRoom(roomIdOrAlias: string, viaServers: string[] = []): PermalinkParts {\n        return new PermalinkParts(roomIdOrAlias, null, null, viaServers);\n    }\n\n    public static forEvent(roomId: string, eventId: string, viaServers: string[] = []): PermalinkParts {\n        return new PermalinkParts(roomId, eventId, null, viaServers);\n    }\n\n    public get primaryEntityId(): string | null {\n        return this.roomIdOrAlias || this.userId;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport PermalinkConstructor, { PermalinkParts } from \"./PermalinkConstructor\";\n\n/**\n * Generates permalinks that self-reference the running webapp\n */\nexport default class ElementPermalinkConstructor extends PermalinkConstructor {\n    private elementUrl: string;\n\n    public constructor(elementUrl: string) {\n        super();\n        this.elementUrl = elementUrl;\n\n        if (!this.elementUrl.startsWith(\"http:\") && !this.elementUrl.startsWith(\"https:\")) {\n            throw new Error(\"Element prefix URL does not appear to be an HTTP(S) URL\");\n        }\n    }\n\n    public forEvent(roomId: string, eventId: string, serverCandidates: string[]): string {\n        return `${this.elementUrl}/#/room/${roomId}/${eventId}${this.encodeServerCandidates(serverCandidates)}`;\n    }\n\n    public forRoom(roomIdOrAlias: string, serverCandidates?: string[]): string {\n        return `${this.elementUrl}/#/room/${roomIdOrAlias}${this.encodeServerCandidates(serverCandidates)}`;\n    }\n\n    public forUser(userId: string): string {\n        return `${this.elementUrl}/#/user/${userId}`;\n    }\n\n    public forEntity(entityId: string): string {\n        if (entityId[0] === \"!\" || entityId[0] === \"#\") {\n            return this.forRoom(entityId);\n        } else if (entityId[0] === \"@\") {\n            return this.forUser(entityId);\n        } else throw new Error(\"Unrecognized entity\");\n    }\n\n    public isPermalinkHost(testHost: string): boolean {\n        const parsedUrl = new URL(this.elementUrl);\n        return testHost === (parsedUrl.host || parsedUrl.hostname); // one of the hosts should match\n    }\n\n    public encodeServerCandidates(candidates?: string[]): string {\n        if (!candidates || candidates.length === 0) return \"\";\n        return `?via=${candidates.map((c) => encodeURIComponent(c)).join(\"&via=\")}`;\n    }\n\n    // Heavily inspired by/borrowed from the matrix-bot-sdk (with permission):\n    // https://github.com/turt2live/matrix-js-bot-sdk/blob/7c4665c9a25c2c8e0fe4e509f2616505b5b66a1c/src/Permalinks.ts#L33-L61\n    // Adapted for Element's URL format\n    public parsePermalink(fullUrl: string): PermalinkParts {\n        if (!fullUrl || !fullUrl.startsWith(this.elementUrl)) {\n            throw new Error(\"Does not appear to be a permalink\");\n        }\n\n        const parts = fullUrl.substring(`${this.elementUrl}/#/`.length);\n        return ElementPermalinkConstructor.parseAppRoute(parts);\n    }\n\n    /**\n     * Parses an app route (`(user|room)/identifier`) to a Matrix entity\n     * (room, user).\n     * @param {string} route The app route\n     * @returns {PermalinkParts}\n     */\n    public static parseAppRoute(route: string): PermalinkParts {\n        const parts = route.split(\"/\");\n\n        if (parts.length < 2) {\n            // we're expecting an entity and an ID of some kind at least\n            throw new Error(\"URL is missing parts\");\n        }\n\n        // Split optional query out of last part\n        const [lastPartMaybeWithQuery] = parts.splice(-1, 1);\n        const [lastPart, query = \"\"] = lastPartMaybeWithQuery.split(\"?\");\n        parts.push(lastPart);\n\n        const entityType = parts[0];\n        const entity = parts[1];\n        if (entityType === \"user\") {\n            // Probably a user, no further parsing needed.\n            return PermalinkParts.forUser(entity);\n        } else if (entityType === \"room\") {\n            // Rejoin the rest because v3 events can have slashes (annoyingly)\n            const eventId = parts.length > 2 ? parts.slice(2).join(\"/\") : \"\";\n            const via = query.split(/&?via=/).filter((p) => !!p);\n            return PermalinkParts.forEvent(entity, eventId, via);\n        } else {\n            throw new Error(\"Unknown entity type in permalink\");\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport PermalinkConstructor, { PermalinkParts } from \"./PermalinkConstructor\";\n\n/**\n * Generates matrix: scheme permalinks\n */\nexport default class MatrixSchemePermalinkConstructor extends PermalinkConstructor {\n    public constructor() {\n        super();\n    }\n\n    private encodeEntity(entity: string): string {\n        if (entity[0] === \"!\") {\n            return `roomid/${entity.slice(1)}`;\n        } else if (entity[0] === \"#\") {\n            return `r/${entity.slice(1)}`;\n        } else if (entity[0] === \"@\") {\n            return `u/${entity.slice(1)}`;\n        } else if (entity[0] === \"$\") {\n            return `e/${entity.slice(1)}`;\n        }\n\n        throw new Error(\"Cannot encode entity: \" + entity);\n    }\n\n    public forEvent(roomId: string, eventId: string, serverCandidates: string[]): string {\n        return (\n            `matrix:${this.encodeEntity(roomId)}` +\n            `/${this.encodeEntity(eventId)}${this.encodeServerCandidates(serverCandidates)}`\n        );\n    }\n\n    public forRoom(roomIdOrAlias: string, serverCandidates: string[]): string {\n        return `matrix:${this.encodeEntity(roomIdOrAlias)}${this.encodeServerCandidates(serverCandidates)}`;\n    }\n\n    public forUser(userId: string): string {\n        return `matrix:${this.encodeEntity(userId)}`;\n    }\n\n    public forEntity(entityId: string): string {\n        return `matrix:${this.encodeEntity(entityId)}`;\n    }\n\n    public isPermalinkHost(testHost: string): boolean {\n        // TODO: Change API signature to accept the URL for checking\n        return testHost === \"\";\n    }\n\n    public encodeServerCandidates(candidates: string[]): string {\n        if (!candidates || candidates.length === 0) return \"\";\n        return `?via=${candidates.map((c) => encodeURIComponent(c)).join(\"&via=\")}`;\n    }\n\n    public parsePermalink(fullUrl: string): PermalinkParts {\n        if (!fullUrl || !fullUrl.startsWith(\"matrix:\")) {\n            throw new Error(\"Does not appear to be a permalink\");\n        }\n\n        const url = new URL(fullUrl);\n        const parts = url.pathname.split(\"/\");\n\n        const identifier = parts[0];\n        const entityNoSigil = parts[1];\n        if (identifier === \"u\") {\n            // Probably a user, no further parsing needed.\n            return PermalinkParts.forUser(`@${entityNoSigil}`);\n        } else if (identifier === \"r\" || identifier === \"roomid\") {\n            const sigil = identifier === \"r\" ? \"#\" : \"!\";\n\n            if (parts.length === 2) {\n                // room without event permalink\n                const [roomId, query = \"\"] = entityNoSigil.split(\"?\");\n                const via = query.split(/&?via=/g).filter((p) => !!p);\n                return PermalinkParts.forRoom(`${sigil}${roomId}`, via);\n            }\n\n            if (parts[2] === \"e\") {\n                // event permalink\n                const eventIdAndQuery = parts.length > 3 ? parts.slice(3).join(\"/\") : \"\";\n                const [eventId, query = \"\"] = eventIdAndQuery.split(\"?\");\n                const via = query.split(/&?via=/g).filter((p) => !!p);\n                return PermalinkParts.forEvent(`${sigil}${entityNoSigil}`, `$${eventId}`, via);\n            }\n\n            throw new Error(\"Faulty room permalink\");\n        } else {\n            throw new Error(\"Unknown entity type in permalink\");\n        }\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { isIP } from \"is-ip\";\nimport * as utils from \"matrix-js-sdk/src/utils\";\nimport { type Room, type MatrixClient, RoomStateEvent, EventType } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport MatrixToPermalinkConstructor, {\n    baseUrl as matrixtoBaseUrl,\n    baseUrlPattern as matrixToBaseUrlPattern,\n} from \"./MatrixToPermalinkConstructor\";\nimport { type PermalinkParts } from \"./PermalinkConstructor\";\nimport type PermalinkConstructor from \"./PermalinkConstructor\";\nimport ElementPermalinkConstructor from \"./ElementPermalinkConstructor\";\nimport SdkConfig from \"../../SdkConfig\";\nimport { ELEMENT_URL_PATTERN } from \"../../linkify-matrix\";\nimport MatrixSchemePermalinkConstructor from \"./MatrixSchemePermalinkConstructor\";\n\n// The maximum number of servers to pick when working out which servers\n// to add to permalinks. The servers are appended as ?via=example.org\nconst MAX_SERVER_CANDIDATES = 3;\n\nconst ANY_REGEX = /.*/;\n\n// Permalinks can have servers appended to them so that the user\n// receiving them can have a fighting chance at joining the room.\n// These servers are called \"candidates\" at this point because\n// it is unclear whether they are going to be useful to actually\n// join in the future.\n//\n// We pick 3 servers based on the following criteria:\n//\n//   Server 1: The highest power level user in the room, provided\n//   they are at least PL 50. We don't calculate \"what is a moderator\"\n//   here because it is less relevant for the vast majority of rooms.\n//   We also want to ensure that we get an admin or high-ranking mod\n//   as they are less likely to leave the room. If no user happens\n//   to meet this criteria, we'll pick the most popular server in the\n//   room.\n//\n//   Server 2: The next most popular server in the room (in user\n//   distribution). This cannot be the same as Server 1. If no other\n//   servers are available then we'll only return Server 1.\n//\n//   Server 3: The next most popular server by user distribution. This\n//   has the same rules as Server 2, with the added exception that it\n//   must be unique from Server 1 and 2.\n\n// Rationale for popular servers: It's hard to get rid of people when\n// they keep flocking in from a particular server. Sure, the server could\n// be ACL'd in the future or for some reason be evicted from the room\n// however an event like that is unlikely the larger the room gets. If\n// the server is ACL'd at the time of generating the link however, we\n// shouldn't pick them. We also don't pick IP addresses.\n\n// Note: we don't pick the server the room was created on because the\n// homeserver should already be using that server as a last ditch attempt\n// and there's less of a guarantee that the server is a resident server.\n// Instead, we actively figure out which servers are likely to be residents\n// in the future and try to use those.\n\n// Note: Users receiving permalinks that happen to have all 3 potential\n// servers fail them (in terms of joining) are somewhat expected to hunt\n// down the person who gave them the link to ask for a participating server.\n// The receiving user can then manually append the known-good server to\n// the list and magically have the link work.\n\nexport class RoomPermalinkCreator {\n    private roomId: string;\n    private highestPlUserId: string | null = null;\n    private populationMap: { [serverName: string]: number } = {};\n    private bannedHostsRegexps: RegExp[] = [];\n    private allowedHostsRegexps: RegExp[] = [];\n    private _serverCandidates?: string[];\n    private started = false;\n\n    // We support being given a roomId as a fallback in the event the `room` object\n    // doesn't exist or is not healthy for us to rely on. For example, loading a\n    // permalink to a room which the MatrixClient doesn't know about.\n    // Some of the tests done by this class are relatively expensive, so normally\n    // throttled to not happen on every update. Pass false as the shouldThrottle\n    // param to disable this behaviour, eg. for tests.\n    public constructor(\n        private room: Room | null,\n        roomId: string | null = null,\n        shouldThrottle = true,\n    ) {\n        this.roomId = room ? room.roomId : roomId!;\n\n        if (!this.roomId) {\n            throw new Error(\"Failed to resolve a roomId for the permalink creator to use\");\n        }\n    }\n\n    public load(): void {\n        if (!this.room || !this.room.currentState) {\n            // Under rare and unknown circumstances it is possible to have a room with no\n            // currentState, at least potentially at the early stages of joining a room.\n            // To avoid breaking everything, we'll just warn rather than throw as well as\n            // not bother updating the various aspects of the share link.\n            logger.warn(\"Tried to load a permalink creator with no room state\");\n            return;\n        }\n        this.fullUpdate();\n    }\n\n    public start(): void {\n        if (this.started) return;\n        this.load();\n        this.room?.currentState.on(RoomStateEvent.Update, this.onRoomStateUpdate);\n        this.started = true;\n    }\n\n    public stop(): void {\n        this.room?.currentState.removeListener(RoomStateEvent.Update, this.onRoomStateUpdate);\n        this.started = false;\n    }\n\n    public get serverCandidates(): string[] | undefined {\n        return this._serverCandidates;\n    }\n\n    public forEvent(eventId: string): string {\n        return getPermalinkConstructor().forEvent(this.roomId, eventId, this._serverCandidates);\n    }\n\n    public forShareableRoom(): string {\n        if (this.room) {\n            // Prefer to use canonical alias for permalink if possible\n            const alias = this.room.getCanonicalAlias();\n            if (alias) {\n                return getPermalinkConstructor().forRoom(alias);\n            }\n        }\n        return getPermalinkConstructor().forRoom(this.roomId, this._serverCandidates);\n    }\n\n    public forRoom(): string {\n        return getPermalinkConstructor().forRoom(this.roomId, this._serverCandidates);\n    }\n\n    private onRoomStateUpdate = (): void => {\n        this.fullUpdate();\n    };\n\n    private fullUpdate(): void {\n        // This updates the internal state of this object from the room state. It's broken\n        // down into separate functions, previously because we did some of these as incremental\n        // updates, but they were on member events which can be very numerous, so the incremental\n        // updates ended up being much slower than a full update. We now have the batch state update\n        // event, so we just update in full, but on each batch of updates.\n        this.updateAllowedServers();\n        this.updateHighestPlUser();\n        this.updatePopulationMap();\n        this.updateServerCandidates();\n    }\n\n    private updateHighestPlUser(): void {\n        const plEvent = this.room?.currentState.getStateEvents(\"m.room.power_levels\", \"\");\n        if (plEvent) {\n            const content = plEvent.getContent();\n            if (content) {\n                const users: Record<string, number> = content.users;\n                if (users) {\n                    const entries = Object.entries(users);\n                    const allowedEntries = entries.filter(([userId]) => {\n                        const member = this.room?.getMember(userId);\n                        if (!member || member.membership !== KnownMembership.Join) {\n                            return false;\n                        }\n                        const serverName = getServerName(userId);\n\n                        const domain = getHostnameFromMatrixServerName(serverName) ?? serverName;\n                        return (\n                            !isHostnameIpAddress(domain) &&\n                            !isHostInRegex(domain, this.bannedHostsRegexps) &&\n                            isHostInRegex(domain, this.allowedHostsRegexps)\n                        );\n                    });\n                    const maxEntry = allowedEntries.reduce<[string | null, number]>(\n                        (max, entry) => {\n                            return entry[1] > max[1] ? entry : max;\n                        },\n                        [null, 0],\n                    );\n                    const [userId, powerLevel] = maxEntry;\n                    // object wasn't empty, and max entry wasn't a demotion from the default\n                    if (userId !== null && powerLevel >= 50) {\n                        this.highestPlUserId = userId;\n                        return;\n                    }\n                }\n            }\n        }\n        this.highestPlUserId = null;\n    }\n\n    private updateAllowedServers(): void {\n        const bannedHostsRegexps: RegExp[] = [];\n        let allowedHostsRegexps = [ANY_REGEX]; // default allow everyone\n        if (this.room?.currentState) {\n            const aclEvent = this.room?.currentState.getStateEvents(EventType.RoomServerAcl, \"\");\n            if (aclEvent && aclEvent.getContent()) {\n                const getRegex = (hostname: string): RegExp => new RegExp(\"^\" + utils.globToRegexp(hostname) + \"$\");\n\n                const denied = aclEvent.getContent<{ deny: string[] }>().deny;\n                if (Array.isArray(denied)) {\n                    denied.forEach((h) => bannedHostsRegexps.push(getRegex(h)));\n                }\n\n                const allowed = aclEvent.getContent<{ allow: string[] }>().allow;\n                allowedHostsRegexps = []; // we don't want to use the default rule here\n                if (Array.isArray(allowed)) {\n                    allowed.forEach((h) => allowedHostsRegexps.push(getRegex(h)));\n                }\n            }\n        }\n        this.bannedHostsRegexps = bannedHostsRegexps;\n        this.allowedHostsRegexps = allowedHostsRegexps;\n    }\n\n    private updatePopulationMap(): void {\n        const populationMap: { [server: string]: number } = {};\n        if (this.room) {\n            for (const member of this.room.getJoinedMembers()) {\n                const serverName = getServerName(member.userId);\n                if (!populationMap[serverName]) {\n                    populationMap[serverName] = 0;\n                }\n                populationMap[serverName]++;\n            }\n        }\n        this.populationMap = populationMap;\n    }\n\n    private updateServerCandidates = (): void => {\n        const candidates = new Set<string>();\n        if (this.highestPlUserId) {\n            candidates.add(getServerName(this.highestPlUserId));\n        }\n\n        const serversByPopulation = Object.keys(this.populationMap).sort(\n            (a, b) => this.populationMap[b] - this.populationMap[a],\n        );\n\n        for (let i = 0; i < serversByPopulation.length && candidates.size < MAX_SERVER_CANDIDATES; i++) {\n            const serverName = serversByPopulation[i];\n            const domain = getHostnameFromMatrixServerName(serverName) ?? \"\";\n            if (\n                !candidates.has(serverName) &&\n                !isHostnameIpAddress(domain) &&\n                !isHostInRegex(domain, this.bannedHostsRegexps) &&\n                isHostInRegex(domain, this.allowedHostsRegexps)\n            ) {\n                candidates.add(serverName);\n            }\n        }\n\n        this._serverCandidates = [...candidates];\n    };\n}\n\n/**\n * Creates a permalink for an Entity. If isPill is set it uses a spec-compliant\n * prefix for the permalink, instead of permalink_prefix\n * @param {string} entityId The entity to link to.\n * @param {boolean} isPill Link should be pillifyable.\n * @returns {string|null} The transformed permalink or null if unable.\n */\nexport function makeGenericPermalink(entityId: string, isPill = false): string {\n    return getPermalinkConstructor(isPill).forEntity(entityId);\n}\n\n/**\n * Creates a permalink for a User. If isPill is set it uses a spec-compliant\n * prefix for the permalink, instead of permalink_prefix\n * @param {string} userId The user to link to.\n * @param {boolean} isPill Link should be pillifyable.\n * @returns {string|null} The transformed permalink or null if unable.\n */\nexport function makeUserPermalink(userId: string, isPill = false): string {\n    return getPermalinkConstructor(isPill).forUser(userId);\n}\n\n/**\n * Creates a permalink for a room. If isPill is set it uses a spec-compliant\n * prefix for the permalink, instead of permalink_prefix\n * @param {MatrixClient} matrixClient The MatrixClient to use\n * @param {string} roomId The user to link to.\n * @param {boolean} isPill Link should be pillifyable.\n * @returns {string|null} The transformed permalink or null if unable.\n */\nexport function makeRoomPermalink(matrixClient: MatrixClient, roomId: string, isPill = false): string {\n    if (!roomId) {\n        throw new Error(\"can't permalink a falsy roomId\");\n    }\n\n    // If the roomId isn't actually a room ID, don't try to list the servers.\n    // Aliases are already routable, and don't need extra information.\n    if (roomId[0] !== \"!\") return getPermalinkConstructor(isPill).forRoom(roomId, []);\n\n    const room = matrixClient.getRoom(roomId);\n    if (!room) {\n        return getPermalinkConstructor(isPill).forRoom(roomId, []);\n    }\n    const permalinkCreator = new RoomPermalinkCreator(room);\n    permalinkCreator.load();\n    return permalinkCreator.forShareableRoom();\n}\n\nexport function isPermalinkHost(host: string): boolean {\n    // Always check if the permalink is a spec permalink (callers are likely to call\n    // parsePermalink after this function).\n    if (new MatrixToPermalinkConstructor().isPermalinkHost(host)) return true;\n    return getPermalinkConstructor().isPermalinkHost(host);\n}\n\n/**\n * Transforms an entity (permalink, room alias, user ID, etc) into a local URL\n * if possible. If it is already a permalink (matrix.to) it gets returned\n * unchanged.\n * @param {string} entity The entity to transform.\n * @returns {string|null} The transformed permalink or null if unable.\n */\nexport function tryTransformEntityToPermalink(matrixClient: MatrixClient, entity: string): string | null {\n    if (!entity) return null;\n\n    // Check to see if it is a bare entity for starters\n    if (entity[0] === \"#\" || entity[0] === \"!\") return makeRoomPermalink(matrixClient, entity);\n    if (entity[0] === \"@\") return makeUserPermalink(entity);\n\n    if (entity.slice(0, 7) === \"matrix:\") {\n        try {\n            const permalinkParts = parsePermalink(entity);\n            if (permalinkParts) {\n                if (permalinkParts.roomIdOrAlias) {\n                    const eventIdPart = permalinkParts.eventId ? `/${permalinkParts.eventId}` : \"\";\n                    let pl = matrixtoBaseUrl + `/#/${permalinkParts.roomIdOrAlias}${eventIdPart}`;\n                    if (permalinkParts.viaServers?.length) {\n                        pl += new MatrixToPermalinkConstructor().encodeServerCandidates(permalinkParts.viaServers);\n                    }\n                    return pl;\n                } else if (permalinkParts.userId) {\n                    return matrixtoBaseUrl + `/#/${permalinkParts.userId}`;\n                }\n            }\n        } catch {}\n    }\n\n    return entity;\n}\n\n/**\n * Transforms a permalink (or possible permalink) into a local URL if possible. If\n * the given permalink is found to not be a permalink, it'll be returned unaltered.\n * @param {string} permalink The permalink to try and transform.\n * @returns {string} The transformed permalink or original URL if unable.\n */\nexport function tryTransformPermalinkToLocalHref(permalink: string): string {\n    if (\n        !permalink.startsWith(\"http:\") &&\n        !permalink.startsWith(\"https:\") &&\n        !permalink.startsWith(\"matrix:\") &&\n        !permalink.startsWith(\"vector:\") // Element Desktop\n    ) {\n        return permalink;\n    }\n\n    try {\n        const m = decodeURIComponent(permalink).match(ELEMENT_URL_PATTERN);\n        if (m) {\n            return m[1];\n        }\n    } catch {\n        // Not a valid URI\n        return permalink;\n    }\n\n    // A bit of a hack to convert permalinks of unknown origin to Element links\n    try {\n        const permalinkParts = parsePermalink(permalink);\n        if (permalinkParts) {\n            if (permalinkParts.roomIdOrAlias) {\n                const eventIdPart = permalinkParts.eventId ? `/${permalinkParts.eventId}` : \"\";\n                permalink = `#/room/${permalinkParts.roomIdOrAlias}${eventIdPart}`;\n                if (permalinkParts.viaServers?.length) {\n                    permalink += new MatrixToPermalinkConstructor().encodeServerCandidates(permalinkParts.viaServers);\n                }\n            } else if (permalinkParts.userId) {\n                permalink = `#/user/${permalinkParts.userId}`;\n            } // else not a valid permalink for our purposes - do not handle\n        }\n    } catch {\n        // Not an href we need to care about\n    }\n\n    return permalink;\n}\n\nexport function getPrimaryPermalinkEntity(permalink: string): string | null {\n    try {\n        let permalinkParts = parsePermalink(permalink);\n\n        // If not a permalink, try the vector patterns.\n        if (!permalinkParts) {\n            const m = permalink.match(ELEMENT_URL_PATTERN);\n            if (m) {\n                // A bit of a hack, but it gets the job done\n                const handler = new ElementPermalinkConstructor(\"http://localhost\");\n                const entityInfo = m[1].split(\"#\").slice(1).join(\"#\");\n                permalinkParts = handler.parsePermalink(`http://localhost/#${entityInfo}`);\n            }\n        }\n\n        if (!permalinkParts) return null; // not processable\n        if (permalinkParts.userId) return permalinkParts.userId;\n        if (permalinkParts.roomIdOrAlias) return permalinkParts.roomIdOrAlias;\n    } catch {\n        // no entity - not a permalink\n    }\n\n    return null;\n}\n\n/**\n * Returns the correct PermalinkConstructor based on permalink_prefix\n * and isPill\n * @param {boolean} isPill Should constructed links be pillifyable.\n * @returns {string|null} The transformed permalink or null if unable.\n */\nfunction getPermalinkConstructor(isPill = false): PermalinkConstructor {\n    const elementPrefix = SdkConfig.get(\"permalink_prefix\");\n    if (elementPrefix && elementPrefix !== matrixtoBaseUrl && !isPill) {\n        return new ElementPermalinkConstructor(elementPrefix);\n    }\n\n    return new MatrixToPermalinkConstructor();\n}\n\nexport function parsePermalink(fullUrl: string): PermalinkParts | null {\n    try {\n        const elementPrefix = SdkConfig.get(\"permalink_prefix\");\n        const decodedUrl = decodeURIComponent(fullUrl);\n        if (new RegExp(matrixToBaseUrlPattern, \"i\").test(decodedUrl)) {\n            return new MatrixToPermalinkConstructor().parsePermalink(decodedUrl);\n        } else if (fullUrl.startsWith(\"matrix:\")) {\n            return new MatrixSchemePermalinkConstructor().parsePermalink(fullUrl);\n        } else if (elementPrefix && fullUrl.startsWith(elementPrefix)) {\n            return new ElementPermalinkConstructor(elementPrefix).parsePermalink(fullUrl);\n        }\n    } catch (e) {\n        logger.error(\"Failed to parse permalink\", e);\n    }\n\n    return null; // not a permalink we can handle\n}\n\nexport function getServerName(userId: string): string {\n    return userId.split(\":\").splice(1).join(\":\");\n}\n\nexport function getHostnameFromMatrixServerName(serverName: string): string | null {\n    if (!serverName) return null;\n    try {\n        return new URL(`https://${serverName}`).hostname;\n    } catch (e) {\n        console.error(\"Error encountered while extracting hostname from server name\", e);\n        return null;\n    }\n}\n\nfunction isHostInRegex(hostname: string, regexps: RegExp[]): boolean {\n    if (!hostname) return true; // assumed\n    if (regexps.length > 0 && !regexps[0].test) throw new Error(regexps[0].toString());\n\n    return regexps.some((h) => h.test(hostname));\n}\n\nfunction isHostnameIpAddress(hostname: string): boolean {\n    if (!hostname) return false;\n\n    // is-ip doesn't want IPv6 addresses surrounded by brackets, so\n    // take them off.\n    if (hostname.startsWith(\"[\") && hostname.endsWith(\"]\")) {\n        hostname = hostname.substring(1, hostname.length - 1);\n    }\n\n    return isIP(hostname);\n}\n\nexport const calculateRoomVia = (room: Room): string[] => {\n    const permalinkCreator = new RoomPermalinkCreator(room);\n    permalinkCreator.load();\n    return permalinkCreator.serverCandidates ?? [];\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { tryTransformPermalinkToLocalHref } from \"./Permalinks\";\n\n/**\n * Converts a permalink to a local HREF and navigates accordingly. Throws if the permalink\n * cannot be transformed.\n * @param uri The permalink to navigate to.\n */\nexport function navigateToPermalink(uri: string): void {\n    const localUri = tryTransformPermalinkToLocalHref(uri);\n    if (!localUri || localUri === uri) {\n        // parse failure can lead to an unmodified URL\n        throw new Error(\"Failed to transform URI\");\n    }\n    window.location.hash = localUri; // it'll just be a fragment\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport SdkConfig from \"../SdkConfig\";\n\nexport function isPresenceEnabled(matrixClient: MatrixClient): boolean {\n    const hsUrl = matrixClient.baseUrl;\n    const urls = SdkConfig.get(\"enable_presence_by_hs_url\");\n    if (!urls) return true;\n    if (urls[hsUrl] || urls[hsUrl] === undefined) return true;\n    return false;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// Returns a promise which resolves when the input promise resolves with its value\n// or when the timeout of ms is reached with the value of given timeoutValue\nexport async function timeout<T, Y>(promise: Promise<T>, timeoutValue: Y, ms: number): Promise<T | Y> {\n    const timeoutPromise = new Promise<T | Y>((resolve) => {\n        const timeoutId = window.setTimeout(resolve, ms, timeoutValue);\n        promise.then(() => {\n            clearTimeout(timeoutId);\n        });\n    });\n\n    return Promise.race([promise, timeoutPromise]);\n}\n\n// Helper method to retry a Promise a given number of times or until a predicate fails\nexport async function retry<T, E extends Error>(\n    fn: () => Promise<T>,\n    num: number,\n    predicate?: (e: E) => boolean,\n): Promise<T> {\n    let lastErr!: any;\n    for (let i = 0; i < num; i++) {\n        try {\n            const v = await fn();\n            // If `await fn()` throws then we won't reach here\n            return v;\n        } catch (err) {\n            if (predicate && !predicate(err as E)) {\n                throw err;\n            }\n            lastErr = err;\n        }\n    }\n    throw lastErr;\n}\n\n/**\n * Batch promises into groups of a given size.\n * Execute the promises in parallel, but wait for all promises in a batch to resolve before moving to the next batch.\n * @param funcs - The promises to batch\n * @param batchSize - The number of promises to execute in parallel\n */\nexport async function batch<T>(funcs: Array<() => Promise<T>>, batchSize: number): Promise<T[]> {\n    const results: T[] = [];\n    for (let i = 0; i < funcs.length; i += batchSize) {\n        const batch = funcs.slice(i, i + batchSize);\n        results.push(...(await Promise.all(batch.map((f) => f()))));\n    }\n    return results;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixEvent, type MatrixClient } from \"matrix-js-sdk/src/matrix\";\nimport { isSupportedReceiptType } from \"matrix-js-sdk/src/utils\";\n\n/**\n * Determines if a read receipt update event includes the client's own user.\n * @param event The event to check.\n * @param client The client to check against.\n * @returns True if the read receipt update includes the client, false otherwise.\n */\nexport function readReceiptChangeIsFor(event: MatrixEvent, client: MatrixClient): boolean {\n    const myUserId = client.getUserId()!;\n    for (const eventId of Object.keys(event.getContent())) {\n        for (const [receiptType, receipt] of Object.entries(event.getContent()[eventId])) {\n            if (!isSupportedReceiptType(receiptType)) continue;\n\n            if (Object.keys(receipt || {}).includes(myUserId)) return true;\n        }\n    }\n    return false;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room, UNSTABLE_ELEMENT_FUNCTIONAL_USERS } from \"matrix-js-sdk/src/matrix\";\n\nexport const getFunctionalMembers = (room: Room): string[] => {\n    const [functionalUsersStateEvent] = room.currentState.getStateEvents(UNSTABLE_ELEMENT_FUNCTIONAL_USERS.name);\n\n    if (Array.isArray(functionalUsersStateEvent?.getContent().service_members)) {\n        return functionalUsersStateEvent.getContent().service_members;\n    }\n\n    return [];\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type Room, type RoomMember } from \"matrix-js-sdk/src/matrix\";\n\nimport { getFunctionalMembers } from \"./getFunctionalMembers\";\n\n/**\n * Returns all room members that are non-functional (all actual room members).\n *\n * A functional user is a user that is not a real user, but a bot, assistant, etc.\n */\nexport const getJoinedNonFunctionalMembers = (room: Room): RoomMember[] => {\n    const functionalMembers = getFunctionalMembers(room);\n    return room.getJoinedMembers().filter((m) => !functionalMembers.includes(m.userId));\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type MatrixClient } from \"matrix-js-sdk/src/matrix\";\n\nimport { shouldForceDisableEncryption } from \"./crypto/shouldForceDisableEncryption\";\nimport { getE2EEWellKnown } from \"./WellKnownUtils\";\n\nexport function privateShouldBeEncrypted(client: MatrixClient): boolean {\n    if (shouldForceDisableEncryption(client)) {\n        return false;\n    }\n    const e2eeWellKnown = getE2EEWellKnown(client);\n    if (e2eeWellKnown) {\n        const defaultDisabled = e2eeWellKnown[\"default\"] === false;\n        return !defaultDisabled;\n    }\n    return true;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { arrayDiff, type Diff } from \"./arrays\";\n\n/**\n * Determines if two sets are different through a shallow comparison.\n * @param a The first set. Must be defined.\n * @param b The second set. Must be defined.\n * @returns True if they are different, false otherwise.\n */\nexport function setHasDiff<T>(a: Set<T>, b: Set<T>): boolean {\n    if (a.size === b.size) {\n        // When the lengths are equal, check to see if either set is missing an element from the other.\n        if (Array.from(b).some((i) => !a.has(i))) return true;\n        if (Array.from(a).some((i) => !b.has(i))) return true;\n\n        // if all the keys are common, say so\n        return false;\n    } else {\n        return true; // different lengths means they are naturally diverged\n    }\n}\n\n/**\n * Determines the values added and removed between two sets.\n * @param a The first set. Must be defined.\n * @param b The second set. Must be defined.\n * @returns The difference between the values in each set.\n */\nexport function setDiff<T>(a: Set<T>, b: Set<T>): Diff<T> {\n    return arrayDiff(Array.from(a), Array.from(b));\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { type JSX, useRef, useState } from \"react\";\nimport { type Room, JoinRule } from \"matrix-js-sdk/src/matrix\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { _t } from \"../../../languageHandler\";\nimport BaseDialog from \"./BaseDialog\";\nimport AccessibleButton, { type ButtonEvent } from \"../elements/AccessibleButton\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { BetaPill } from \"../beta/BetaCard\";\nimport type Field from \"../elements/Field\";\nimport type RoomAliasField from \"../elements/RoomAliasField\";\nimport { createSpace, SpaceCreateForm } from \"../spaces/SpaceCreateMenu\";\nimport { SubspaceSelector } from \"./AddExistingToSpaceDialog\";\nimport JoinRuleDropdown from \"../elements/JoinRuleDropdown\";\n\ninterface IProps {\n    space: Room;\n    onAddExistingSpaceClick(): void;\n    onFinished(added?: boolean): void;\n}\n\nconst CreateSubspaceDialog: React.FC<IProps> = ({ space, onAddExistingSpaceClick, onFinished }) => {\n    const [parentSpace, setParentSpace] = useState(space);\n\n    const [busy, setBusy] = useState<boolean>(false);\n    const [name, setName] = useState(\"\");\n    const spaceNameField = useRef<Field>(null);\n    const [alias, setAlias] = useState(\"\");\n    const spaceAliasField = useRef<RoomAliasField>(null);\n    const [avatar, setAvatar] = useState<File | undefined>();\n    const [topic, setTopic] = useState<string>(\"\");\n\n    const spaceJoinRule = space.getJoinRule();\n    let defaultJoinRule = JoinRule.Restricted;\n    if (spaceJoinRule === JoinRule.Public) {\n        defaultJoinRule = JoinRule.Public;\n    }\n    const [joinRule, setJoinRule] = useState<JoinRule>(defaultJoinRule);\n\n    const onCreateSubspaceClick = async (e: ButtonEvent): Promise<void> => {\n        e.preventDefault();\n        if (busy) return;\n\n        setBusy(true);\n        // require & validate the space name field\n        if (spaceNameField.current && !(await spaceNameField.current.validate({ allowEmpty: false }))) {\n            spaceNameField.current.focus();\n            spaceNameField.current.validate({ allowEmpty: false, focused: true });\n            setBusy(false);\n            return;\n        }\n        // validate the space name alias field but do not require it\n        if (\n            spaceAliasField.current &&\n            joinRule === JoinRule.Public &&\n            !(await spaceAliasField.current.validate({ allowEmpty: true }))\n        ) {\n            spaceAliasField.current.focus();\n            spaceAliasField.current.validate({ allowEmpty: true, focused: true });\n            setBusy(false);\n            return;\n        }\n\n        try {\n            await createSpace(\n                space.client,\n                name,\n                joinRule === JoinRule.Public,\n                alias,\n                topic,\n                avatar,\n                {},\n                { parentSpace, joinRule },\n            );\n\n            onFinished(true);\n        } catch (e) {\n            logger.error(e);\n        }\n    };\n\n    let joinRuleMicrocopy: JSX.Element | undefined;\n    if (joinRule === JoinRule.Restricted) {\n        joinRuleMicrocopy = (\n            <p>\n                {_t(\n                    \"create_space|subspace_join_rule_restricted_description\",\n                    {},\n                    {\n                        SpaceName: () => <strong>{parentSpace.name}</strong>,\n                    },\n                )}\n            </p>\n        );\n    } else if (joinRule === JoinRule.Public) {\n        joinRuleMicrocopy = (\n            <p>\n                {_t(\n                    \"create_space|subspace_join_rule_public_description\",\n                    {},\n                    {\n                        SpaceName: () => <strong>{parentSpace.name}</strong>,\n                    },\n                )}\n            </p>\n        );\n    } else if (joinRule === JoinRule.Invite) {\n        joinRuleMicrocopy = <p>{_t(\"create_space|subspace_join_rule_invite_description\")}</p>;\n    }\n\n    return (\n        <BaseDialog\n            title={\n                <SubspaceSelector\n                    title={_t(\"create_space|subspace_dropdown_title\")}\n                    space={space}\n                    value={parentSpace}\n                    onChange={setParentSpace}\n                />\n            }\n            className=\"mx_CreateSubspaceDialog\"\n            contentId=\"mx_CreateSubspaceDialog\"\n            onFinished={onFinished}\n            fixedWidth={false}\n        >\n            <MatrixClientContext.Provider value={space.client}>\n                <div className=\"mx_CreateSubspaceDialog_content\">\n                    <div className=\"mx_CreateSubspaceDialog_betaNotice\">\n                        <BetaPill />\n                        {_t(\"create_space|subspace_beta_notice\")}\n                    </div>\n\n                    <SpaceCreateForm\n                        busy={busy}\n                        onSubmit={onCreateSubspaceClick}\n                        setAvatar={setAvatar}\n                        name={name}\n                        setName={setName}\n                        nameFieldRef={spaceNameField}\n                        topic={topic}\n                        setTopic={setTopic}\n                        alias={alias}\n                        setAlias={setAlias}\n                        showAliasField={joinRule === JoinRule.Public}\n                        aliasFieldRef={spaceAliasField}\n                    >\n                        <JoinRuleDropdown\n                            label={_t(\"create_space|subspace_join_rule_label\")}\n                            labelInvite={_t(\"create_space|subspace_join_rule_invite_only\")}\n                            labelPublic={_t(\"common|public_space\")}\n                            labelRestricted={_t(\"create_room|join_rule_restricted\")}\n                            width={478}\n                            value={joinRule}\n                            onChange={setJoinRule}\n                        />\n                        {joinRuleMicrocopy}\n                    </SpaceCreateForm>\n                </div>\n\n                <div className=\"mx_CreateSubspaceDialog_footer\">\n                    <div className=\"mx_CreateSubspaceDialog_footer_prompt\">\n                        <div>{_t(\"create_space|subspace_existing_space_prompt\")}</div>\n                        <AccessibleButton\n                            kind=\"link\"\n                            onClick={() => {\n                                onAddExistingSpaceClick();\n                                onFinished();\n                            }}\n                        >\n                            {_t(\"space|add_existing_subspace|space_dropdown_title\")}\n                        </AccessibleButton>\n                    </div>\n\n                    <AccessibleButton kind=\"primary_outline\" disabled={busy} onClick={() => onFinished(false)}>\n                        {_t(\"action|cancel\")}\n                    </AccessibleButton>\n                    <AccessibleButton kind=\"primary\" disabled={busy} onClick={onCreateSubspaceClick}>\n                        {busy ? _t(\"create_space|subspace_adding\") : _t(\"action|add\")}\n                    </AccessibleButton>\n                </div>\n            </MatrixClientContext.Provider>\n        </BaseDialog>\n    );\n};\n\nexport default CreateSubspaceDialog;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React, { useState } from \"react\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { _t } from \"../../../languageHandler\";\nimport BaseDialog from \"./BaseDialog\";\nimport AccessibleButton from \"../elements/AccessibleButton\";\nimport MatrixClientContext from \"../../../contexts/MatrixClientContext\";\nimport { AddExistingToSpace, defaultSpacesRenderer, SubspaceSelector } from \"./AddExistingToSpaceDialog\";\n\ninterface IProps {\n    space: Room;\n    onCreateSubspaceClick(): void;\n    onFinished(added?: boolean): void;\n}\n\nconst AddExistingSubspaceDialog: React.FC<IProps> = ({ space, onCreateSubspaceClick, onFinished }) => {\n    const [selectedSpace, setSelectedSpace] = useState(space);\n\n    return (\n        <BaseDialog\n            title={\n                <SubspaceSelector\n                    title={_t(\"space|add_existing_subspace|space_dropdown_title\")}\n                    space={space}\n                    value={selectedSpace}\n                    onChange={setSelectedSpace}\n                />\n            }\n            className=\"mx_AddExistingToSpaceDialog\"\n            contentId=\"mx_AddExistingToSpace\"\n            onFinished={onFinished}\n            fixedWidth={false}\n        >\n            <MatrixClientContext.Provider value={space.client}>\n                <AddExistingToSpace\n                    space={space}\n                    onFinished={onFinished}\n                    footerPrompt={\n                        <>\n                            <div>{_t(\"space|add_existing_subspace|create_prompt\")}</div>\n                            <AccessibleButton onClick={onCreateSubspaceClick} kind=\"link\">\n                                {_t(\"space|add_existing_subspace|create_button\")}\n                            </AccessibleButton>\n                        </>\n                    }\n                    filterPlaceholder={_t(\"space|add_existing_subspace|filter_placeholder\")}\n                    spacesRenderer={defaultSpacesRenderer}\n                />\n            </MatrixClientContext.Provider>\n        </BaseDialog>\n    );\n};\n\nexport default AddExistingSubspaceDialog;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport { type Room, type ICreateRoomStateEvent, type RoomType, EventType, JoinRule } from \"matrix-js-sdk/src/matrix\";\nimport { KnownMembership } from \"matrix-js-sdk/src/types\";\n\nimport { calculateRoomVia } from \"./permalinks/Permalinks\";\nimport Modal from \"../Modal\";\nimport CreateRoomDialog from \"../components/views/dialogs/CreateRoomDialog\";\nimport createRoom from \"../createRoom\";\nimport { _t } from \"../languageHandler\";\nimport SpacePublicShare from \"../components/views/spaces/SpacePublicShare\";\nimport InfoDialog from \"../components/views/dialogs/InfoDialog\";\nimport { showRoomInviteDialog } from \"../RoomInvite\";\nimport CreateSubspaceDialog from \"../components/views/dialogs/CreateSubspaceDialog\";\nimport AddExistingSubspaceDialog from \"../components/views/dialogs/AddExistingSubspaceDialog\";\nimport defaultDispatcher from \"../dispatcher/dispatcher\";\nimport { Action } from \"../dispatcher/actions\";\nimport Spinner from \"../components/views/elements/Spinner\";\nimport { shouldShowComponent } from \"../customisations/helpers/UIComponents\";\nimport { UIComponent } from \"../settings/UIFeature\";\nimport {\n    type OpenSpacePreferencesPayload,\n    type SpacePreferenceTab,\n} from \"../dispatcher/payloads/OpenSpacePreferencesPayload\";\nimport { type OpenSpaceSettingsPayload } from \"../dispatcher/payloads/OpenSpaceSettingsPayload\";\nimport { type OpenAddExistingToSpaceDialogPayload } from \"../dispatcher/payloads/OpenAddExistingToSpaceDialogPayload\";\nimport { SdkContextClass } from \"../contexts/SDKContext\";\n\nexport const shouldShowSpaceSettings = (space: Room): boolean => {\n    const userId = space.client.getUserId()!;\n    return (\n        space.getMyMembership() === KnownMembership.Join &&\n        (space.currentState.maySendStateEvent(EventType.RoomAvatar, userId) ||\n            space.currentState.maySendStateEvent(EventType.RoomName, userId) ||\n            space.currentState.maySendStateEvent(EventType.RoomTopic, userId) ||\n            space.currentState.maySendStateEvent(EventType.RoomJoinRules, userId))\n    );\n};\n\nexport const makeSpaceParentEvent = (room: Room, canonical = false): ICreateRoomStateEvent => ({\n    type: EventType.SpaceParent,\n    content: {\n        via: calculateRoomVia(room),\n        canonical: canonical,\n    },\n    state_key: room.roomId,\n});\n\nexport function showSpaceSettings(space: Room): void {\n    defaultDispatcher.dispatch<OpenSpaceSettingsPayload>({\n        action: Action.OpenSpaceSettings,\n        space,\n    });\n}\n\nexport const showAddExistingRooms = (space: Room): void => {\n    defaultDispatcher.dispatch<OpenAddExistingToSpaceDialogPayload>({\n        action: Action.OpenAddToExistingSpaceDialog,\n        space,\n    });\n};\n\nexport const showCreateNewRoom = async (space: Room, type?: RoomType): Promise<boolean> => {\n    const modal = Modal.createDialog(CreateRoomDialog, {\n        type,\n        defaultPublic: space.getJoinRule() === JoinRule.Public,\n        parentSpace: space,\n    });\n    const [shouldCreate, opts] = await modal.finished;\n    if (shouldCreate) {\n        await createRoom(space.client, opts!);\n    }\n    return !!shouldCreate;\n};\n\nexport const shouldShowSpaceInvite = (space: Room): boolean =>\n    ((space?.getMyMembership() === KnownMembership.Join && space.canInvite(space.client.getUserId()!)) ||\n        space.getJoinRule() === JoinRule.Public) &&\n    shouldShowComponent(UIComponent.InviteUsers);\n\nexport const showSpaceInvite = (space: Room, initialText = \"\"): void => {\n    if (space.getJoinRule() === \"public\") {\n        const modal = Modal.createDialog(InfoDialog, {\n            title: _t(\"invite|to_space\", { spaceName: space.name }),\n            description: (\n                <React.Fragment>\n                    <span>{_t(\"space|share_public\")}</span>\n                    <SpacePublicShare space={space} onFinished={() => modal.close()} />\n                </React.Fragment>\n            ),\n            fixedWidth: false,\n            button: false,\n            className: \"mx_SpacePanel_sharePublicSpace\",\n            hasCloseButton: true,\n        });\n    } else {\n        showRoomInviteDialog(space.roomId, initialText);\n    }\n};\n\nexport const showAddExistingSubspace = (space: Room): void => {\n    const { finished } = Modal.createDialog(\n        AddExistingSubspaceDialog,\n        {\n            space,\n            onCreateSubspaceClick: () => showCreateNewSubspace(space),\n        },\n        \"mx_AddExistingToSpaceDialog_wrapper\",\n    );\n    finished.then(([added]) => {\n        if (added && SdkContextClass.instance.roomViewStore.getRoomId() === space.roomId) {\n            defaultDispatcher.fire(Action.UpdateSpaceHierarchy);\n        }\n    });\n};\n\nexport const showCreateNewSubspace = (space: Room): void => {\n    const { finished } = Modal.createDialog(\n        CreateSubspaceDialog,\n        {\n            space,\n            onAddExistingSpaceClick: () => showAddExistingSubspace(space),\n        },\n        \"mx_CreateSubspaceDialog_wrapper\",\n    );\n    finished.then(([added]) => {\n        if (added && SdkContextClass.instance.roomViewStore.getRoomId() === space.roomId) {\n            defaultDispatcher.fire(Action.UpdateSpaceHierarchy);\n        }\n    });\n};\n\nexport const bulkSpaceBehaviour = async (\n    space: Room,\n    children: Room[],\n    fn: (room: Room) => Promise<unknown>,\n): Promise<void> => {\n    const modal = Modal.createDialog(Spinner, undefined, \"mx_Dialog_spinner\");\n    try {\n        for (const room of children) {\n            await fn(room);\n        }\n        await fn(space);\n    } finally {\n        modal.close();\n    }\n};\n\nexport const showSpacePreferences = (space: Room, initialTabId?: SpacePreferenceTab): void => {\n    defaultDispatcher.dispatch<OpenSpacePreferencesPayload>({\n        action: Action.OpenSpacePreferences,\n        space,\n        initialTabId,\n    });\n};\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n/**\n * Copy plaintext to user's clipboard\n * It will overwrite user's selection range\n * In certain browsers it may only work if triggered by a user action or may ask user for permissions\n * Tries to use new async clipboard API if available\n * @param text the plaintext to put in the user's clipboard\n */\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nexport async function copyPlaintext(text: string): Promise<boolean> {\n    try {\n        if (navigator?.clipboard?.writeText) {\n            await navigator.clipboard.writeText(text);\n            return true;\n        } else {\n            const textArea = document.createElement(\"textarea\");\n            textArea.value = text;\n\n            // Avoid scrolling to bottom\n            textArea.style.top = \"0\";\n            textArea.style.left = \"0\";\n            textArea.style.position = \"fixed\";\n\n            document.body.appendChild(textArea);\n            const selection = document.getSelection()!;\n            const range = document.createRange();\n            // range.selectNodeContents(textArea);\n            range.selectNode(textArea);\n            selection.removeAllRanges();\n            selection.addRange(range);\n\n            const successful = document.execCommand(\"copy\");\n            selection.removeAllRanges();\n            document.body.removeChild(textArea);\n            return successful;\n        }\n    } catch (e) {\n        logger.error(\"copyPlaintext failed\", e);\n    }\n    return false;\n}\n\nexport function selectText(target: Element): void {\n    const range = document.createRange();\n    range.selectNodeContents(target);\n\n    const selection = window.getSelection()!;\n    selection.removeAllRanges();\n    selection.addRange(range);\n}\n\n/**\n * Copy rich text to user's clipboard\n * It will overwrite user's selection range\n * In certain browsers it may only work if triggered by a user action or may ask user for permissions\n * @param ref pointer to the node to copy\n */\nexport function copyNode(ref?: Element | null): boolean {\n    if (!ref) return false;\n    selectText(ref);\n    return document.execCommand(\"copy\");\n}\n\n/**\n * Returns text which has been selected by the user\n * @returns the selected text\n */\nexport function getSelectedText(): string {\n    return window.getSelection()!.toString();\n}\n\nexport const graphemeSegmenter = new Intl.Segmenter();\n\n/**\n * Returns the first grapheme in the given string,\n * especially useful for strings containing emoji, will not break compound emoji up.\n * @param str string to parse\n * @returns the first grapheme or an empty string if given an empty string\n */\nexport function getFirstGrapheme(str: string): string {\n    const result = graphemeSegmenter.segment(str)[Symbol.iterator]().next();\n    return result.done ? \"\" : result.value.segment;\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nexport function toPx(pixelValue: number): string {\n    return pixelValue + \"px\";\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2022 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport type { Room } from \"matrix-js-sdk/src/matrix\";\n\n/**\n * Determines whether the given room is a video room.\n */\nexport const isVideoRoom = (room: Room): boolean => room.isElementVideoRoom() || room.isCallRoom();\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\n\nimport ToastStore from \"../../../stores/ToastStore\";\nimport GenericToast, { type IProps as IGenericToastProps } from \"./GenericToast\";\nimport { useExpiringCounter } from \"../../../hooks/useTimeout\";\n\ninterface IProps extends IGenericToastProps {\n    toastKey: string;\n    numSeconds: number;\n    dismissLabel: string;\n    onDismiss?(): void;\n}\n\nconst SECOND = 1000;\n\nconst GenericExpiringToast: React.FC<IProps> = ({\n    description,\n    primaryLabel,\n    dismissLabel,\n    onPrimaryClick,\n    onDismiss,\n    toastKey,\n    numSeconds,\n}) => {\n    const onReject = (): void => {\n        if (onDismiss) onDismiss();\n        ToastStore.sharedInstance().dismissToast(toastKey);\n    };\n    const counter = useExpiringCounter(onReject, SECOND, numSeconds);\n\n    let rejectLabel = dismissLabel;\n    if (counter > 0) {\n        rejectLabel += ` (${counter})`;\n    }\n\n    return (\n        <GenericToast\n            description={description}\n            primaryLabel={primaryLabel}\n            onPrimaryClick={onPrimaryClick}\n            secondaryLabel={rejectLabel}\n            onSecondaryClick={onReject}\n        />\n    );\n};\n\nexport default GenericExpiringToast;\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 Šimon Brandner <simon.bra.ag@gmail.com>\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport React from \"react\";\nimport classNames from \"classnames\";\n\nimport { _t, _td } from \"../../../languageHandler\";\nimport BaseDialog from \"..//dialogs/BaseDialog\";\nimport DialogButtons from \"./DialogButtons\";\nimport AccessibleButton from \"./AccessibleButton\";\nimport TabbedView, { Tab, TabLocation } from \"../../structures/TabbedView\";\nimport PlatformPeg from \"../../../PlatformPeg\";\nimport { type NonEmptyArray } from \"../../../@types/common\";\n\nexport function getDesktopCapturerSources(): Promise<Array<DesktopCapturerSource>> {\n    const options: GetSourcesOptions = {\n        thumbnailSize: {\n            height: 176,\n            width: 312,\n        },\n        types: [\"screen\", \"window\"],\n    };\n    const plaf = PlatformPeg.get();\n    return plaf ? plaf?.getDesktopCapturerSources(options) : Promise.resolve<DesktopCapturerSource[]>([]);\n}\n\nexport enum Tabs {\n    Screens = \"screen\",\n    Windows = \"window\",\n}\n\nexport interface ExistingSourceIProps {\n    source: DesktopCapturerSource;\n    onSelect(source: DesktopCapturerSource): void;\n    selected: boolean;\n}\n\nexport class ExistingSource extends React.Component<ExistingSourceIProps> {\n    private onClick = (): void => {\n        this.props.onSelect(this.props.source);\n    };\n\n    public render(): React.ReactNode {\n        const thumbnailClasses = classNames({\n            mx_desktopCapturerSourcePicker_source_thumbnail: true,\n            mx_desktopCapturerSourcePicker_source_thumbnail_selected: this.props.selected,\n        });\n\n        return (\n            <AccessibleButton\n                className=\"mx_desktopCapturerSourcePicker_source\"\n                title={this.props.source.name}\n                onClick={this.onClick}\n            >\n                <img alt={this.props.source.name} className={thumbnailClasses} src={this.props.source.thumbnailURL} />\n                <span className=\"mx_desktopCapturerSourcePicker_source_name\">{this.props.source.name}</span>\n            </AccessibleButton>\n        );\n    }\n}\n\nexport interface PickerIState {\n    selectedTab: Tabs;\n    sources: Array<DesktopCapturerSource>;\n    selectedSource?: DesktopCapturerSource;\n}\nexport interface PickerIProps {\n    onFinished(source?: DesktopCapturerSource): void;\n}\n\nexport default class DesktopCapturerSourcePicker extends React.Component<PickerIProps, PickerIState> {\n    public interval?: number;\n\n    public constructor(props: PickerIProps) {\n        super(props);\n\n        this.state = {\n            selectedTab: Tabs.Screens,\n            sources: [],\n        };\n    }\n\n    public async componentDidMount(): Promise<void> {\n        // window.setInterval() first waits and then executes, therefore\n        // we call getDesktopCapturerSources() here without any delay.\n        // Otherwise the dialog would be left empty for some time.\n        this.setState({\n            sources: await getDesktopCapturerSources(),\n        });\n\n        // We update the sources every 500ms to get newer thumbnails\n        this.interval = window.setInterval(async (): Promise<void> => {\n            this.setState({\n                sources: await getDesktopCapturerSources(),\n            });\n        }, 500);\n    }\n\n    public componentWillUnmount(): void {\n        clearInterval(this.interval);\n    }\n\n    private onSelect = (source: DesktopCapturerSource): void => {\n        this.setState({ selectedSource: source });\n    };\n\n    private onShare = (): void => {\n        this.props.onFinished(this.state.selectedSource);\n    };\n\n    private onTabChange = (tab: Tabs): void => {\n        this.setState({ selectedSource: undefined, selectedTab: tab });\n    };\n\n    private onCloseClick = (): void => {\n        this.props.onFinished();\n    };\n\n    private getTab(type: Tabs, label: TranslationKey): Tab<Tabs> {\n        const sources = this.state.sources\n            .filter((source) => source.id.startsWith(type))\n            .map((source) => {\n                return (\n                    <ExistingSource\n                        selected={this.state.selectedSource?.id === source.id}\n                        source={source}\n                        onSelect={this.onSelect}\n                        key={source.id}\n                    />\n                );\n            });\n\n        return new Tab(type, label, null, <div className=\"mx_desktopCapturerSourcePicker_tab\">{sources}</div>);\n    }\n\n    public render(): React.ReactNode {\n        const tabs: NonEmptyArray<Tab<Tabs>> = [\n            this.getTab(Tabs.Screens, _td(\"voip|screenshare_monitor\")),\n            this.getTab(Tabs.Windows, _td(\"voip|screenshare_window\")),\n        ];\n\n        return (\n            <BaseDialog\n                className=\"mx_desktopCapturerSourcePicker\"\n                onFinished={this.onCloseClick}\n                title={_t(\"voip|screenshare_title\")}\n            >\n                <TabbedView\n                    tabs={tabs}\n                    tabLocation={TabLocation.TOP}\n                    activeTabId={this.state.selectedTab}\n                    onChange={this.onTabChange}\n                />\n                <DialogButtons\n                    primaryButton={_t(\"action|share\")}\n                    hasCancel={true}\n                    onCancel={this.onCloseClick}\n                    onPrimaryButtonClick={this.onShare}\n                    primaryDisabled={!this.state.selectedSource}\n                />\n            </BaseDialog>\n        );\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019-2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type IMatrixProfile,\n    type IEventWithRoomId as IMatrixEvent,\n    type IResultRoomEvents,\n    type Direction,\n} from \"matrix-js-sdk/src/matrix\";\n\n// The following interfaces take their names and member names from seshat and the spec\n/* eslint-disable camelcase */\n\n/** A record of a place to resume crawling events in a given room. */\nexport interface ICrawlerCheckpoint {\n    /** The room to be indexed */\n    roomId: string;\n\n    /** The pagination index to resume crawling from. */\n    token: string;\n\n    /**\n     * If `fullCrawl` is false (or absent) and we find that we have already indexed the events we find, then we stop crawling.\n     *\n     * If `fullCrawl` is true, then we keep going until we reach the end of the room history.\n     */\n    fullCrawl?: boolean;\n\n    /** Whether we should crawl in the forward or backward direction. */\n    direction: Direction;\n}\n\nexport interface ISearchArgs {\n    search_term: string;\n    before_limit: number;\n    after_limit: number;\n    order_by_recency: boolean;\n    room_id?: string;\n    limit: number;\n    next_batch?: string;\n}\n\nexport interface IEventAndProfile {\n    event: IMatrixEvent;\n    profile: IMatrixProfile;\n}\n\nexport interface ILoadArgs {\n    roomId: string;\n    limit: number;\n    fromEvent?: string;\n    direction?: string;\n}\n\nexport interface IIndexStats {\n    size: number;\n    eventCount: number;\n    roomCount: number;\n}\n\n/**\n * Base class for classes that provide platform-specific event indexing.\n *\n * Instances of this class are provided by the application.\n */\nexport default abstract class BaseEventIndexManager {\n    /**\n     * Does our EventIndexManager support event indexing.\n     *\n     * If an EventIndexManager implementor has runtime dependencies that\n     * optionally enable event indexing they may override this method to perform\n     * the necessary runtime checks here.\n     *\n     * @return {Promise} A promise that will resolve to true if event indexing\n     * is supported, false otherwise.\n     */\n    public async supportsEventIndexing(): Promise<boolean> {\n        return true;\n    }\n    /**\n     * Initialize the event index for the given user.\n     *\n     * @param {string} userId The event that should be added to the index.\n     * @param {string} deviceId The profile of the event sender at the\n     *\n     * @return {Promise} A promise that will resolve when the event index is\n     * initialized.\n     */\n    public async initEventIndex(userId: string, deviceId: string): Promise<void> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Queue up an event to be added to the index.\n     *\n     * @param {MatrixEvent} ev The event that should be added to the index.\n     * @param {IMatrixProfile} profile The profile of the event sender at the\n     * time the event was received.\n     *\n     * @return {Promise} A promise that will resolve when the was queued up for\n     * addition.\n     */\n    public async addEventToIndex(ev: IMatrixEvent, profile: IMatrixProfile): Promise<void> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    public async deleteEvent(eventId: string): Promise<boolean> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    public async isEventIndexEmpty(): Promise<boolean> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Check if the room with the given id is already indexed.\n     *\n     * @param {string} roomId The ID of the room which we want to check if it\n     * has been already indexed.\n     *\n     * @return {Promise<boolean>} Returns true if the index contains events for\n     * the given room, false otherwise.\n     */\n    public isRoomIndexed(roomId: string): Promise<boolean> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Get statistical information of the index.\n     *\n     * @return {Promise<IIndexStats>} A promise that will resolve to the index\n     * statistics.\n     */\n    public async getStats(): Promise<IIndexStats> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Get the user version of the database.\n     * @return {Promise<number>} A promise that will resolve to the user stored\n     * version number.\n     */\n    public async getUserVersion(): Promise<number> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Set the user stored version to the given version number.\n     *\n     * @param {number} version The new version that should be stored in the\n     * database.\n     *\n     * @return {Promise<void>} A promise that will resolve once the new version\n     * is stored.\n     */\n    public async setUserVersion(version: number): Promise<void> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Commit the previously queued up events to the index.\n     *\n     * @return {Promise} A promise that will resolve once the queued up events\n     * were added to the index.\n     */\n    public async commitLiveEvents(): Promise<void> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Search the event index using the given term for matching events.\n     *\n     * @param {ISearchArgs} searchArgs The search configuration for the search,\n     * sets the search term and determines the search result contents.\n     *\n     * @return {Promise<IResultRoomEvents[]>} A promise that will resolve to an array\n     * of search results once the search is done.\n     */\n    public async searchEventIndex(searchArgs: ISearchArgs): Promise<IResultRoomEvents> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Add events from the room history to the event index.\n     *\n     * This is used to add a batch of events to the index.\n     *\n     * @param {[IEventAndProfile]} events The list of events and profiles that\n     * should be added to the event index.\n     * @param {[ICrawlerCheckpoint]} checkpoint A new crawler checkpoint that\n     * should be stored in the index which should be used to continue crawling\n     * the room.\n     * @param {[ICrawlerCheckpoint]} oldCheckpoint The checkpoint that was used\n     * to fetch the current batch of events. This checkpoint will be removed\n     * from the index.\n     *\n     * @return {Promise} A promise that will resolve to true if all the events\n     * were already added to the index, false otherwise.\n     */\n    public async addHistoricEvents(\n        events: IEventAndProfile[],\n        checkpoint: ICrawlerCheckpoint | null,\n        oldCheckpoint: ICrawlerCheckpoint | null,\n    ): Promise<boolean> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Add a new crawler checkpoint to the index.\n     *\n     * @param {ICrawlerCheckpoint} checkpoint The checkpoint that should be added\n     * to the index.\n     *\n     * @return {Promise} A promise that will resolve once the checkpoint has\n     * been stored.\n     */\n    public async addCrawlerCheckpoint(checkpoint: ICrawlerCheckpoint): Promise<void> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Add a new crawler checkpoint to the index.\n     *\n     * @param {ICrawlerCheckpoint} checkpoint The checkpoint that should be\n     * removed from the index.\n     *\n     * @return {Promise} A promise that will resolve once the checkpoint has\n     * been removed.\n     */\n    public async removeCrawlerCheckpoint(checkpoint: ICrawlerCheckpoint): Promise<void> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Load the stored checkpoints from the index.\n     *\n     * @return {Promise<[ICrawlerCheckpoint]>} A promise that will resolve to an\n     * array of crawler checkpoints once they have been loaded from the index.\n     */\n    public async loadCheckpoints(): Promise<ICrawlerCheckpoint[]> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /** Load events that contain an mxc URL to a file from the index.\n     *\n     * @param  {object} args Arguments object for the method.\n     * @param  {string} args.roomId The ID of the room for which the events\n     * should be loaded.\n     * @param  {number} args.limit The maximum number of events to return.\n     * @param  {string} args.fromEvent An event id of a previous event returned\n     * by this method. Passing this means that we are going to continue loading\n     * events from this point in the history.\n     * @param  {string} args.direction The direction to which we should continue\n     * loading events from. This is used only if fromEvent is used as well.\n     *\n     * @return {Promise<[IEventAndProfile]>} A promise that will resolve to an\n     * array of Matrix events that contain mxc URLs accompanied with the\n     * historic profile of the sender.\n     */\n    public async loadFileEvents(args: ILoadArgs): Promise<IEventAndProfile[]> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * close our event index.\n     *\n     * @return {Promise} A promise that will resolve once the event index has\n     * been closed.\n     */\n    public async closeEventIndex(): Promise<void> {\n        throw new Error(\"Unimplemented\");\n    }\n\n    /**\n     * Delete our current event index.\n     *\n     * @return {Promise} A promise that will resolve once the event index has\n     * been deleted.\n     */\n    public async deleteEventIndex(): Promise<void> {\n        throw new Error(\"Unimplemented\");\n    }\n}\n","/*\nCopyright 2022-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { type ElectronChannel } from \"../../@types/global\";\n\ninterface IPCPayload {\n    id?: number;\n    error?: string | { message: string };\n    reply?: any;\n}\n\nexport class IPCManager {\n    private pendingIpcCalls: { [ipcCallId: number]: PromiseWithResolvers<any> } = {};\n    private nextIpcCallId = 0;\n\n    public constructor(\n        private readonly sendChannel: ElectronChannel = \"ipcCall\",\n        private readonly recvChannel: ElectronChannel = \"ipcReply\",\n    ) {\n        if (!window.electron) {\n            throw new Error(\"Cannot instantiate ElectronPlatform, window.electron is not set\");\n        }\n        window.electron.on(this.recvChannel, this.onIpcReply);\n    }\n\n    public async call(name: string, ...args: any[]): Promise<any> {\n        // TODO this should be moved into the preload.js file.\n        const ipcCallId = ++this.nextIpcCallId;\n        const deferred = Promise.withResolvers<any>();\n        this.pendingIpcCalls[ipcCallId] = deferred;\n        // Maybe add a timeout to these? Probably not necessary.\n        window.electron!.send(this.sendChannel, { id: ipcCallId, name, args });\n        return deferred.promise;\n    }\n\n    private onIpcReply = (_ev: Event, payload: IPCPayload): void => {\n        if (payload.id === undefined) {\n            logger.warn(\"Ignoring IPC reply with no ID\");\n            return;\n        }\n\n        if (this.pendingIpcCalls[payload.id] === undefined) {\n            logger.warn(\"Unknown IPC payload ID: \" + payload.id);\n            return;\n        }\n\n        const callbacks = this.pendingIpcCalls[payload.id];\n        delete this.pendingIpcCalls[payload.id];\n        if (payload.error) {\n            // `seshat.ts` sends a JavaScript object with a `message` property. Turn it into a proper Error.\n            let error = payload.error;\n            if (typeof error === \"object\" && error.message) {\n                error = new Error(error.message);\n            }\n            callbacks.reject(error);\n        } else {\n            callbacks.resolve(payload.reply);\n        }\n    };\n}\n","/*\nCopyright 2022-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// eslint-disable-next-line no-restricted-imports\nimport {\n    type IMatrixProfile,\n    type IEventWithRoomId as IMatrixEvent,\n    type IResultRoomEvents,\n} from \"matrix-js-sdk/src/@types/search\";\n\nimport BaseEventIndexManager, {\n    type ICrawlerCheckpoint,\n    type IEventAndProfile,\n    type IIndexStats,\n    type ISearchArgs,\n    type ILoadArgs,\n} from \"../../indexing/BaseEventIndexManager\";\nimport { IPCManager } from \"./IPCManager\";\n\nexport class SeshatIndexManager extends BaseEventIndexManager {\n    private readonly ipc = new IPCManager(\"seshat\", \"seshatReply\");\n\n    public async supportsEventIndexing(): Promise<boolean> {\n        return this.ipc.call(\"supportsEventIndexing\");\n    }\n\n    public async initEventIndex(userId: string, deviceId: string): Promise<void> {\n        return this.ipc.call(\"initEventIndex\", userId, deviceId);\n    }\n\n    public async addEventToIndex(ev: IMatrixEvent, profile: IMatrixProfile): Promise<void> {\n        return this.ipc.call(\"addEventToIndex\", ev, profile);\n    }\n\n    public async deleteEvent(eventId: string): Promise<boolean> {\n        return this.ipc.call(\"deleteEvent\", eventId);\n    }\n\n    public async isEventIndexEmpty(): Promise<boolean> {\n        return this.ipc.call(\"isEventIndexEmpty\");\n    }\n\n    public async isRoomIndexed(roomId: string): Promise<boolean> {\n        return this.ipc.call(\"isRoomIndexed\", roomId);\n    }\n\n    public async commitLiveEvents(): Promise<void> {\n        return this.ipc.call(\"commitLiveEvents\");\n    }\n\n    public async searchEventIndex(searchConfig: ISearchArgs): Promise<IResultRoomEvents> {\n        return this.ipc.call(\"searchEventIndex\", searchConfig);\n    }\n\n    public async addHistoricEvents(\n        events: IEventAndProfile[],\n        checkpoint: ICrawlerCheckpoint | null,\n        oldCheckpoint: ICrawlerCheckpoint | null,\n    ): Promise<boolean> {\n        return this.ipc.call(\"addHistoricEvents\", events, checkpoint, oldCheckpoint);\n    }\n\n    public async addCrawlerCheckpoint(checkpoint: ICrawlerCheckpoint): Promise<void> {\n        return this.ipc.call(\"addCrawlerCheckpoint\", checkpoint);\n    }\n\n    public async removeCrawlerCheckpoint(checkpoint: ICrawlerCheckpoint): Promise<void> {\n        return this.ipc.call(\"removeCrawlerCheckpoint\", checkpoint);\n    }\n\n    public async loadFileEvents(args: ILoadArgs): Promise<IEventAndProfile[]> {\n        return this.ipc.call(\"loadFileEvents\", args);\n    }\n\n    public async loadCheckpoints(): Promise<ICrawlerCheckpoint[]> {\n        return this.ipc.call(\"loadCheckpoints\");\n    }\n\n    public async closeEventIndex(): Promise<void> {\n        return this.ipc.call(\"closeEventIndex\");\n    }\n\n    public async getStats(): Promise<IIndexStats> {\n        return this.ipc.call(\"getStats\");\n    }\n\n    public async getUserVersion(): Promise<number> {\n        return this.ipc.call(\"getUserVersion\");\n    }\n\n    public async setUserVersion(version: number): Promise<void> {\n        return this.ipc.call(\"setUserVersion\", version);\n    }\n\n    public async deleteEventIndex(): Promise<void> {\n        return this.ipc.call(\"deleteEventIndex\");\n    }\n}\n","/*\nCopyright 2024-2025 New Vector Ltd.\nCopyright 2022 Šimon Brandner <simon.bra.ag@gmail.com>\nCopyright 2018-2021 New Vector Ltd\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2016 Aviral Dasgupta\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport {\n    type MatrixClient,\n    type Room,\n    type MatrixEvent,\n    type OidcRegistrationClientMetadata,\n} from \"matrix-js-sdk/src/matrix\";\nimport React from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { uniqueId } from \"lodash\";\n\nimport BasePlatform, { UpdateCheckStatus, type UpdateStatus } from \"../../BasePlatform\";\nimport type BaseEventIndexManager from \"../../indexing/BaseEventIndexManager\";\nimport dis from \"../../dispatcher/dispatcher\";\nimport SdkConfig from \"../../SdkConfig\";\nimport { type IConfigOptions } from \"../../IConfigOptions\";\nimport * as rageshake from \"../../rageshake/rageshake\";\nimport Modal from \"../../Modal\";\nimport InfoDialog from \"../../components/views/dialogs/InfoDialog\";\nimport Spinner from \"../../components/views/elements/Spinner\";\nimport { Action } from \"../../dispatcher/actions\";\nimport { type ActionPayload } from \"../../dispatcher/payloads\";\nimport { showToast as showUpdateToast } from \"../../toasts/UpdateToast\";\nimport { type CheckUpdatesPayload } from \"../../dispatcher/payloads/CheckUpdatesPayload\";\nimport ToastStore from \"../../stores/ToastStore\";\nimport GenericExpiringToast from \"../../components/views/toasts/GenericExpiringToast\";\nimport { BreadcrumbsStore } from \"../../stores/BreadcrumbsStore\";\nimport { UPDATE_EVENT } from \"../../stores/AsyncStore\";\nimport { avatarUrlForRoom, getInitialLetter } from \"../../Avatar\";\nimport DesktopCapturerSourcePicker from \"../../components/views/elements/DesktopCapturerSourcePicker\";\nimport { MatrixClientPeg } from \"../../MatrixClientPeg\";\nimport { SeshatIndexManager } from \"./SeshatIndexManager\";\nimport { IPCManager } from \"./IPCManager\";\nimport { _t } from \"../../languageHandler\";\nimport { BadgeOverlayRenderer } from \"../../favicon\";\nimport GenericToast from \"../../components/views/toasts/GenericToast.tsx\";\n\ninterface SquirrelUpdate {\n    releaseNotes: string;\n    releaseName: string;\n    releaseDate: Date;\n    updateURL: string;\n}\n\nconst SSO_ID_KEY = \"element-desktop-ssoid\";\n\nfunction platformFriendlyName(): string {\n    // used to use window.process but the same info is available here\n    if (navigator.userAgent.includes(\"Macintosh\")) {\n        return \"macOS\";\n    } else if (navigator.userAgent.includes(\"FreeBSD\")) {\n        return \"FreeBSD\";\n    } else if (navigator.userAgent.includes(\"OpenBSD\")) {\n        return \"OpenBSD\";\n    } else if (navigator.userAgent.includes(\"SunOS\")) {\n        return \"SunOS\";\n    } else if (navigator.userAgent.includes(\"Windows\")) {\n        return \"Windows\";\n    } else if (navigator.userAgent.includes(\"Linux\")) {\n        return \"Linux\";\n    } else {\n        return \"Unknown\";\n    }\n}\n\nfunction getUpdateCheckStatus(status: boolean | string): UpdateStatus {\n    if (status === true) {\n        return { status: UpdateCheckStatus.Downloading };\n    } else if (status === false) {\n        return { status: UpdateCheckStatus.NotAvailable };\n    } else {\n        return {\n            status: UpdateCheckStatus.Error,\n            detail: status,\n        };\n    }\n}\n\nexport default class ElectronPlatform extends BasePlatform {\n    private readonly ipc = new IPCManager(\"ipcCall\", \"ipcReply\");\n    private readonly eventIndexManager: BaseEventIndexManager = new SeshatIndexManager();\n    public readonly initialised: Promise<void>;\n    private readonly electron: Electron;\n    private protocol!: string;\n    private sessionId!: string;\n    private badgeOverlayRenderer?: BadgeOverlayRenderer;\n    private config!: IConfigOptions;\n    private supportedSettings?: Record<string, boolean>;\n    private clientStartedPromiseWithResolvers = Promise.withResolvers<void>();\n\n    public constructor() {\n        super();\n\n        if (!window.electron) {\n            throw new Error(\"Cannot instantiate ElectronPlatform, window.electron is not set\");\n        }\n        this.electron = window.electron;\n\n        /*\n            IPC Call `check_updates` returns:\n            true if there is an update available\n            false if there is not\n            or the error if one is encountered\n         */\n        this.electron.on(\"check_updates\", (event, status) => {\n            dis.dispatch<CheckUpdatesPayload>({\n                action: Action.CheckUpdates,\n                ...getUpdateCheckStatus(status),\n            });\n        });\n\n        // `userAccessToken` (IPC) is requested by the main process when appending authentication\n        // to media downloads. A reply is sent over the same channel.\n        this.electron.on(\"userAccessToken\", () => {\n            this.electron.send(\"userAccessToken\", MatrixClientPeg.get()?.getAccessToken());\n        });\n\n        // `homeserverUrl` (IPC) is requested by the main process. A reply is sent over the same channel.\n        this.electron.on(\"homeserverUrl\", () => {\n            this.electron.send(\"homeserverUrl\", MatrixClientPeg.get()?.getHomeserverUrl());\n        });\n\n        // `serverSupportedVersions` is requested by the main process when it needs to know if the\n        // server supports a particular version. This is primarily used to detect authenticated media\n        // support. A reply is sent over the same channel.\n        this.electron.on(\"serverSupportedVersions\", async () => {\n            this.electron.send(\"serverSupportedVersions\", await MatrixClientPeg.get()?.getVersions());\n        });\n\n        // try to flush the rageshake logs to indexeddb before quit.\n        this.electron.on(\"before-quit\", function () {\n            logger.log(\"element-desktop closing\");\n            rageshake.flush();\n        });\n\n        this.electron.on(\"update-downloaded\", this.onUpdateDownloaded);\n\n        this.electron.on(\"preferences\", () => {\n            dis.fire(Action.ViewUserSettings);\n        });\n\n        this.electron.on(\"userDownloadCompleted\", (ev, { id, name }) => {\n            const key = `DOWNLOAD_TOAST_${id}`;\n\n            const onAccept = (): void => {\n                this.electron.send(\"userDownloadAction\", { id, open: true });\n                ToastStore.sharedInstance().dismissToast(key);\n            };\n\n            const onDismiss = (): void => {\n                this.electron.send(\"userDownloadAction\", { id });\n            };\n\n            ToastStore.sharedInstance().addOrReplaceToast({\n                key,\n                title: _t(\"download_completed\"),\n                props: {\n                    description: name,\n                    primaryLabel: _t(\"action|open\"),\n                    onPrimaryClick: onAccept,\n                    dismissLabel: _t(\"action|dismiss\"),\n                    onDismiss,\n                    numSeconds: 10,\n                },\n                component: GenericExpiringToast,\n                priority: 99,\n            });\n        });\n\n        this.electron.on(\"openDesktopCapturerSourcePicker\", async () => {\n            const { finished } = Modal.createDialog(DesktopCapturerSourcePicker);\n            const [source] = await finished;\n            // getDisplayMedia promise does not return if no dummy is passed here as source\n            await this.ipc.call(\"callDisplayMediaCallback\", source ?? { id: \"\", name: \"\", thumbnailURL: \"\" });\n        });\n\n        this.electron.on(\"showToast\", async (ev, { title, description, priority = 40 }) => {\n            await this.clientStartedPromiseWithResolvers.promise;\n\n            const key = uniqueId(\"electron_showToast_\");\n            const onPrimaryClick = (): void => {\n                ToastStore.sharedInstance().dismissToast(key);\n            };\n\n            ToastStore.sharedInstance().addOrReplaceToast({\n                key,\n                title,\n                props: {\n                    description,\n                    primaryLabel: _t(\"action|dismiss\"),\n                    onPrimaryClick,\n                },\n                component: GenericToast,\n                priority,\n            });\n        });\n\n        BreadcrumbsStore.instance.on(UPDATE_EVENT, this.onBreadcrumbsUpdate);\n\n        this.initialised = this.initialise();\n    }\n\n    protected onAction(payload: ActionPayload): void {\n        super.onAction(payload);\n        // Whitelist payload actions, no point sending most across\n        if ([\"call_state\"].includes(payload.action)) {\n            this.electron.send(\"app_onAction\", payload);\n        }\n\n        if (payload.action === Action.ClientStarted) {\n            this.clientStartedPromiseWithResolvers.resolve();\n        }\n    }\n\n    private async initialise(): Promise<void> {\n        const { protocol, sessionId, config, supportedSettings, supportsBadgeOverlay } =\n            await this.electron.initialise();\n        this.protocol = protocol;\n        this.sessionId = sessionId;\n        this.config = config;\n        this.supportedSettings = supportedSettings;\n        if (supportsBadgeOverlay) {\n            this.badgeOverlayRenderer = new BadgeOverlayRenderer();\n        }\n    }\n\n    public async getConfig(): Promise<IConfigOptions | undefined> {\n        await this.initialised;\n        return this.config;\n    }\n\n    private onBreadcrumbsUpdate = (): void => {\n        const rooms = BreadcrumbsStore.instance.rooms.slice(0, 7).map((r) => ({\n            roomId: r.roomId,\n            avatarUrl: avatarUrlForRoom(\n                r,\n                Math.floor(60 * window.devicePixelRatio),\n                Math.floor(60 * window.devicePixelRatio),\n                \"crop\",\n            ),\n            initial: getInitialLetter(r.name),\n        }));\n        void this.ipc.call(\"breadcrumbs\", rooms);\n    };\n\n    private onUpdateDownloaded = async (ev: Event, { releaseNotes, releaseName }: SquirrelUpdate): Promise<void> => {\n        dis.dispatch<CheckUpdatesPayload>({\n            action: Action.CheckUpdates,\n            status: UpdateCheckStatus.Ready,\n        });\n        if (this.shouldShowUpdate(releaseName)) {\n            showUpdateToast(await this.getAppVersion(), releaseName, releaseNotes);\n        }\n    };\n\n    public getHumanReadableName(): string {\n        return \"Electron Platform\"; // no translation required: only used for analytics\n    }\n\n    /**\n     * Return true if platform supports multi-language\n     * spell-checking, otherwise false.\n     */\n    public supportsSpellCheckSettings(): boolean {\n        return true;\n    }\n\n    public allowOverridingNativeContextMenus(): boolean {\n        return true;\n    }\n\n    public setNotificationCount(count: number): void {\n        if (this.notificationCount === count) return;\n        super.setNotificationCount(count);\n        if (this.badgeOverlayRenderer) {\n            this.badgeOverlayRenderer\n                .render(count)\n                .then((buffer) => {\n                    this.electron.send(\"setBadgeCount\", count, buffer);\n                })\n                .catch((ex) => {\n                    logger.warn(\"Unable to generate badge overlay\", ex);\n                });\n        } else {\n            this.electron.send(\"setBadgeCount\", count);\n        }\n    }\n\n    public setErrorStatus(errorDidOccur: boolean): void {\n        if (!this.badgeOverlayRenderer) {\n            super.setErrorStatus(errorDidOccur);\n            return;\n        }\n        // Check before calling super so we don't override the previous state.\n        if (this.errorDidOccur !== errorDidOccur) {\n            super.setErrorStatus(errorDidOccur);\n            let promise: Promise<ArrayBuffer | null>;\n            if (errorDidOccur) {\n                promise = this.badgeOverlayRenderer.render(this.notificationCount || \"×\", \"#f00\");\n            } else {\n                promise = this.badgeOverlayRenderer.render(this.notificationCount);\n            }\n            promise\n                .then((buffer) => {\n                    this.electron.send(\"setBadgeCount\", this.notificationCount, buffer, errorDidOccur);\n                })\n                .catch((ex) => {\n                    logger.warn(\"Unable to generate badge overlay\", ex);\n                });\n        }\n    }\n\n    public supportsNotifications(): boolean {\n        return true;\n    }\n\n    public maySendNotifications(): boolean {\n        return true;\n    }\n\n    public displayNotification(\n        title: string,\n        msg: string,\n        avatarUrl: string,\n        room: Room,\n        ev?: MatrixEvent,\n    ): Notification {\n        // GNOME notification spec parses HTML tags for styling...\n        // Electron Docs state all supported linux notification systems follow this markup spec\n        // https://github.com/electron/electron/blob/master/docs/tutorial/desktop-environment-integration.md#linux\n        // maybe we should pass basic styling (italics, bold, underline) through from MD\n        // we only have to strip out < and > as the spec doesn't include anything about things like &amp;\n        // so we shouldn't assume that all implementations will treat those properly. Very basic tag parsing is done.\n        if (navigator.userAgent.includes(\"Linux\")) {\n            msg = msg.replace(/</g, \"&lt;\").replace(/>/g, \"&gt;\");\n        }\n\n        const notification = super.displayNotification(title, msg, avatarUrl, room, ev);\n\n        const handler = notification.onclick as () => void;\n        notification.onclick = (): void => {\n            handler?.();\n            void this.ipc.call(\"focusWindow\");\n        };\n\n        return notification;\n    }\n\n    public loudNotification(ev: MatrixEvent, room: Room): void {\n        this.electron.send(\"loudNotification\");\n    }\n\n    public needsUrlTooltips(): boolean {\n        return true;\n    }\n\n    public async getAppVersion(): Promise<string> {\n        return this.ipc.call(\"getAppVersion\");\n    }\n\n    public supportsSetting(settingName?: string): boolean {\n        if (settingName === undefined) return true;\n        return this.supportedSettings?.[settingName] === true;\n    }\n\n    public async getSettingValue(settingName: string): Promise<any> {\n        await this.initialised;\n        return this.electron.getSettingValue(settingName);\n    }\n\n    public async setSettingValue(settingName: string, value: any): Promise<void> {\n        await this.initialised;\n        return this.electron.setSettingValue(settingName, value);\n    }\n\n    public async canSelfUpdate(): Promise<boolean> {\n        const feedUrl = await this.ipc.call(\"getUpdateFeedUrl\");\n        return Boolean(feedUrl);\n    }\n\n    public startUpdateCheck(): void {\n        super.startUpdateCheck();\n        this.electron.send(\"check_updates\");\n    }\n\n    public installUpdate(): void {\n        // IPC to the main process to install the update, since quitAndInstall\n        // doesn't fire the before-quit event so the main process needs to know\n        // it should exit.\n        this.electron.send(\"install_update\");\n    }\n\n    public getDefaultDeviceDisplayName(): string {\n        const brand = SdkConfig.get().brand;\n        return _t(\"desktop_default_device_name\", {\n            brand,\n            platformName: platformFriendlyName(),\n        });\n    }\n\n    public requestNotificationPermission(): Promise<string> {\n        return Promise.resolve(\"granted\");\n    }\n\n    public reload(): void {\n        window.location.reload();\n    }\n\n    public getEventIndexingManager(): BaseEventIndexManager | null {\n        return this.eventIndexManager;\n    }\n\n    public async setLanguage(preferredLangs: string[]): Promise<any> {\n        return this.ipc.call(\"setLanguage\", preferredLangs);\n    }\n\n    public setSpellCheckEnabled(enabled: boolean): void {\n        this.ipc.call(\"setSpellCheckEnabled\", enabled).catch((error) => {\n            logger.log(\"Failed to send setSpellCheckEnabled IPC to Electron\");\n            logger.error(error);\n        });\n    }\n\n    public async getSpellCheckEnabled(): Promise<boolean> {\n        return this.ipc.call(\"getSpellCheckEnabled\");\n    }\n\n    public setSpellCheckLanguages(preferredLangs: string[]): void {\n        this.ipc.call(\"setSpellCheckLanguages\", preferredLangs).catch((error) => {\n            logger.log(\"Failed to send setSpellCheckLanguages IPC to Electron\");\n            logger.error(error);\n        });\n    }\n\n    public async getSpellCheckLanguages(): Promise<string[]> {\n        return this.ipc.call(\"getSpellCheckLanguages\");\n    }\n\n    public async getDesktopCapturerSources(options: GetSourcesOptions): Promise<Array<DesktopCapturerSource>> {\n        return this.ipc.call(\"getDesktopCapturerSources\", options);\n    }\n\n    public supportsDesktopCapturer(): boolean {\n        return true;\n    }\n\n    public supportsJitsiScreensharing(): boolean {\n        // See https://github.com/element-hq/element-web/issues/4880\n        return false;\n    }\n\n    public async getAvailableSpellCheckLanguages(): Promise<string[]> {\n        return this.ipc.call(\"getAvailableSpellCheckLanguages\");\n    }\n\n    public getSSOCallbackUrl(fragmentAfterLogin?: string): URL {\n        const url = super.getSSOCallbackUrl(fragmentAfterLogin);\n        url.protocol = \"element\";\n        url.searchParams.set(SSO_ID_KEY, this.sessionId);\n        return url;\n    }\n\n    public startSingleSignOn(\n        mxClient: MatrixClient,\n        loginType: \"sso\" | \"cas\",\n        fragmentAfterLogin: string,\n        idpId?: string,\n    ): void {\n        // this will get intercepted by electron-main will-navigate\n        super.startSingleSignOn(mxClient, loginType, fragmentAfterLogin, idpId);\n        Modal.createDialog(InfoDialog, {\n            title: _t(\"auth|sso_complete_in_browser_dialog_title\"),\n            description: <Spinner />,\n        });\n    }\n\n    public navigateForwardBack(back: boolean): void {\n        void this.ipc.call(back ? \"navigateBack\" : \"navigateForward\");\n    }\n\n    public overrideBrowserShortcuts(): boolean {\n        return true;\n    }\n\n    public async getPickleKey(userId: string, deviceId: string): Promise<string | null> {\n        try {\n            return await this.ipc.call(\"getPickleKey\", userId, deviceId);\n        } catch {\n            // if we can't connect to the password storage, assume there's no\n            // pickle key\n            return null;\n        }\n    }\n\n    public async createPickleKey(userId: string, deviceId: string): Promise<string | null> {\n        try {\n            return await this.ipc.call(\"createPickleKey\", userId, deviceId);\n        } catch {\n            // if we can't connect to the password storage, assume there's no\n            // pickle key\n            return null;\n        }\n    }\n\n    public async destroyPickleKey(userId: string, deviceId: string): Promise<void> {\n        try {\n            await this.ipc.call(\"destroyPickleKey\", userId, deviceId);\n        } catch {}\n    }\n\n    public async clearStorage(): Promise<void> {\n        try {\n            await super.clearStorage();\n            await this.ipc.call(\"clearStorage\");\n        } catch {}\n    }\n\n    public get baseUrl(): string {\n        // This configuration is element-desktop specific so the types here do not know about it\n        return (SdkConfig.get() as unknown as Record<string, string>)[\"web_base_url\"] ?? \"https://app.element.io\";\n    }\n\n    public get defaultOidcClientUri(): string {\n        // Default to element.io as our scheme `io.element.desktop` is within its scope on default MAS policies\n        return \"https://element.io\";\n    }\n\n    public async getOidcClientMetadata(): Promise<OidcRegistrationClientMetadata> {\n        const baseMetadata = await super.getOidcClientMetadata();\n        return {\n            ...baseMetadata,\n            applicationType: \"native\",\n        };\n    }\n\n    public getOidcClientState(): string {\n        return `:${SSO_ID_KEY}:${this.sessionId}`;\n    }\n\n    /**\n     * The URL to return to after a successful OIDC authentication\n     */\n    public getOidcCallbackUrl(): URL {\n        const url = super.getOidcCallbackUrl();\n        url.protocol = this.protocol;\n        // Trim the double slash into a single slash to comply with https://datatracker.ietf.org/doc/html/rfc8252#section-7.1\n        if (url.href.startsWith(`${url.protocol}//`)) {\n            url.href = url.href.replace(\"://\", \":/\");\n        }\n        return url;\n    }\n\n    public checkSessionLockFree(): boolean {\n        return true;\n    }\n\n    public async getSessionLock(_onNewInstance: () => Promise<void>): Promise<boolean> {\n        return true;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2023 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { v4 as uuidv4 } from \"uuid\";\n\n/*\n * Functionality for checking that only one instance is running at once\n *\n * The algorithm here is twofold.\n *\n * First, we \"claim\" a lock by periodically writing to `STORAGE_ITEM_PING`. On shutdown, we clear that item. So,\n * a new instance starting up can check if the lock is free by inspecting `STORAGE_ITEM_PING`. If it is unset,\n * or is stale, the new instance can assume the lock is free and claim it for itself. Otherwise, the new instance\n * has to wait for the ping to be stale, or the item to be cleared.\n *\n * Secondly, we need a mechanism for proactively telling existing instances to shut down. We do this by writing a\n * unique value to `STORAGE_ITEM_CLAIMANT`. Other instances of the app are supposed to monitor for writes to\n * `STORAGE_ITEM_CLAIMANT` and initiate shutdown when it happens.\n *\n * There is slight complexity in `STORAGE_ITEM_CLAIMANT` in that we need to watch out for yet another instance\n * starting up and staking a claim before we even get a chance to take the lock. When that happens we just bail out\n * and let the newer instance get the lock.\n *\n * `STORAGE_ITEM_OWNER` has no functional role in the lock mechanism; it exists solely as a diagnostic indicator\n * of which instance is writing to `STORAGE_ITEM_PING`.\n */\n\nexport const SESSION_LOCK_CONSTANTS = {\n    /**\n     * LocalStorage key for an item which indicates we have the lock.\n     *\n     * The instance which holds the lock writes the current time to this key every few seconds, to indicate it is still\n     * alive and holds the lock.\n     */\n    STORAGE_ITEM_PING: \"react_sdk_session_lock_ping\",\n\n    /**\n     * LocalStorage key for an item which holds the unique \"session ID\" of the instance which currently holds the lock.\n     *\n     * This property doesn't actually form a functional part of the locking algorithm; it is purely diagnostic.\n     */\n    STORAGE_ITEM_OWNER: \"react_sdk_session_lock_owner\",\n\n    /**\n     * LocalStorage key for the session ID of the most recent claimant to the lock.\n     *\n     * Each instance writes to this key on startup, so existing instances can detect new ones starting up.\n     */\n    STORAGE_ITEM_CLAIMANT: \"react_sdk_session_lock_claimant\",\n\n    /**\n     * The number of milliseconds after which we consider a lock claim stale\n     */\n    LOCK_EXPIRY_TIME_MS: 15000,\n};\n\n/**\n * See if any instances are currently running\n *\n * @returns true if any instance is currently active\n */\nexport function checkSessionLockFree(): boolean {\n    const prefixedLogger = logger.getChild(`checkSessionLockFree`);\n\n    const lastPingTime = window.localStorage.getItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_PING);\n    if (lastPingTime === null) {\n        // no other holder\n        prefixedLogger.info(\"No other session has the lock\");\n        return true;\n    }\n\n    const lockHolder = window.localStorage.getItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_OWNER);\n\n    // see if it has expired\n    const timeAgo = Date.now() - parseInt(lastPingTime);\n\n    const remaining = SESSION_LOCK_CONSTANTS.LOCK_EXPIRY_TIME_MS - timeAgo;\n    if (remaining <= 0) {\n        // another session claimed the lock, but it is stale.\n        prefixedLogger.info(`Last ping (from ${lockHolder}) was ${timeAgo}ms ago: lock is free`);\n        return true;\n    }\n\n    prefixedLogger.info(`Last ping (from ${lockHolder}) was ${timeAgo}ms ago: lock is taken`);\n    return false;\n}\n\n/**\n * Ensure that only one instance of the application is running at once.\n *\n * If there are any other running instances, tells them to stop, and waits for them to do so.\n *\n * Once we are the sole instance, sets a background job going to service a lock. Then, if another instance starts up,\n * `onNewInstance` is called: it should shut the app down to make sure we aren't doing any more work.\n *\n * @param onNewInstance - callback to handle another instance starting up. NOTE: this may be called before\n *     `getSessionLock` returns if the lock is stolen before we get a chance to start.\n *\n * @returns true if we successfully claimed the lock; false if another instance stole it from under our nose\n *     (in which `onNewInstance` will have been called)\n */\nexport async function getSessionLock(onNewInstance: () => Promise<void>): Promise<boolean> {\n    /** unique ID for this session */\n    const sessionIdentifier = uuidv4();\n\n    const prefixedLogger = logger.getChild(`getSessionLock[${sessionIdentifier}]`);\n\n    /** The ID of our regular task to service the lock.\n     *\n     * Non-null while we hold the lock; null if we have not yet claimed it, or have released it. */\n    let lockServicer: number | null = null;\n\n    /**\n     * See if the lock is free.\n     *\n     * @returns\n     *  - `>0`: the number of milliseconds before the current claim on the lock can be considered stale.\n     *  - `0`: the lock is free for the taking\n     *  - `<0`: someone else has staked a claim for the lock, so we are no longer in line for it.\n     */\n    function checkLock(): number {\n        // first of all, check that we are still the active claimant (ie, another instance hasn't come along while we were waiting.\n        const claimant = window.localStorage.getItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_CLAIMANT);\n        if (claimant !== sessionIdentifier) {\n            prefixedLogger.warn(`Lock was claimed by ${claimant} while we were waiting for it: aborting startup`);\n            return -1;\n        }\n\n        const lastPingTime = window.localStorage.getItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_PING);\n        const lockHolder = window.localStorage.getItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_OWNER);\n        if (lastPingTime === null) {\n            prefixedLogger.info(\"No other session has the lock: proceeding with startup\");\n            return 0;\n        }\n\n        const timeAgo = Date.now() - parseInt(lastPingTime);\n        // If the last ping time is in the future (i.e., timeAgo is negative), the chances are that the system clock has\n        // been wound back since the ping. Rather than waiting hours/days/millenia for us to get there, treat a future\n        // ping as \"just now\" by clipping to 0.\n        const remaining = SESSION_LOCK_CONSTANTS.LOCK_EXPIRY_TIME_MS - Math.max(timeAgo, 0);\n        if (remaining <= 0) {\n            // another session claimed the lock, but it is stale.\n            prefixedLogger.info(`Last ping (from ${lockHolder}) was ${timeAgo}ms ago: proceeding with startup`);\n            return 0;\n        }\n\n        prefixedLogger.info(`Last ping (from ${lockHolder}) was ${timeAgo}ms ago, waiting ${remaining}ms`);\n        return remaining;\n    }\n\n    function serviceLock(): void {\n        window.localStorage.setItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_OWNER, sessionIdentifier);\n        window.localStorage.setItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_PING, Date.now().toString());\n    }\n\n    // handler for storage events, used later\n    function onStorageEvent(event: StorageEvent): void {\n        if (event.key === SESSION_LOCK_CONSTANTS.STORAGE_ITEM_CLAIMANT) {\n            // It's possible that the event was delayed, and this update actually predates our claim on the lock.\n            // (In particular: suppose tab A and tab B start concurrently and both attempt to set STORAGE_ITEM_CLAIMANT.\n            // Each write queues up a `storage` event for all other tabs. So both tabs see the `storage` event from the\n            // other, even though by the time it arrives we may have overwritten it.)\n            //\n            // To resolve any doubt, we check the *actual* state of the storage.\n            const claimingSession = window.localStorage.getItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_CLAIMANT);\n            if (claimingSession === sessionIdentifier) {\n                return;\n            }\n            prefixedLogger.info(`Session ${claimingSession} is waiting for the lock`);\n            window.removeEventListener(\"storage\", onStorageEvent);\n            releaseLock().catch((err) => {\n                prefixedLogger.error(\"Error releasing session lock\", err);\n            });\n        }\n    }\n\n    // handler for pagehide and unload events, used later\n    function onPagehideEvent(): void {\n        // only remove the ping if we still think we're the owner. Otherwise we could be removing someone else's claim!\n        if (lockServicer !== null) {\n            prefixedLogger.debug(\"page hide: clearing our claim\");\n            window.clearInterval(lockServicer);\n            window.localStorage.removeItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_PING);\n            window.localStorage.removeItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_OWNER);\n            lockServicer = null;\n        }\n\n        // It's worth noting that, according to the spec, the page might come back to life again after a pagehide.\n        //\n        // In practice that's unlikely because Element is unlikely to qualify for the bfcache, but if it does,\n        // this is probably the best we can do: we certainly don't want to stop the user loading any new tabs because\n        // Element happens to be in a bfcache somewhere.\n        //\n        // So, we just hope that we aren't in the middle of any crypto operations, and rely on `onStorageEvent` kicking\n        // in soon enough after we resume to tell us if another tab woke up while we were asleep.\n    }\n\n    async function releaseLock(): Promise<void> {\n        // tell the app to shut down\n        await onNewInstance();\n\n        // and, once it has done so, stop pinging the lock.\n        if (lockServicer !== null) {\n            window.clearInterval(lockServicer);\n        }\n        window.localStorage.removeItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_PING);\n        window.localStorage.removeItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_OWNER);\n        lockServicer = null;\n    }\n\n    // first of all, stake a claim for the lock. This tells anyone else holding the lock that we want it.\n    window.localStorage.setItem(SESSION_LOCK_CONSTANTS.STORAGE_ITEM_CLAIMANT, sessionIdentifier);\n\n    // now, wait for the lock to be free.\n    // eslint-disable-next-line no-constant-condition\n    while (true) {\n        const remaining = checkLock();\n\n        if (remaining == 0) {\n            // ok, the lock is free, and nobody else has staked a more recent claim.\n            break;\n        } else if (remaining < 0) {\n            // someone else staked a claim for the lock; we bail out.\n            await onNewInstance();\n            return false;\n        }\n\n        // someone else has the lock.\n        // wait for either the ping to expire, or a storage event.\n        let onStorageUpdate: (event: StorageEvent) => void;\n\n        const storageUpdatePromise = new Promise((resolve) => {\n            onStorageUpdate = (event: StorageEvent) => {\n                if (\n                    event.key === SESSION_LOCK_CONSTANTS.STORAGE_ITEM_PING ||\n                    event.key === SESSION_LOCK_CONSTANTS.STORAGE_ITEM_CLAIMANT\n                )\n                    resolve(event);\n            };\n        });\n\n        // We construct our own promise here rather than using the `sleep` utility, to make it easier to test the\n        // SessionLock in a separate Window.\n        const sleepPromise = new Promise((resolve) => {\n            setTimeout(resolve, remaining, undefined);\n        });\n\n        window.addEventListener(\"storage\", onStorageUpdate!);\n        const winner = await Promise.race([sleepPromise, storageUpdatePromise]);\n        window.removeEventListener(\"storage\", onStorageUpdate!);\n\n        // If we got through the whole of the sleep without any writes to the store, we know that the\n        // ping is now stale. There's no point in going round and calling `checkLock` again: we know that\n        // nothing has changed since last time.\n        if (!(winner instanceof StorageEvent)) {\n            prefixedLogger.info(\"Existing claim went stale: proceeding with startup\");\n            break;\n        }\n    }\n\n    // If we get here, we know the lock is ours for the taking.\n\n    // CRITICAL SECTION\n    //\n    // The following code, up to the end of the function, must all be synchronous (ie, no `await` calls), to ensure that\n    // we get our listeners in place and all the writes to localStorage done before other tabs run again.\n\n    // claim the lock, and kick off a background process to service it every 5 seconds\n    serviceLock();\n    lockServicer = window.setInterval(serviceLock, 5000);\n\n    // Now add a listener for other claimants to the lock.\n    window.addEventListener(\"storage\", onStorageEvent);\n\n    // also add a listener to clear our claims when our tab closes or navigates away\n    window.addEventListener(\"pagehide\", onPagehideEvent);\n\n    // The pagehide event is called unreliably on Firefox, so additionally add an unload handler.\n    // https://bugzilla.mozilla.org/show_bug.cgi?id=1854492\n    window.addEventListener(\"unload\", onPagehideEvent);\n\n    return true;\n}\n","/*\nCopyright 2017-2024 New Vector Ltd.\nCopyright 2016 Aviral Dasgupta\nCopyright 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport UAParser from \"ua-parser-js\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport { MatrixClientPeg } from \"../../MatrixClientPeg\";\nimport BasePlatform, { UpdateCheckStatus, type UpdateStatus } from \"../../BasePlatform\";\nimport dis from \"../../dispatcher/dispatcher\";\nimport { hideToast as hideUpdateToast, showToast as showUpdateToast } from \"../../toasts/UpdateToast\";\nimport { Action } from \"../../dispatcher/actions\";\nimport { type CheckUpdatesPayload } from \"../../dispatcher/payloads/CheckUpdatesPayload\";\nimport { parseQs } from \"../url_utils\";\nimport { _t } from \"../../languageHandler\";\nimport ToastStore from \"../../stores/ToastStore.ts\";\nimport GenericToast from \"../../components/views/toasts/GenericToast.tsx\";\nimport SdkConfig from \"../../SdkConfig.ts\";\nimport type { ActionPayload } from \"../../dispatcher/payloads.ts\";\nimport * as SessionLock from \"../../utils/SessionLock.ts\";\n\nconst POKE_RATE_MS = 10 * 60 * 1000; // 10 min\n\nfunction getNormalizedAppVersion(version: string): string {\n    // if version looks like semver with leading v, strip it (matches scripts/normalize-version.sh)\n    const semVerRegex = /^v\\d+.\\d+.\\d+(-.+)?$/;\n    if (semVerRegex.test(version)) {\n        return version.substring(1);\n    }\n    return version;\n}\n\nexport default class WebPlatform extends BasePlatform {\n    private static readonly VERSION = process.env.VERSION!; // baked in by Webpack\n    private readonly registerServiceWorkerPromise: Promise<void>;\n\n    public constructor() {\n        super();\n\n        // Register the service worker in the background\n        this.registerServiceWorkerPromise = this.registerServiceWorker();\n        this.registerServiceWorkerPromise.catch((e) => {\n            console.error(\"Error registering/updating service worker:\", e);\n        });\n    }\n\n    protected onAction(payload: ActionPayload): void {\n        super.onAction(payload);\n\n        switch (payload.action) {\n            case Action.ClientStarted:\n                // Defer drawing the toast until the client is started as the lifecycle methods reset the ToastStore right before\n                this.registerServiceWorkerPromise.catch(this.handleServiceWorkerRegistrationError);\n                break;\n        }\n    }\n\n    private async registerServiceWorker(): Promise<void> {\n        // sw.js is exported by webpack, sourced from `/src/serviceworker/index.ts`\n        const registration = await navigator.serviceWorker.register(\"sw.js\");\n        if (!registration) {\n            throw new Error(\"Service worker registration failed\");\n        }\n\n        navigator.serviceWorker.addEventListener(\"message\", this.onServiceWorkerPostMessage);\n        await registration.update();\n    }\n\n    private handleServiceWorkerRegistrationError = (): void => {\n        const key = \"service_worker_error\";\n        const brand = SdkConfig.get().brand;\n        ToastStore.sharedInstance().addOrReplaceToast({\n            key,\n            title: _t(\"service_worker_error|title\"),\n            props: {\n                description: _t(\"service_worker_error|description\", { brand }),\n                primaryLabel: _t(\"action|ok\"),\n                onPrimaryClick: () => {\n                    ToastStore.sharedInstance().dismissToast(key);\n                },\n            },\n            component: GenericToast,\n            priority: 95,\n        });\n    };\n\n    private onServiceWorkerPostMessage = (event: MessageEvent): void => {\n        try {\n            if (event.data?.[\"type\"] === \"userinfo\" && event.data?.[\"responseKey\"]) {\n                const userId = localStorage.getItem(\"mx_user_id\");\n                const deviceId = localStorage.getItem(\"mx_device_id\");\n                const homeserver = MatrixClientPeg.get()?.getHomeserverUrl();\n                event.source!.postMessage({\n                    responseKey: event.data[\"responseKey\"],\n                    userId,\n                    deviceId,\n                    homeserver,\n                });\n            }\n        } catch (e) {\n            console.error(\"Error responding to service worker: \", e);\n        }\n    };\n\n    public getHumanReadableName(): string {\n        return \"Web Platform\"; // no translation required: only used for analytics\n    }\n\n    /**\n     * Returns true if the platform supports displaying\n     * notifications, otherwise false.\n     */\n    public supportsNotifications(): boolean {\n        return Boolean(window.Notification);\n    }\n\n    /**\n     * Returns true if the application currently has permission\n     * to display notifications. Otherwise false.\n     */\n    public maySendNotifications(): boolean {\n        return window.Notification.permission === \"granted\";\n    }\n\n    /**\n     * Requests permission to send notifications. Returns\n     * a promise that is resolved when the user has responded\n     * to the request. The promise has a single string argument\n     * that is 'granted' if the user allowed the request or\n     * 'denied' otherwise.\n     */\n    public requestNotificationPermission(): Promise<string> {\n        // annoyingly, the latest spec says this returns a\n        // promise, but this is only supported in Chrome 46\n        // and Firefox 47, so adapt the callback API.\n        return new Promise(function (resolve, reject) {\n            window.Notification.requestPermission((result) => {\n                resolve(result);\n            }).catch(reject);\n        });\n    }\n\n    private async getMostRecentVersion(): Promise<string> {\n        const res = await fetch(\"version\", {\n            method: \"GET\",\n            cache: \"no-cache\",\n        });\n\n        if (res.ok) {\n            const text = await res.text();\n            return getNormalizedAppVersion(text.trim());\n        }\n\n        return Promise.reject({ status: res.status });\n    }\n\n    public getAppVersion(): Promise<string> {\n        return Promise.resolve(getNormalizedAppVersion(WebPlatform.VERSION));\n    }\n\n    public startUpdater(): void {\n        // Poll for an update immediately, and reload the page now if we're out of date\n        // already as we've just initialised an old version of the app somehow.\n        //\n        // Forcibly reloading the page aims to avoid users interacting at all with the old\n        // and potentially broken version of the app.\n        //\n        // Ideally, loading an old copy would be impossible with the\n        // cache-control: nocache HTTP header set, but Firefox doesn't always obey it :/\n        console.log(\"startUpdater, current version is \" + getNormalizedAppVersion(WebPlatform.VERSION));\n        void this.pollForUpdate((version: string, newVersion: string) => {\n            const query = parseQs(location);\n            if (query.updated) {\n                console.log(\"Update reloaded but still on an old version, stopping\");\n                // We just reloaded already and are still on the old version!\n                // Show the toast rather than reload in a loop.\n                showUpdateToast(version, newVersion);\n                return;\n            }\n\n            // Set updated as a cachebusting query param and reload the page.\n            const url = new URL(window.location.href);\n            url.searchParams.set(\"updated\", newVersion);\n            console.log(\"Update reloading to \" + url.toString());\n            window.location.href = url.toString();\n        });\n        setInterval(() => this.pollForUpdate(showUpdateToast, hideUpdateToast), POKE_RATE_MS);\n    }\n\n    public async canSelfUpdate(): Promise<boolean> {\n        return true;\n    }\n\n    // Exported for tests\n    public pollForUpdate = (\n        showUpdate: (currentVersion: string, mostRecentVersion: string) => void,\n        showNoUpdate?: () => void,\n    ): Promise<UpdateStatus> => {\n        return this.getMostRecentVersion().then(\n            (mostRecentVersion) => {\n                const currentVersion = getNormalizedAppVersion(WebPlatform.VERSION);\n\n                if (currentVersion !== mostRecentVersion) {\n                    if (this.shouldShowUpdate(mostRecentVersion)) {\n                        console.log(\"Update available to \" + mostRecentVersion + \", will notify user\");\n                        showUpdate(currentVersion, mostRecentVersion);\n                    } else {\n                        console.log(\"Update available to \" + mostRecentVersion + \" but won't be shown\");\n                    }\n                    return { status: UpdateCheckStatus.Ready };\n                } else {\n                    console.log(\"No update available, already on \" + mostRecentVersion);\n                    showNoUpdate?.();\n                }\n\n                return { status: UpdateCheckStatus.NotAvailable };\n            },\n            (err) => {\n                logger.error(\"Failed to poll for update\", err);\n                return {\n                    status: UpdateCheckStatus.Error,\n                    detail: err.message || (err.status ? err.status.toString() : \"Unknown Error\"),\n                };\n            },\n        );\n    };\n\n    public startUpdateCheck(): void {\n        super.startUpdateCheck();\n        void this.pollForUpdate(showUpdateToast, hideUpdateToast).then((updateState) => {\n            dis.dispatch<CheckUpdatesPayload>({\n                action: Action.CheckUpdates,\n                ...updateState,\n            });\n        });\n    }\n\n    public installUpdate(): void {\n        window.location.reload();\n    }\n\n    public getDefaultDeviceDisplayName(): string {\n        // strip query-string and fragment from uri\n        const url = new URL(window.location.href);\n\n        // `appName` in the format `develop.element.io/abc/xyz`\n        const appName = [\n            url.host,\n            url.pathname.replace(/\\/$/, \"\"), // Remove trailing slash if present\n        ].join(\"\");\n\n        const ua = new UAParser();\n        const browserName = ua.getBrowser().name || \"unknown browser\";\n        let osName = ua.getOS().name || \"unknown OS\";\n        // Stylise the value from the parser to match Apple's current branding.\n        if (osName === \"Mac OS\") osName = \"macOS\";\n        return _t(\"web_default_device_name\", {\n            appName,\n            browserName,\n            osName,\n        });\n    }\n\n    public reload(): void {\n        window.location.reload();\n    }\n\n    public checkSessionLockFree(): boolean {\n        return SessionLock.checkSessionLockFree();\n    }\n\n    public async getSessionLock(onNewInstance: () => Promise<void>): Promise<boolean> {\n        return SessionLock.getSessionLock(onNewInstance);\n    }\n}\n","/*\nCopyright 2020-2024 New Vector Ltd.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport WebPlatform from \"./WebPlatform\";\n\nexport default class PWAPlatform extends WebPlatform {\n    public setNotificationCount(count: number): void {\n        if (!navigator.setAppBadge) return super.setNotificationCount(count);\n        if (this.notificationCount === count) return;\n        this.notificationCount = count;\n\n        navigator.setAppBadge(count).catch((e) => {\n            logger.error(\"Failed to update PWA app badge\", e);\n        });\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\nCopyright 2018 New Vector Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n/*\n * Separate file that sets up rageshake logging when imported.\n * This is necessary so that rageshake logging is set up before\n * anything else. Webpack puts all import statements at the top\n * of the file before any code, so imports will always be\n * evaluated first. Other imports can cause other code to be\n * evaluated (eg. the loglevel library in js-sdk, which if set\n * up before rageshake causes some js-sdk logging to be missing\n * from the rageshake.)\n */\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\n\nimport * as rageshake from \"../rageshake/rageshake\";\nimport SdkConfig from \"../SdkConfig\";\nimport sendBugReport, { loadBugReport } from \"../rageshake/submit-rageshake\";\nimport { BugReportEndpointURLLocal } from \"../IConfigOptions\";\n\nexport function initRageshake(): Promise<void> {\n    // we manually check persistence for rageshakes ourselves\n    const prom = rageshake.init(/*setUpPersistence=*/ false);\n    prom.then(\n        async () => {\n            logger.log(\"Initialised rageshake.\");\n            logger.log(\n                \"To fix line numbers in Chrome: \" +\n                    \"Meatball menu → Settings → Ignore list → Add /rageshake\\\\.ts & /logger\\\\.ts$\",\n            );\n\n            window.addEventListener(\"beforeunload\", () => {\n                logger.log(\"element-web closing\");\n                // try to flush the logs to indexeddb\n                rageshake.flush();\n            });\n\n            await rageshake.cleanup();\n        },\n        (err) => {\n            logger.error(\"Failed to initialise rageshake: \" + err);\n        },\n    );\n    return prom;\n}\n\nexport function initRageshakeStore(): Promise<void> {\n    return rageshake.tryInitStorage();\n}\n\nwindow.mxSendRageshake = async function (text: string, withLogs = true): Promise<void> {\n    const url = SdkConfig.get().bug_report_endpoint_url;\n    if (!url) {\n        logger.error(\"Cannot send a rageshake - no bug_report_endpoint_url configured\");\n        return;\n    }\n\n    if (!text || !text.trim()) {\n        logger.error(\"Cannot send a rageshake without a message - please tell us what went wrong\");\n        return;\n    }\n    if (url === BugReportEndpointURLLocal) {\n        try {\n            const tape = await loadBugReport({\n                userText: text,\n                sendLogs: withLogs,\n                progressCallback: logger.log.bind(console),\n            });\n            const blob = new Blob([new Uint8Array(tape.out)], { type: \"application/gzip\" });\n            const url = URL.createObjectURL(blob);\n            logger.log(`Your logs are available at ${url}`);\n        } catch (err) {\n            logger.error(\"Failed to load bug report\", err);\n        }\n    } else {\n        try {\n            await sendBugReport(url, {\n                userText: text,\n                sendLogs: withLogs,\n                progressCallback: logger.log.bind(console),\n            });\n            logger.log(\"Bug report sent!\");\n        } catch (err) {\n            logger.error(\"Failed to send bug report\", err);\n        }\n    }\n};\n","/*\nCopyright 2018-2024 New Vector Ltd.\nCopyright 2019 Michael Telatynski <7t3chguy@gmail.com>\nCopyright 2017 Vector Creations Ltd\nCopyright 2015, 2016 OpenMarket Ltd\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { createRoot } from \"react-dom/client\";\nimport React, { StrictMode } from \"react\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { ModuleLoader } from \"@element-hq/element-web-module-api\";\n\nimport type { QueryDict } from \"matrix-js-sdk/src/utils\";\nimport * as languageHandler from \"../languageHandler\";\nimport SettingsStore from \"../settings/SettingsStore\";\nimport PlatformPeg from \"../PlatformPeg\";\nimport SdkConfig from \"../SdkConfig\";\nimport { setTheme } from \"../theme\";\nimport { ModuleRunner } from \"../modules/ModuleRunner\";\nimport type MatrixChat from \"../components/structures/MatrixChat\";\nimport ElectronPlatform from \"./platform/ElectronPlatform\";\nimport PWAPlatform from \"./platform/PWAPlatform\";\nimport WebPlatform from \"./platform/WebPlatform\";\nimport { initRageshake, initRageshakeStore } from \"./rageshakesetup\";\nimport { ModuleApi } from \"../modules/Api.ts\";\n\nexport const rageshakePromise = initRageshake();\n\nexport function preparePlatform(): void {\n    if (window.electron) {\n        logger.log(\"Using Electron platform\");\n        PlatformPeg.set(new ElectronPlatform());\n    } else if (window.matchMedia(\"(display-mode: standalone)\").matches) {\n        logger.log(\"Using PWA platform\");\n        PlatformPeg.set(new PWAPlatform());\n    } else {\n        logger.log(\"Using Web platform\");\n        PlatformPeg.set(new WebPlatform());\n    }\n}\n\nexport function setupLogStorage(): Promise<void> {\n    if (SdkConfig.get().bug_report_endpoint_url) {\n        return initRageshakeStore();\n    }\n    logger.warn(\"No bug report endpoint set - logs will not be persisted\");\n    return Promise.resolve();\n}\n\nexport async function loadConfig(): Promise<void> {\n    // XXX: We call this twice, once here and once in MatrixChat as a prop. We call it here to ensure\n    // granular settings are loaded correctly and to avoid duplicating the override logic for the theme.\n    //\n    // Note: this isn't called twice for some wrappers, like the Jitsi wrapper.\n    const platformConfig = await PlatformPeg.get()?.getConfig();\n    if (platformConfig) {\n        SdkConfig.put(platformConfig);\n    } else {\n        SdkConfig.reset();\n    }\n}\n\nexport async function loadLanguage(): Promise<void> {\n    const prefLang = SettingsStore.getValue(\"language\", null, /*excludeDefault=*/ true);\n    let langs: string[] = [];\n\n    if (!prefLang) {\n        languageHandler.getLanguagesFromBrowser().forEach((l) => {\n            langs.push(...languageHandler.getNormalizedLanguageKeys(l));\n        });\n    } else {\n        langs = [prefLang];\n    }\n    try {\n        await languageHandler.setLanguage(...langs);\n        document.documentElement.setAttribute(\"lang\", languageHandler.getCurrentLanguage());\n    } catch (e) {\n        logger.error(\"Unable to set language\", e);\n    }\n}\n\nexport async function loadTheme(): Promise<void> {\n    return setTheme();\n}\n\nexport async function loadApp(fragParams: QueryDict): Promise<void> {\n    // load app.js async so that its code is not executed immediately and we can catch any exceptions\n    const module = await import(\n        /* webpackChunkName: \"element-web-app\" */\n        /* webpackPreload: true */\n        \"./app\"\n    );\n    function setWindowMatrixChat(matrixChat: MatrixChat): void {\n        window.matrixChat = matrixChat;\n    }\n    const app = await module.loadApp(fragParams, setWindowMatrixChat);\n    const root = createRoot(document.getElementById(\"matrixchat\")!);\n    root.render(app);\n}\n\nexport async function showError(title: string, messages?: string[]): Promise<void> {\n    const { ErrorView } = await import(\n        /* webpackChunkName: \"error-view\" */\n        \"../async-components/structures/ErrorView\"\n    );\n    const root = createRoot(document.getElementById(\"matrixchat\")!);\n    root.render(\n        <StrictMode>\n            <ErrorView title={title} messages={messages} />\n        </StrictMode>,\n    );\n}\n\nexport async function showIncompatibleBrowser(onAccept: () => void): Promise<void> {\n    const { UnsupportedBrowserView } = await import(\n        /* webpackChunkName: \"error-view\" */\n        \"../async-components/structures/ErrorView\"\n    );\n    const root = createRoot(document.getElementById(\"matrixchat\")!);\n    root.render(\n        <StrictMode>\n            <UnsupportedBrowserView onAccept={onAccept} />\n        </StrictMode>,\n    );\n}\n\n/**\n * @deprecated in favour of the plugin system\n */\nexport async function loadModules(): Promise<void> {\n    const { INSTALLED_MODULES } = await import(\"../modules.js\");\n    for (const InstalledModule of INSTALLED_MODULES) {\n        ModuleRunner.instance.registerModule((api) => new InstalledModule(api));\n    }\n}\n\nexport async function loadPlugins(): Promise<void> {\n    // Add React to the global namespace, this is part of the new Module API contract to avoid needing\n    // every single module to ship its own copy of React. This also makes it easier to access via the console\n    // and incidentally means we can forget our React imports in JSX files without penalty.\n    window.React = React;\n\n    const modules = SdkConfig.get(\"modules\");\n    if (!modules?.length) return;\n    const moduleLoader = new ModuleLoader(ModuleApi.instance);\n    window.mxModuleLoader = moduleLoader;\n    for (const src of modules) {\n        // We need to instruct webpack to not mangle this import as it is not available at compile time\n        const module = await import(/* webpackIgnore: true */ src);\n        await moduleLoader.load(module);\n    }\n    await moduleLoader.start();\n}\n\nexport { _t } from \"../languageHandler\";\n\nexport { extractErrorMessageFromError } from \"../components/views/dialogs/ErrorDialog\";\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2019, 2020 , 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type User, type MatrixClient, type RoomMember } from \"matrix-js-sdk/src/matrix\";\nimport { type VerificationRequest } from \"matrix-js-sdk/src/crypto-api\";\n\nimport dis from \"./dispatcher/dispatcher\";\nimport { RightPanelPhases } from \"./stores/right-panel/RightPanelStorePhases\";\nimport RightPanelStore from \"./stores/right-panel/RightPanelStore\";\nimport { type IRightPanelCardState } from \"./stores/right-panel/RightPanelStoreIPanelState\";\nimport { findDMForUser } from \"./utils/dm/findDMForUser\";\n\n/**\n * Verify another user.\n *\n * Note: cross-signing must be set up before calling this function.\n */\nexport async function verifyUser(matrixClient: MatrixClient, user: User): Promise<void> {\n    if (matrixClient.isGuest()) {\n        dis.dispatch({ action: \"require_registration\" });\n        return;\n    }\n    const existingRequest = pendingVerificationRequestForUser(matrixClient, user);\n    setRightPanel({ member: user, verificationRequest: existingRequest });\n}\n\nfunction setRightPanel(state: IRightPanelCardState): void {\n    if (RightPanelStore.instance.roomPhaseHistory.some((card) => card.phase == RightPanelPhases.RoomSummary)) {\n        RightPanelStore.instance.pushCard({ phase: RightPanelPhases.EncryptionPanel, state });\n    } else {\n        RightPanelStore.instance.setCards([\n            { phase: RightPanelPhases.RoomSummary },\n            { phase: RightPanelPhases.MemberInfo, state: { member: state.member } },\n            { phase: RightPanelPhases.EncryptionPanel, state },\n        ]);\n    }\n}\n\nexport function pendingVerificationRequestForUser(\n    matrixClient: MatrixClient,\n    user: User | RoomMember,\n): VerificationRequest | undefined {\n    const dmRoom = findDMForUser(matrixClient, user.userId);\n    if (dmRoom) {\n        return matrixClient.getCrypto()!.findVerificationRequestDMInProgress(dmRoom.roomId, user.userId);\n    }\n}\n","/*\n * Copyright 2026 Element Creations Ltd.\n *\n * SPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\n * Please see LICENSE files in the repository root for full details.\n */\n\nimport { DecryptionFailureCode } from \"matrix-js-sdk/src/crypto-api\";\nimport {\n    BaseViewModel,\n    DecryptionFailureReason,\n    type DecryptionFailureBodyViewSnapshot as DecryptionFailureBodyViewSnapshotInterface,\n    type DecryptionFailureBodyViewModel as DecryptionFailureBodyViewModelInterface,\n} from \"@element-hq/web-shared-components\";\n\nexport interface DecryptionFailureBodyViewModelProps {\n    /**\n     * The message event being rendered.\n     */\n    decryptionFailureCode: DecryptionFailureCode | null;\n    /**\n     * The local device verification state.\n     */\n    verificationState?: boolean;\n    /**\n     * Extra CSS classes to apply to the component\n     */\n    extraClassNames?: string[];\n}\n\n/**\n * ViewModel for the decryption failure body, providing the current state of the component.\n */\nexport class DecryptionFailureBodyViewModel\n    extends BaseViewModel<DecryptionFailureBodyViewSnapshotInterface, DecryptionFailureBodyViewModelProps>\n    implements DecryptionFailureBodyViewModelInterface\n{\n    /**\n     * Convert enum DecryptionFailureCode to enum DecryptionFailureReason.\n     */\n    private static getDecryptionReasonFromCode(\n        decryptionFailureCode: DecryptionFailureCode | null,\n    ): DecryptionFailureReason {\n        switch (decryptionFailureCode) {\n            case DecryptionFailureCode.HISTORICAL_MESSAGE_BACKUP_UNCONFIGURED:\n                return DecryptionFailureReason.HISTORICAL_MESSAGE_BACKUP_UNCONFIGURED;\n            case DecryptionFailureCode.HISTORICAL_MESSAGE_NO_KEY_BACKUP:\n                return DecryptionFailureReason.HISTORICAL_MESSAGE_NO_KEY_BACKUP;\n            case DecryptionFailureCode.HISTORICAL_MESSAGE_USER_NOT_JOINED:\n                return DecryptionFailureReason.HISTORICAL_MESSAGE_USER_NOT_JOINED;\n            case DecryptionFailureCode.MEGOLM_KEY_WITHHELD_FOR_UNVERIFIED_DEVICE:\n                return DecryptionFailureReason.MEGOLM_KEY_WITHHELD_FOR_UNVERIFIED_DEVICE;\n            case DecryptionFailureCode.SENDER_IDENTITY_PREVIOUSLY_VERIFIED:\n                return DecryptionFailureReason.SENDER_IDENTITY_PREVIOUSLY_VERIFIED;\n            case DecryptionFailureCode.UNSIGNED_SENDER_DEVICE:\n                return DecryptionFailureReason.UNSIGNED_SENDER_DEVICE;\n            default:\n                return DecryptionFailureReason.UNABLE_TO_DECRYPT;\n        }\n    }\n\n    /**\n     * @param decryptionFailureCode - The decryption failure code for the event.\n     * @param verificationState - The local device verification state.\n     * @param extraClassNames - Extra CSS classes to apply to the component.\n     */\n    private static readonly computeSnapshot = (\n        decryptionFailureCode: DecryptionFailureCode | null,\n        verificationState?: boolean,\n        extraClassNames?: string[],\n    ): DecryptionFailureBodyViewSnapshotInterface => {\n        // Keep mx_DecryptionFailureBody and mx_EventTile_content to support the compatibility with existing timeline and the all the layout\n        const defaultClassNames = [\"mx_DecryptionFailureBody\", \"mx_EventTile_content\"];\n        return {\n            decryptionFailureReason: DecryptionFailureBodyViewModel.getDecryptionReasonFromCode(decryptionFailureCode),\n            isLocalDeviceVerified: verificationState,\n            extraClassNames: extraClassNames ? defaultClassNames.concat(extraClassNames) : defaultClassNames,\n        };\n    };\n\n    public constructor(props: DecryptionFailureBodyViewModelProps) {\n        super(\n            props,\n            DecryptionFailureBodyViewModel.computeSnapshot(\n                props.decryptionFailureCode,\n                props.verificationState,\n                props.extraClassNames,\n            ),\n        );\n    }\n\n    /**\n     * Updates the properties of the view model and recomputes the snapshot.\n     * @param verificationState - The updated local device verification state.\n     */\n    public setVerificationState(verificationState?: boolean): void {\n        this.props.verificationState = verificationState;\n        this.snapshot.merge({ isLocalDeviceVerified: verificationState });\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { ClientEvent, type IClientWellKnown } from \"matrix-js-sdk/src/matrix\";\n\nimport SdkConfig from \"../SdkConfig\";\nimport { MatrixClientPeg } from \"../MatrixClientPeg\";\n\nconst JITSI_WK_PROPERTY_LEGACY = \"im.vector.riot.jitsi\";\nconst JITSI_WK_PROPERTY = \"io.element.jitsi\";\n\nexport interface JitsiWidgetData {\n    conferenceId: string;\n    isAudioOnly: boolean;\n    domain: string;\n}\n\nexport class Jitsi {\n    private static instance: Jitsi;\n\n    private domain?: string;\n    private _useFor1To1Calls = false;\n\n    public get preferredDomain(): string {\n        return this.domain || \"meet.element.io\";\n    }\n\n    public get useFor1To1Calls(): boolean {\n        return this._useFor1To1Calls;\n    }\n\n    /**\n     * Checks for auth needed by looking up a well-known file\n     *\n     * If the file does not exist, we assume no auth.\n     *\n     * See https://github.com/matrix-org/prosody-mod-auth-matrix-user-verification\n     */\n    public async getJitsiAuth(): Promise<string | null> {\n        if (!this.preferredDomain) {\n            return null;\n        }\n        let data;\n        try {\n            const response = await fetch(`https://${this.preferredDomain}/.well-known/element/jitsi`);\n            data = await response.json();\n        } catch {\n            return null;\n        }\n        if (data.auth) {\n            return data.auth;\n        }\n        return null;\n    }\n\n    public start(): void {\n        const cli = MatrixClientPeg.safeGet();\n        cli.on(ClientEvent.ClientWellKnown, this.update);\n        // call update initially in case we missed the first WellKnown.client event and for if no well-known present\n        this.update(cli.getClientWellKnown());\n    }\n\n    private update = async (discoveryResponse?: IClientWellKnown): Promise<any> => {\n        // Start with a default of the config's domain\n        let domain = SdkConfig.getObject(\"jitsi\")?.get(\"preferred_domain\") || \"meet.element.io\";\n\n        logger.log(\"Attempting to get Jitsi conference information from homeserver\");\n        const wkJitsiConfig = discoveryResponse?.[JITSI_WK_PROPERTY] ?? discoveryResponse?.[JITSI_WK_PROPERTY_LEGACY];\n\n        const wkPreferredDomain = wkJitsiConfig?.[\"preferredDomain\"];\n        if (wkPreferredDomain) domain = wkPreferredDomain;\n\n        // Put the result into memory for us to use later\n        this.domain = domain;\n        logger.log(\"Jitsi conference domain:\", this.preferredDomain);\n        this._useFor1To1Calls = wkJitsiConfig?.[\"useFor1To1Calls\"] || false;\n        logger.log(\"Jitsi use for 1:1 calls:\", this.useFor1To1Calls);\n    };\n\n    /**\n     * Parses the given URL into the data needed for a Jitsi widget, if the widget\n     * URL matches the preferredDomain for the app.\n     * @param {string} url The URL to parse.\n     * @returns {JitsiWidgetData} The widget data if eligible, otherwise null.\n     */\n    public parsePreferredConferenceUrl(url: string): JitsiWidgetData | null {\n        const parsed = new URL(url);\n        if (parsed.hostname !== this.preferredDomain) return null; // invalid\n        return {\n            // URL pathnames always contain a leading slash.\n            // Remove it to be left with just the conference name.\n            conferenceId: parsed.pathname.substring(1),\n            domain: parsed.hostname,\n            isAudioOnly: false,\n        };\n    }\n\n    public static getInstance(): Jitsi {\n        if (!Jitsi.instance) {\n            Jitsi.instance = new Jitsi();\n        }\n        return Jitsi.instance;\n    }\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2021 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\nimport { type IWidget } from \"matrix-widget-api\";\nimport { logger } from \"matrix-js-sdk/src/logger\";\nimport { type Room } from \"matrix-js-sdk/src/matrix\";\n\nimport { getCallBehaviourWellKnown } from \"../utils/WellKnownUtils\";\nimport WidgetUtils from \"../utils/WidgetUtils\";\nimport { type IStoredLayout, WidgetLayoutStore } from \"../stores/widgets/WidgetLayoutStore\";\nimport WidgetEchoStore from \"../stores/WidgetEchoStore\";\nimport WidgetStore, { type IApp } from \"../stores/WidgetStore\";\nimport SdkConfig from \"../SdkConfig\";\nimport { getJoinedNonFunctionalMembers } from \"../utils/room/getJoinedNonFunctionalMembers\";\n\n/* eslint-disable camelcase */\ninterface IManagedHybridWidgetData {\n    widget_id: string;\n    widget: IWidget;\n    layout: IStoredLayout;\n}\n/* eslint-enable camelcase */\n\nfunction getWidgetBuildUrl(room: Room): string | undefined {\n    const functionalMembers = getJoinedNonFunctionalMembers(room);\n    const isDm = functionalMembers.length === 2;\n    if (SdkConfig.get().widget_build_url) {\n        if (isDm && SdkConfig.get().widget_build_url_ignore_dm) {\n            return undefined;\n        }\n        return SdkConfig.get().widget_build_url;\n    }\n\n    const wellKnown = getCallBehaviourWellKnown(room.client);\n    if (isDm && wellKnown?.ignore_dm) {\n        return undefined;\n    }\n    /* eslint-disable-next-line camelcase */\n    return wellKnown?.widget_build_url;\n}\n\nexport function isManagedHybridWidgetEnabled(room: Room): boolean {\n    return !!getWidgetBuildUrl(room);\n}\n\nexport async function addManagedHybridWidget(room: Room): Promise<void> {\n    // Check for permission\n    if (!WidgetUtils.canUserModifyWidgets(room.client, room.roomId)) {\n        logger.error(`User not allowed to modify widgets in ${room.roomId}`);\n        return;\n    }\n\n    // Get widget data\n    /* eslint-disable-next-line camelcase */\n    const widgetBuildUrl = getWidgetBuildUrl(room);\n    if (!widgetBuildUrl) {\n        return;\n    }\n    let widgetData: IManagedHybridWidgetData;\n    try {\n        const response = await fetch(`${widgetBuildUrl}?roomId=${room.roomId}`);\n        widgetData = await response.json();\n    } catch (e) {\n        logger.error(`Managed hybrid widget builder failed for room ${room.roomId}`, e);\n        return;\n    }\n    if (!widgetData) {\n        return;\n    }\n    const { widget_id: widgetId, widget: widgetContent, layout } = widgetData;\n\n    // Ensure the widget is not already present in the room\n    let widgets = WidgetStore.instance.getApps(room.roomId);\n    const existing = widgets.some((w) => w.id === widgetId) || WidgetEchoStore.roomHasPendingWidgets(room.roomId, []);\n    if (existing) {\n        logger.error(`Managed hybrid widget already present in room ${room.roomId}`);\n        return;\n    }\n\n    // Add the widget\n    try {\n        await WidgetUtils.setRoomWidgetContent(room.client, room.roomId, widgetId, {\n            ...widgetContent,\n            \"io.element.managed_hybrid\": true,\n        });\n    } catch (e) {\n        logger.error(`Unable to add managed hybrid widget in room ${room.roomId}`, e);\n        return;\n    }\n\n    // Move the widget into position\n    if (!WidgetLayoutStore.instance.canCopyLayoutToRoom(room)) {\n        return;\n    }\n    widgets = WidgetStore.instance.getApps(room.roomId);\n    const installedWidget = widgets.find((w) => w.id === widgetId);\n    if (!installedWidget) {\n        return;\n    }\n    WidgetLayoutStore.instance.moveToContainer(room, installedWidget, layout.container);\n    WidgetLayoutStore.instance.setContainerHeight(room, layout.container, layout.height);\n    WidgetLayoutStore.instance.copyLayoutToRoom(room);\n}\n\nexport function isManagedHybridWidget(widget: IApp): boolean {\n    return !!widget[\"io.element.managed_hybrid\"];\n}\n","/*\nCopyright 2024 New Vector Ltd.\nCopyright 2020 The Matrix.org Foundation C.I.C.\n\nSPDX-License-Identifier: AGPL-3.0-only OR GPL-3.0-only OR LicenseRef-Element-Commercial\nPlease see LICENSE files in the repository root for full details.\n*/\n\n// TODO: Move to matrix-widget-api\nexport class WidgetType {\n    public static readonly JITSI = new WidgetType(\"m.jitsi\", \"jitsi\");\n    public static readonly STICKERPICKER = new WidgetType(\"m.stickerpicker\", \"m.stickerpicker\");\n    public static readonly INTEGRATION_MANAGER = new WidgetType(\"m.integration_manager\", \"m.integration_manager\");\n    public static readonly CUSTOM = new WidgetType(\"m.custom\", \"m.custom\");\n    public static readonly CALL = new WidgetType(\"m.call\", \"m.call\");\n\n    public constructor(\n        public readonly preferred: string,\n        public readonly legacy: string,\n    ) {}\n\n    public matches(type: string): boolean {\n        return type === this.preferred || type === this.legacy;\n    }\n\n    public static fromString(type: string): WidgetType {\n        // First try and match it against something we're already aware of\n        const known = Object.values(WidgetType).filter((v) => v instanceof WidgetType);\n        const knownMatch = known.find((w) => w.matches(type));\n        if (knownMatch) return knownMatch;\n\n        // If that fails, invent a new widget type\n        return new WidgetType(type, type);\n    }\n}\n","module.exports = \"img/betas/video_rooms.7fada3d.png\";","module.exports = \"img/social/email-1.4053cdb.png\";","module.exports = \"img/social/facebook.b008f77.png\";","module.exports = \"img/social/linkedin.5764540.png\";","module.exports = \"img/social/reddit.5424a6c.png\";","module.exports = \"img/social/twitter-2.711a2e5.png\";","import p, { useState as Se, useEffect as on, useMemo as st, useSyncExternalStore as wh, forwardRef as $, createContext as Eh, useContext as Sh, useId as To, version as Th, useRef as yt, Children as Ah, useCallback as fe, memo as Mf } from \"react\";\nimport { IconButton as ft, Button as Fe, Tooltip as Ih, InlineSpinner as jh, Text as mt, Badge as ii, Menu as xn, MenuTitle as Dc, RadioMenuItem as ai, CheckboxMenuItem as Oh, MenuItem as ae, H1 as Ph, ChatFilter as kh, UnreadCounter as Rh, Unread as Mh, ToggleMenuItem as qc, Separator as Ch, ContextMenu as Nh } from \"@vector-im/compound-web\";\nimport { Virtuoso as xh } from \"react-virtuoso\";\nimport { VirtuosoMockContext as h5 } from \"react-virtuoso\";\nclass zh {\n  disposables = [];\n  _isDisposed = !1;\n  /**\n   * Relinquish all tracked disposable values\n   */\n  dispose() {\n    if (!this.isDisposed) {\n      this._isDisposed = !0;\n      for (const t of this.disposables)\n        typeof t == \"function\" ? t() : t.dispose();\n    }\n  }\n  /**\n   * Track a value that needs to be eventually relinquished\n   */\n  track(t) {\n    return this.throwIfDisposed(), this.disposables.push(t), t;\n  }\n  /**\n   * Add an event listener that will be removed on dispose\n   */\n  trackListener(t, n, r) {\n    this.throwIfDisposed(), t.on(n, r), this.track(() => {\n      t.off(n, r);\n    });\n  }\n  throwIfDisposed() {\n    if (this.isDisposed) throw new Error(\"Disposable is already disposed\");\n  }\n  /**\n   * Whether this disposable has been disposed\n   */\n  get isDisposed() {\n    return this._isDisposed;\n  }\n}\nclass Bh {\n  constructor(t, n) {\n    this.snapshot = t, this.emit = n;\n  }\n  /**\n   * Replace current snapshot with a new snapshot value.\n   * @param snapshot New snapshot value\n   */\n  set(t) {\n    this.snapshot = t, this.emit();\n  }\n  /**\n   * Update a part of the current snapshot by merging into the existing snapshot.\n   * @param snapshot A subset of the snapshot to merge into the current snapshot.\n   */\n  merge(t) {\n    this.snapshot = { ...this.snapshot, ...t }, this.emit();\n  }\n  /**\n   * The current value of the snapshot.\n   */\n  get current() {\n    return this.snapshot;\n  }\n}\nclass Fh {\n  listeners = /* @__PURE__ */ new Set();\n  /**\n   * Subscribe to changes in the view model.\n   * @param listener Will be called whenever the snapshot changes.\n   * @returns A function to unsubscribe from the view model updates.\n   */\n  add = (t) => (this.listeners.add(t), () => {\n    this.listeners.delete(t);\n  });\n  /**\n   * Emit an update to all subscribed listeners.\n   */\n  emit = () => {\n    for (const t of this.listeners)\n      t();\n  };\n}\nclass k8 {\n  subs;\n  snapshot;\n  props;\n  disposables = new zh();\n  constructor(t, n) {\n    this.props = t, this.subs = new Fh(), this.snapshot = new Bh(n, () => {\n      this.subs.emit();\n    });\n  }\n  subscribe = (t) => this.subs.add(t);\n  /**\n   * Returns the current snapshot of the view model.\n   */\n  getSnapshot = () => this.snapshot.current;\n  /**\n   * Relinquish any resources held by this view-model.\n   */\n  dispose() {\n    this.disposables.dispose();\n  }\n  /**\n   * Whether this view-model has been disposed.\n   */\n  get isDisposed() {\n    return this.disposables.isDisposed;\n  }\n}\nclass Dh {\n  constructor(t) {\n    this.snapshot = t;\n  }\n  getSnapshot = () => this.snapshot;\n  subscribe(t) {\n    return () => {\n    };\n  }\n}\nfunction R8(e) {\n  const [t, n] = Se(e);\n  return on(() => {\n    let r = t;\n    if (t.isDisposed) {\n      const o = e();\n      r = o, n(o);\n    }\n    return () => {\n      r.dispose();\n    };\n  }, []), t;\n}\nfunction M8(e, t) {\n  return st(() => {\n    const n = new Dh(e);\n    return Object.assign(n, t), n;\n  }, [e, t]);\n}\nfunction me(e) {\n  return wh(e.subscribe, e.getSnapshot, e.getSnapshot);\n}\nvar Cf = typeof globalThis < \"u\" ? globalThis : typeof window < \"u\" ? window : typeof global < \"u\" ? global : typeof self < \"u\" ? self : {};\nfunction Nf(e) {\n  return e && e.__esModule && Object.prototype.hasOwnProperty.call(e, \"default\") ? e.default : e;\n}\nvar si = { exports: {} };\nvar Lc;\nfunction qh() {\n  return Lc || (Lc = 1, (function(e) {\n    (function() {\n      var t = {}.hasOwnProperty;\n      function n() {\n        for (var i = \"\", a = 0; a < arguments.length; a++) {\n          var s = arguments[a];\n          s && (i = o(i, r(s)));\n        }\n        return i;\n      }\n      function r(i) {\n        if (typeof i == \"string\" || typeof i == \"number\")\n          return i;\n        if (typeof i != \"object\")\n          return \"\";\n        if (Array.isArray(i))\n          return n.apply(null, i);\n        if (i.toString !== Object.prototype.toString && !i.toString.toString().includes(\"[native code]\"))\n          return i.toString();\n        var a = \"\";\n        for (var s in i)\n          t.call(i, s) && i[s] && (a = o(a, s));\n        return a;\n      }\n      function o(i, a) {\n        return a ? i ? i + \" \" + a : i + a : i;\n      }\n      e.exports ? (n.default = n, e.exports = n) : window.classNames = n;\n    })();\n  })(si)), si.exports;\n}\nvar Lh = qh();\nconst pe = /* @__PURE__ */ Nf(Lh), Hh = \"_mediaBody_11o4b_8\", $h = {\n  mediaBody: Hh\n};\nfunction Uh({\n  as: e,\n  className: t,\n  children: n,\n  ...r\n}) {\n  const o = e || \"div\";\n  return /* @__PURE__ */ p.createElement(o, { className: pe(\"mx_MediaBody\", $h.mediaBody, t), ...r }, n);\n}\nconst Kh = \"_flex_4dswl_9\", Gh = {\n  flex: Kh\n};\nfunction Q({\n  as: e = \"div\",\n  display: t = \"flex\",\n  direction: n = \"row\",\n  align: r = \"start\",\n  justify: o = \"start\",\n  gap: i = \"0\",\n  wrap: a = \"nowrap\",\n  className: s,\n  children: c,\n  ...l\n}) {\n  const f = st(\n    () => ({\n      \"--mx-flex-display\": t,\n      \"--mx-flex-direction\": n,\n      \"--mx-flex-align\": r,\n      \"--mx-flex-justify\": o,\n      \"--mx-flex-gap\": i,\n      \"--mx-flex-wrap\": a\n    }),\n    [r, n, t, i, o, a]\n  );\n  return p.createElement(e, { ...l, className: pe(Gh.flex, s), style: f }, c);\n}\nconst Vh = \"_audioPlayer_1ly1h_8\", Yh = \"_mediaInfo_1ly1h_12\", Wh = \"_mediaName_1ly1h_17\", Zh = \"_byline_1ly1h_26\", Jh = \"_clock_1ly1h_30\", Qh = \"_error_1ly1h_34\", _n = {\n  audioPlayer: Vh,\n  mediaInfo: Yh,\n  mediaName: Wh,\n  byline: Zh,\n  clock: Jh,\n  error: Qh\n};\nvar Hr = { exports: {} }, Jn = {};\nvar Hc;\nfunction Xh() {\n  if (Hc) return Jn;\n  Hc = 1;\n  var e = /* @__PURE__ */ Symbol.for(\"react.transitional.element\"), t = /* @__PURE__ */ Symbol.for(\"react.fragment\");\n  function n(r, o, i) {\n    var a = null;\n    if (i !== void 0 && (a = \"\" + i), o.key !== void 0 && (a = \"\" + o.key), \"key\" in o) {\n      i = {};\n      for (var s in o)\n        s !== \"key\" && (i[s] = o[s]);\n    } else i = o;\n    return o = i.ref, {\n      $$typeof: e,\n      type: r,\n      key: a,\n      ref: o !== void 0 ? o : null,\n      props: i\n    };\n  }\n  return Jn.Fragment = t, Jn.jsx = n, Jn.jsxs = n, Jn;\n}\nvar Qn = {};\nvar $c;\nfunction em() {\n  return $c || ($c = 1, process.env.NODE_ENV !== \"production\" && (function() {\n    function e(O) {\n      if (O == null) return null;\n      if (typeof O == \"function\")\n        return O.$$typeof === L ? null : O.displayName || O.name || null;\n      if (typeof O == \"string\") return O;\n      switch (O) {\n        case E:\n          return \"Fragment\";\n        case g:\n          return \"Profiler\";\n        case m:\n          return \"StrictMode\";\n        case S:\n          return \"Suspense\";\n        case I:\n          return \"SuspenseList\";\n        case N:\n          return \"Activity\";\n      }\n      if (typeof O == \"object\")\n        switch (typeof O.tag == \"number\" && console.error(\n          \"Received an unexpected object in getComponentNameFromType(). This is likely a bug in React. Please file an issue.\"\n        ), O.$$typeof) {\n          case w:\n            return \"Portal\";\n          case y:\n            return O.displayName || \"Context\";\n          case T:\n            return (O._context.displayName || \"Context\") + \".Consumer\";\n          case v:\n            var _ = O.render;\n            return O = O.displayName, O || (O = _.displayName || _.name || \"\", O = O !== \"\" ? \"ForwardRef(\" + O + \")\" : \"ForwardRef\"), O;\n          case k:\n            return _ = O.displayName || null, _ !== null ? _ : e(O.type) || \"Memo\";\n          case M:\n            _ = O._payload, O = O._init;\n            try {\n              return e(O(_));\n            } catch {\n            }\n        }\n      return null;\n    }\n    function t(O) {\n      return \"\" + O;\n    }\n    function n(O) {\n      try {\n        t(O);\n        var _ = !1;\n      } catch {\n        _ = !0;\n      }\n      if (_) {\n        _ = console;\n        var A = _.error, j = typeof Symbol == \"function\" && Symbol.toStringTag && O[Symbol.toStringTag] || O.constructor.name || \"Object\";\n        return A.call(\n          _,\n          \"The provided key is an unsupported type %s. This value must be coerced to a string before using it here.\",\n          j\n        ), t(O);\n      }\n    }\n    function r(O) {\n      if (O === E) return \"<>\";\n      if (typeof O == \"object\" && O !== null && O.$$typeof === M)\n        return \"<...>\";\n      try {\n        var _ = e(O);\n        return _ ? \"<\" + _ + \">\" : \"<...>\";\n      } catch {\n        return \"<...>\";\n      }\n    }\n    function o() {\n      var O = V.A;\n      return O === null ? null : O.getOwner();\n    }\n    function i() {\n      return Error(\"react-stack-top-frame\");\n    }\n    function a(O) {\n      if (ie.call(O, \"key\")) {\n        var _ = Object.getOwnPropertyDescriptor(O, \"key\").get;\n        if (_ && _.isReactWarning) return !1;\n      }\n      return O.key !== void 0;\n    }\n    function s(O, _) {\n      function A() {\n        K || (K = !0, console.error(\n          \"%s: `key` is not a prop. Trying to access it will result in `undefined` being returned. If you need to access the same value within the child component, you should pass it as a different prop. (https://react.dev/link/special-props)\",\n          _\n        ));\n      }\n      A.isReactWarning = !0, Object.defineProperty(O, \"key\", {\n        get: A,\n        configurable: !0\n      });\n    }\n    function c() {\n      var O = e(this.type);\n      return W[O] || (W[O] = !0, console.error(\n        \"Accessing element.ref was removed in React 19. ref is now a regular prop. It will be removed from the JSX Element type in a future release.\"\n      )), O = this.props.ref, O !== void 0 ? O : null;\n    }\n    function l(O, _, A, j, B, U) {\n      var z = A.ref;\n      return O = {\n        $$typeof: h,\n        type: O,\n        key: _,\n        props: A,\n        _owner: j\n      }, (z !== void 0 ? z : null) !== null ? Object.defineProperty(O, \"ref\", {\n        enumerable: !1,\n        get: c\n      }) : Object.defineProperty(O, \"ref\", { enumerable: !1, value: null }), O._store = {}, Object.defineProperty(O._store, \"validated\", {\n        configurable: !1,\n        enumerable: !1,\n        writable: !0,\n        value: 0\n      }), Object.defineProperty(O, \"_debugInfo\", {\n        configurable: !1,\n        enumerable: !1,\n        writable: !0,\n        value: null\n      }), Object.defineProperty(O, \"_debugStack\", {\n        configurable: !1,\n        enumerable: !1,\n        writable: !0,\n        value: B\n      }), Object.defineProperty(O, \"_debugTask\", {\n        configurable: !1,\n        enumerable: !1,\n        writable: !0,\n        value: U\n      }), Object.freeze && (Object.freeze(O.props), Object.freeze(O)), O;\n    }\n    function f(O, _, A, j, B, U) {\n      var z = _.children;\n      if (z !== void 0)\n        if (j)\n          if (ce(z)) {\n            for (j = 0; j < z.length; j++)\n              d(z[j]);\n            Object.freeze && Object.freeze(z);\n          } else\n            console.error(\n              \"React.jsx: Static children should always be an array. You are likely explicitly calling React.jsxs or React.jsxDEV. Use the Babel transform instead.\"\n            );\n        else d(z);\n      if (ie.call(_, \"key\")) {\n        z = e(O);\n        var q = Object.keys(_).filter(function(x) {\n          return x !== \"key\";\n        });\n        j = 0 < q.length ? \"{key: someKey, \" + q.join(\": ..., \") + \": ...}\" : \"{key: someKey}\", he[z + j] || (q = 0 < q.length ? \"{\" + q.join(\": ..., \") + \": ...}\" : \"{}\", console.error(\n          `A props object containing a \"key\" prop is being spread into JSX:\n  let props = %s;\n  <%s {...props} />\nReact keys must be passed directly to JSX without using spread:\n  let props = %s;\n  <%s key={someKey} {...props} />`,\n          j,\n          z,\n          q,\n          z\n        ), he[z + j] = !0);\n      }\n      if (z = null, A !== void 0 && (n(A), z = \"\" + A), a(_) && (n(_.key), z = \"\" + _.key), \"key\" in _) {\n        A = {};\n        for (var F in _)\n          F !== \"key\" && (A[F] = _[F]);\n      } else A = _;\n      return z && s(\n        A,\n        typeof O == \"function\" ? O.displayName || O.name || \"Unknown\" : O\n      ), l(\n        O,\n        z,\n        A,\n        o(),\n        B,\n        U\n      );\n    }\n    function d(O) {\n      u(O) ? O._store && (O._store.validated = 1) : typeof O == \"object\" && O !== null && O.$$typeof === M && (O._payload.status === \"fulfilled\" ? u(O._payload.value) && O._payload.value._store && (O._payload.value._store.validated = 1) : O._store && (O._store.validated = 1));\n    }\n    function u(O) {\n      return typeof O == \"object\" && O !== null && O.$$typeof === h;\n    }\n    var b = p, h = /* @__PURE__ */ Symbol.for(\"react.transitional.element\"), w = /* @__PURE__ */ Symbol.for(\"react.portal\"), E = /* @__PURE__ */ Symbol.for(\"react.fragment\"), m = /* @__PURE__ */ Symbol.for(\"react.strict_mode\"), g = /* @__PURE__ */ Symbol.for(\"react.profiler\"), T = /* @__PURE__ */ Symbol.for(\"react.consumer\"), y = /* @__PURE__ */ Symbol.for(\"react.context\"), v = /* @__PURE__ */ Symbol.for(\"react.forward_ref\"), S = /* @__PURE__ */ Symbol.for(\"react.suspense\"), I = /* @__PURE__ */ Symbol.for(\"react.suspense_list\"), k = /* @__PURE__ */ Symbol.for(\"react.memo\"), M = /* @__PURE__ */ Symbol.for(\"react.lazy\"), N = /* @__PURE__ */ Symbol.for(\"react.activity\"), L = /* @__PURE__ */ Symbol.for(\"react.client.reference\"), V = b.__CLIENT_INTERNALS_DO_NOT_USE_OR_WARN_USERS_THEY_CANNOT_UPGRADE, ie = Object.prototype.hasOwnProperty, ce = Array.isArray, D = console.createTask ? console.createTask : function() {\n      return null;\n    };\n    b = {\n      react_stack_bottom_frame: function(O) {\n        return O();\n      }\n    };\n    var K, W = {}, ne = b.react_stack_bottom_frame.bind(\n      b,\n      i\n    )(), le = D(r(i)), he = {};\n    Qn.Fragment = E, Qn.jsx = function(O, _, A) {\n      var j = 1e4 > V.recentlyCreatedOwnerStacks++;\n      return f(\n        O,\n        _,\n        A,\n        !1,\n        j ? Error(\"react-stack-top-frame\") : ne,\n        j ? D(r(O)) : le\n      );\n    }, Qn.jsxs = function(O, _, A) {\n      var j = 1e4 > V.recentlyCreatedOwnerStacks++;\n      return f(\n        O,\n        _,\n        A,\n        !0,\n        j ? Error(\"react-stack-top-frame\") : ne,\n        j ? D(r(O)) : le\n      );\n    };\n  })()), Qn;\n}\nvar Uc;\nfunction tm() {\n  return Uc || (Uc = 1, process.env.NODE_ENV === \"production\" ? Hr.exports = Xh() : Hr.exports = em()), Hr.exports;\n}\nvar R = tm();\nfunction xf(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"m8.98 4.677 9.921 5.58c1.36.764 1.36 2.722 0 3.486l-9.92 5.58C7.647 20.073 6 19.11 6 17.58V6.42c0-1.53 1.647-2.493 2.98-1.743\"\n    })\n  });\n}\nxf.displayName = \"PlaySolidIcon\";\nconst nm = $(xf);\nfunction zf(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M8 4a2 2 0 0 0-2 2v12a2 2 0 1 0 4 0V6a2 2 0 0 0-2-2m8 0a2 2 0 0 0-2 2v12a2 2 0 1 0 4 0V6a2 2 0 0 0-2-2\"\n    })\n  });\n}\nzf.displayName = \"PauseSolidIcon\";\nconst rm = $(zf), om = \"_button_yfjla_8\", im = {\n  button: om\n}, Bf = Eh(null);\nBf.displayName = \"I18nContext\";\nfunction Pe() {\n  const e = Sh(Bf);\n  if (!e)\n    throw new Error(\"useI18n must be used within an I18nContext.Provider\");\n  return e;\n}\nfunction am({\n  disabled: e = !1,\n  playing: t = !1,\n  togglePlay: n,\n  ...r\n}) {\n  const { translate: o } = Pe(), i = o(t ? \"action|pause\" : \"action|play\");\n  return /* @__PURE__ */ p.createElement(\n    ft,\n    {\n      size: \"32px\",\n      \"aria-label\": i,\n      tooltip: i,\n      onClick: n,\n      className: im.button,\n      disabled: e,\n      ...r\n    },\n    t ? /* @__PURE__ */ p.createElement(rm, null) : /* @__PURE__ */ p.createElement(nm, null)\n  );\n}\nfunction sm(e, t = 2) {\n  if (e === 0) return \"0 Bytes\";\n  const n = 1024, r = t < 0 ? 0 : t, o = [\"Bytes\", \"KB\", \"MB\", \"GB\", \"TB\", \"PB\", \"EB\", \"ZB\", \"YB\"], i = Math.floor(Math.log(e) / Math.log(n));\n  return parseFloat((e / Math.pow(n, i)).toFixed(r)) + \" \" + o[i];\n}\nfunction Ce(e, t, n, r, o) {\n  return Et(t, ((i, a) => {\n    const s = i[a];\n    if (s === void 0)\n      throw new TypeError(Ks(a));\n    return s;\n  })(e, t), n, r, o);\n}\nfunction Et(e, t, n, r, o, i) {\n  const a = ur(t, n, r);\n  if (o && t !== a)\n    throw new RangeError(Jd(e, t, n, r, i));\n  return a;\n}\nfunction ke(e) {\n  return e !== null && /object|function/.test(typeof e);\n}\nfunction qe(e, t = Map) {\n  const n = new t();\n  return (r, ...o) => {\n    if (n.has(r))\n      return n.get(r);\n    const i = e(r, ...o);\n    return n.set(r, i), i;\n  };\n}\nfunction lr(e) {\n  return kn({\n    name: e\n  }, 1);\n}\nfunction kn(e, t) {\n  return St(((n) => ({\n    value: n,\n    configurable: 1,\n    writable: !t\n  })), e);\n}\nfunction cm(e) {\n  return St(((t) => ({\n    get: t,\n    configurable: 1\n  })), e);\n}\nfunction Qa(e) {\n  return {\n    [Symbol.toStringTag]: {\n      value: e,\n      configurable: 1\n    }\n  };\n}\nfunction zn(e, t) {\n  const n = {};\n  let r = e.length;\n  for (const o of t)\n    n[e[--r]] = o;\n  return n;\n}\nfunction St(e, t, n) {\n  const r = {};\n  for (const o in t)\n    r[o] = e(t[o], o, n);\n  return r;\n}\nfunction Ao(e, t, n) {\n  const r = {};\n  for (let o = 0; o < t.length; o++) {\n    const i = t[o];\n    r[i] = e(i, o, n);\n  }\n  return r;\n}\nfunction Ff(e, t, n) {\n  const r = {};\n  for (let o = 0; o < e.length; o++)\n    r[t[o]] = n[e[o]];\n  return r;\n}\nfunction Ze(e, t) {\n  const n = /* @__PURE__ */ Object.create(null);\n  for (const r of e)\n    n[r] = t[r];\n  return n;\n}\nfunction Kc(e, t) {\n  for (const n of t)\n    if (n in e)\n      return 1;\n  return 0;\n}\nfunction Df(e, t, n) {\n  for (const r of e)\n    if (t[r] !== n[r])\n      return 0;\n  return 1;\n}\nfunction qf(e, t, n) {\n  const r = {\n    ...n\n  };\n  for (let o = 0; o < t; o++)\n    r[e[o]] = 0;\n  return r;\n}\nfunction J(e, ...t) {\n  return (...n) => e(...t, ...n);\n}\nfunction Gc(e) {\n  return e[0].toUpperCase() + e.substring(1);\n}\nfunction br(e) {\n  return e.slice().sort();\n}\nfunction so(e, t) {\n  return String(t).padStart(e, \"0\");\n}\nfunction Bt(e, t) {\n  return Math.sign(e - t);\n}\nfunction ur(e, t, n) {\n  return Math.min(Math.max(e, t), n);\n}\nfunction vt(e, t) {\n  return [Math.floor(e / t), ar(e, t)];\n}\nfunction ar(e, t) {\n  return (e % t + t) % t;\n}\nfunction qt(e, t) {\n  return [Io(e, t), Xa(e, t)];\n}\nfunction Io(e, t) {\n  return Math.trunc(e / t) || 0;\n}\nfunction Xa(e, t) {\n  return e % t || 0;\n}\nfunction $r(e) {\n  return Math.abs(e % 1) === 0.5;\n}\nfunction Lf(e, t, n) {\n  let r = 0, o = 0;\n  for (let s = 0; s <= t; s++) {\n    const c = e[n[s]], l = ut[s], f = se / l, [d, u] = qt(c, f);\n    r += u * l, o += d;\n  }\n  const [i, a] = qt(r, se);\n  return [o + i, a];\n}\nfunction jo(e, t, n) {\n  const r = {};\n  for (let o = t; o >= 0; o--) {\n    const i = ut[o];\n    r[n[o]] = Io(e, i), e = Xa(e, i);\n  }\n  return r;\n}\nfunction lm(e) {\n  if (e !== void 0)\n    return Te(e);\n}\nfunction um(e) {\n  if (e !== void 0)\n    return gt(e);\n}\nfunction Hf(e) {\n  if (e !== void 0)\n    return es(e);\n}\nfunction gt(e) {\n  return Kf(es(e));\n}\nfunction es(e) {\n  return Uf(_g(e));\n}\nfunction $f(e, t) {\n  if (t == null)\n    throw new RangeError(Ks(e));\n  return t;\n}\nfunction _r(e) {\n  if (!ke(e))\n    throw new TypeError(K0);\n  return e;\n}\nfunction ts(e, t, n = e) {\n  if (typeof t !== e)\n    throw new TypeError(Jt(n, t));\n  return t;\n}\nfunction Uf(e, t = \"number\") {\n  if (!Number.isInteger(e))\n    throw new RangeError(D0(t, e));\n  return e || 0;\n}\nfunction Kf(e, t = \"number\") {\n  if (e <= 0)\n    throw new RangeError(q0(t, e));\n  return e;\n}\nfunction ns(e) {\n  if (typeof e == \"symbol\")\n    throw new TypeError(U0);\n  return String(e);\n}\nfunction to(e, t) {\n  return ke(e) ? String(e) : Te(e, t);\n}\nfunction rs(e) {\n  if (typeof e == \"string\")\n    return BigInt(e);\n  if (typeof e != \"bigint\")\n    throw new TypeError($0(e));\n  return e;\n}\nfunction Gf(e, t = \"number\") {\n  if (typeof e == \"bigint\")\n    throw new TypeError(H0(t));\n  if (e = Number(e), !Number.isFinite(e))\n    throw new RangeError(L0(t, e));\n  return e;\n}\nfunction je(e, t) {\n  return Math.trunc(Gf(e, t)) || 0;\n}\nfunction os(e, t) {\n  return Uf(Gf(e, t), t);\n}\nfunction Vc(e, t) {\n  return Kf(je(e, t), t);\n}\nfunction is(e, t) {\n  let [n, r] = qt(t, se), o = e + n;\n  const i = Math.sign(o);\n  return i && i === -Math.sign(r) && (o -= i, r += i * se), [o, r];\n}\nfunction Rn(e, t, n = 1) {\n  return is(e[0] + t[0] * n, e[1] + t[1] * n);\n}\nfunction an(e, t) {\n  return is(e[0], e[1] + t);\n}\nfunction ct(e, t) {\n  return Rn(t, e, -1);\n}\nfunction Le(e, t) {\n  return Bt(e[0], t[0]) || Bt(e[1], t[1]);\n}\nfunction Vf(e, t, n) {\n  return Le(e, t) === -1 || Le(e, n) === 1;\n}\nfunction as(e, t = 1) {\n  const n = BigInt(se / t);\n  return [Number(e / n), Number(e % n) * t];\n}\nfunction co(e, t = 1) {\n  const n = se / t, [r, o] = qt(e, n);\n  return [r, o * t];\n}\nfunction lt(e, t = 1, n) {\n  const [r, o] = e, [i, a] = qt(o, t);\n  return r * (se / t) + (i + (n ? a / t : 0));\n}\nfunction ss(e, t, n = vt) {\n  const [r, o] = e, [i, a] = n(o, t);\n  return [r * (se / t) + i, a];\n}\nfunction cs(e) {\n  return Ce(e, \"isoYear\", gr, mr, 1), e.isoYear === gr ? Ce(e, \"isoMonth\", 4, 12, 1) : e.isoYear === mr && Ce(e, \"isoMonth\", 1, 9, 1), e;\n}\nfunction Ve(e) {\n  return ze({\n    ...e,\n    ...Be,\n    isoHour: 12\n  }), e;\n}\nfunction ze(e) {\n  const t = Ce(e, \"isoYear\", gr, mr, 1), n = t === gr ? 1 : t === mr ? -1 : 0;\n  return n && dt(_e({\n    ...e,\n    isoDay: e.isoDay + n,\n    isoNanosecond: e.isoNanosecond - n\n  })), e;\n}\nfunction dt(e) {\n  if (!e || Vf(e, jg, Ig))\n    throw new RangeError(Qt);\n  return e;\n}\nfunction Lt(e) {\n  return Lf(e, 5, Xe)[1];\n}\nfunction Oo(e) {\n  const [t, n] = vt(e, se);\n  return [jo(n, 5, Xe), t];\n}\nfunction Yc(e) {\n  return ss(e, at);\n}\nfunction Oe(e) {\n  return Bn(e.isoYear, e.isoMonth, e.isoDay, e.isoHour, e.isoMinute, e.isoSecond, e.isoMillisecond);\n}\nfunction _e(e) {\n  const t = Oe(e);\n  if (t !== void 0) {\n    const [n, r] = qt(t, xe);\n    return [n, r * Ot + (e.isoMicrosecond || 0) * jr + (e.isoNanosecond || 0)];\n  }\n}\nfunction ls(e, t) {\n  const [n, r] = Oo(Lt(e) - t);\n  return dt(_e({\n    ...e,\n    isoDay: e.isoDay + r,\n    ...n\n  }));\n}\nfunction lo(...e) {\n  return Bn(...e) / ap;\n}\nfunction Bn(...e) {\n  const [t, n] = Yf(...e), r = t.valueOf();\n  if (!isNaN(r))\n    return r - n * xe;\n}\nfunction Yf(e, t = 1, n = 1, r = 0, o = 0, i = 0, a = 0) {\n  const s = e === gr ? 1 : e === mr ? -1 : 0, c = /* @__PURE__ */ new Date();\n  return c.setUTCHours(r, o, i, a), c.setUTCFullYear(e, t - 1, n + s), [c, s];\n}\nfunction Fn(e, t) {\n  let [n, r] = an(e, t);\n  r < 0 && (r += se, n -= 1);\n  const [o, i] = vt(r, Ot), [a, s] = vt(i, jr);\n  return Po(n * xe + o, a, s);\n}\nfunction Po(e, t = 0, n = 0) {\n  const r = Math.ceil(Math.max(0, Math.abs(e) - rc) / xe) * Math.sign(e), o = new Date(e - r * xe);\n  return zn(Zo, [o.getUTCFullYear(), o.getUTCMonth() + 1, o.getUTCDate() + r, o.getUTCHours(), o.getUTCMinutes(), o.getUTCSeconds(), o.getUTCMilliseconds(), t, n]);\n}\nfunction us(e, t) {\n  if (t < -rc)\n    throw new RangeError(Qt);\n  const n = e.formatToParts(t), r = {};\n  for (const o of n)\n    r[o.type] = o.value;\n  return r;\n}\nfunction fs(e) {\n  return [e.isoYear, e.isoMonth, e.isoDay];\n}\nfunction Wf(e, t) {\n  return [t, 0];\n}\nfunction Zf() {\n  return Ct;\n}\nfunction Jf(e, t) {\n  switch (t) {\n    case 2:\n      return ds(e) ? 29 : 28;\n    case 4:\n    case 6:\n    case 9:\n    case 11:\n      return 30;\n  }\n  return 31;\n}\nfunction Qf(e) {\n  return ds(e) ? 366 : 365;\n}\nfunction ds(e) {\n  return e % 4 == 0 && (e % 100 != 0 || e % 400 == 0);\n}\nfunction Xf(e) {\n  const [t, n] = Yf(e.isoYear, e.isoMonth, e.isoDay);\n  return ar(t.getUTCDay() - n, 7) || 7;\n}\nfunction ed(e) {\n  return this.id === Gn ? (({ isoYear: t }) => t < 1 ? [\"gregory-inverse\", 1 - t] : [\"gregory\", t])(e) : this.id === Ut ? kg(e) : [];\n}\nfunction fm(e) {\n  const t = Oe(e);\n  if (t < Pg) {\n    const { isoYear: i } = e;\n    return i < 1 ? [\"japanese-inverse\", 1 - i] : [\"japanese\", i];\n  }\n  const n = us(pc(Ut), t), { era: r, eraYear: o } = qd(n, Ut);\n  return [r, o];\n}\nfunction ko(e) {\n  return un(e), Dn(e, 1), e;\n}\nfunction un(e) {\n  return td(e, 1), e;\n}\nfunction Wc(e) {\n  return Df(ec, e, td(e));\n}\nfunction td(e, t) {\n  const { isoYear: n } = e, r = Ce(e, \"isoMonth\", 1, Zf(), t);\n  return {\n    isoYear: n,\n    isoMonth: r,\n    isoDay: Ce(e, \"isoDay\", 1, Jf(n, r), t)\n  };\n}\nfunction Dn(e, t) {\n  return zn(Xe, [Ce(e, \"isoHour\", 0, 23, t), Ce(e, \"isoMinute\", 0, 59, t), Ce(e, \"isoSecond\", 0, 59, t), Ce(e, \"isoMillisecond\", 0, 999, t), Ce(e, \"isoMicrosecond\", 0, 999, t), Ce(e, \"isoNanosecond\", 0, 999, t)]);\n}\nfunction te(e) {\n  return e === void 0 ? 0 : wp(_r(e));\n}\nfunction Ro(e, t = 0) {\n  e = pt(e);\n  const n = Ep(e), r = qg(e, t);\n  return [wp(e), r, n];\n}\nfunction qn(e, t, n, r = 9, o = 0, i = 4) {\n  t = pt(t);\n  let a = _p(t, r, o), s = ms(t), c = kr(t, i);\n  const l = Pr(t, r, o, 1);\n  return a == null ? a = Math.max(n, l) : id(a, l), s = gs(s, l, 1), e && (c = ((f) => f < 4 ? (f + 2) % 4 : f)(c)), [a, l, s, c];\n}\nfunction Mo(e, t = 6, n) {\n  let r = ms(e = Co(e, go));\n  const o = kr(e, 7);\n  let i = Pr(e, t);\n  return i = $f(go, i), r = gs(r, i, void 0, n), [i, r, o];\n}\nfunction ps(e) {\n  return oc(pt(e));\n}\nfunction nd(e, t) {\n  return hs(pt(e), t);\n}\nfunction dm(e) {\n  const t = Co(e, mi), n = Gt(mi, Fg, t, 0);\n  if (!n)\n    throw new RangeError(Jt(mi, n));\n  return n;\n}\nfunction hs(e, t = 4) {\n  const n = od(e);\n  return [kr(e, 4), ...rd(Pr(e, t), n)];\n}\nfunction rd(e, t) {\n  return e != null ? [ut[e], e < 4 ? 9 - 3 * e : -1] : [t === void 0 ? 1 : 10 ** (9 - t), t];\n}\nfunction ms(e) {\n  const t = e[sr];\n  return t === void 0 ? 1 : je(t, sr);\n}\nfunction gs(e, t, n, r) {\n  const o = r ? se : ut[t + 1];\n  if (o) {\n    const i = ut[t];\n    if (o % ((e = Et(sr, e, 1, o / i - (r ? 0 : 1), 1)) * i))\n      throw new RangeError(Jt(sr, e));\n  } else\n    e = Et(sr, e, 1, n ? 10 ** 9 : 1, 1);\n  return e;\n}\nfunction od(e) {\n  let t = e[hi];\n  if (t !== void 0) {\n    if (typeof t != \"number\") {\n      if (ns(t) === \"auto\")\n        return;\n      throw new RangeError(Jt(hi, t));\n    }\n    t = Et(hi, Math.floor(t), 0, 9, 1);\n  }\n  return t;\n}\nfunction pt(e) {\n  return e === void 0 ? {} : _r(e);\n}\nfunction Co(e, t) {\n  return typeof e == \"string\" ? {\n    [t]: e\n  } : _r(e);\n}\nfunction No(e) {\n  return {\n    overflow: Rg[e]\n  };\n}\nfunction ys(e, t, n = 9, r = 0, o) {\n  let i = t[e];\n  if (i === void 0)\n    return o ? r : void 0;\n  if (i = ns(i), i === \"auto\")\n    return o ? r : null;\n  let a = La[i];\n  if (a === void 0 && (a = Sg[i]), a === void 0)\n    throw new RangeError(Xd(e, i, La));\n  return Et(e, a, r, n, 1, Gs), a;\n}\nfunction Gt(e, t, n, r = 0) {\n  const o = n[e];\n  if (o === void 0)\n    return r;\n  const i = ns(o), a = t[i];\n  if (a === void 0)\n    throw new RangeError(Xd(e, i, t));\n  return a;\n}\nfunction id(e, t) {\n  if (t > e)\n    throw new RangeError(dg);\n}\nfunction It(e) {\n  return {\n    branding: cc,\n    epochNanoseconds: e\n  };\n}\nfunction Je(e, t, n) {\n  return {\n    branding: Xt,\n    calendar: n,\n    timeZone: t,\n    epochNanoseconds: e\n  };\n}\nfunction Qe(e, t = e.calendar) {\n  return {\n    branding: Vn,\n    calendar: t,\n    ...Ze(Tg, e)\n  };\n}\nfunction jt(e, t = e.calendar) {\n  return {\n    branding: Rr,\n    calendar: t,\n    ...Ze(tc, e)\n  };\n}\nfunction fr(e, t = e.calendar) {\n  return {\n    branding: ic,\n    calendar: t,\n    ...Ze(tc, e)\n  };\n}\nfunction uo(e, t = e.calendar) {\n  return {\n    branding: ac,\n    calendar: t,\n    ...Ze(tc, e)\n  };\n}\nfunction ht(e) {\n  return {\n    branding: sc,\n    ...Ze(gp, e)\n  };\n}\nfunction be(e) {\n  return {\n    branding: lc,\n    sign: Vt(e),\n    ...Ze(Js, e)\n  };\n}\nfunction vs(e) {\n  return ss(e.epochNanoseconds, Ot)[0];\n}\nfunction pm(e) {\n  return ((t, n = 1) => {\n    const [r, o] = t, i = Math.floor(o / n), a = se / n;\n    return BigInt(r) * BigInt(a) + BigInt(i);\n  })(e.epochNanoseconds);\n}\nfunction ad(e) {\n  return e.epochNanoseconds;\n}\nfunction hm(e, t, n, r, o) {\n  const i = sn(r), [a, s] = ((m, g) => {\n    const T = g((m = Co(m, Ua))[vp]);\n    let y = Dg(m);\n    return y = $f(Ua, y), [y, T];\n  })(o, e), c = Math.max(a, i);\n  if (!s && pr(c, s))\n    return Zc(r, a);\n  if (!s)\n    throw new RangeError(Vo);\n  if (!r.sign)\n    return 0;\n  const [l, f, d] = Do(t, n, s), u = js(d), b = qo(d), h = Os(d), w = b(f, l, r);\n  Mn(s) || (ze(l), ze(w));\n  const E = h(f, l, w, a);\n  return pr(a, s) ? Zc(E, a) : ((m, g, T, y, v, S, I) => {\n    const k = Vt(m), [M, N] = bs(y, Xs(T, m), T, k, v, S, I), L = _s(g, M, N);\n    return m[oe[T]] + L * k;\n  })(E, u(w), a, f, l, u, b);\n}\nfunction Zc(e, t) {\n  return lt(we(e), ut[t], 1);\n}\nfunction bs(e, t, n, r, o, i, a) {\n  const s = oe[n], c = {\n    ...t,\n    [s]: t[s] + r\n  }, l = a(e, o, t), f = a(e, o, c);\n  return [i(l), i(f)];\n}\nfunction _s(e, t, n) {\n  const r = lt(ct(t, n));\n  if (!r)\n    throw new RangeError(Kn);\n  return lt(ct(t, e)) / r;\n}\nfunction mm(e, t) {\n  const [n, r, o] = Mo(t, 5, 1);\n  return It(zo(e.epochNanoseconds, n, r, o, 1));\n}\nfunction gm(e, t, n) {\n  let { epochNanoseconds: r, timeZone: o, calendar: i } = t;\n  const [a, s, c] = Mo(n);\n  if (a === 0 && s === 1)\n    return t;\n  const l = e(o);\n  if (a === 6)\n    r = ((f, d, u, b) => {\n      const h = $e(u, d), [w, E] = f(h), m = u.epochNanoseconds, g = $t(d, w), T = $t(d, E);\n      if (Vf(m, g, T))\n        throw new RangeError(Kn);\n      return fd(_s(m, g, T), b) ? T : g;\n    })(ld, l, t, c);\n  else {\n    const f = l.R(r);\n    r = Ln(l, sd(Fn(r, f), a, s, c), f, 2, 0, 1);\n  }\n  return Je(r, o, i);\n}\nfunction ym(e, t) {\n  return Qe(sd(e, ...Mo(t)), e.calendar);\n}\nfunction vm(e, t) {\n  const [n, r, o] = Mo(t, 5);\n  var i;\n  return ht((i = o, ws(e, wr(n, r), i)[0]));\n}\nfunction bm(e, t) {\n  const n = e(t.timeZone), r = $e(t, n), [o, i] = ld(r), a = lt(ct($t(n, o), $t(n, i)), Wo, 1);\n  if (a <= 0)\n    throw new RangeError(Kn);\n  return a;\n}\nfunction _m(e, t) {\n  const { timeZone: n, calendar: r } = t, o = ((i, a, s) => $t(a, i($e(s, a))))(ud, e(n), t);\n  return Je(o, n, r);\n}\nfunction sd(e, t, n, r) {\n  return cd(e, wr(t, n), r);\n}\nfunction cd(e, t, n) {\n  const [r, o] = ws(e, t, n);\n  return ze({\n    ...fn(e, o),\n    ...r\n  });\n}\nfunction ws(e, t, n) {\n  return Oo(Ht(Lt(e), t, n));\n}\nfunction fo(e) {\n  return Ht(e, Yo, 7);\n}\nfunction wr(e, t) {\n  return ut[e] * t;\n}\nfunction ld(e) {\n  const t = ud(e);\n  return [t, fn(t, 1)];\n}\nfunction ud(e) {\n  return Ag(6, e);\n}\nfunction wm(e, t, n) {\n  const r = Math.min(sn(e), 6);\n  return Hn(Bo(we(e, r), t, n), r);\n}\nfunction xo(e, t, n, r, o, i, a, s, c, l) {\n  if (r === 0 && o === 1)\n    return e;\n  const f = pr(r, s) ? Mn(s) && r < 6 && n >= 6 ? Sm : Em : Tm;\n  let [d, u, b] = f(e, t, n, r, o, i, a, s, c, l);\n  return b && r !== 7 && (d = ((h, w, E, m, g, T, y, v) => {\n    const S = Vt(h);\n    for (let I = m + 1; I <= E; I++) {\n      if (I === 7 && E !== 7)\n        continue;\n      const k = Xs(I, h);\n      k[oe[I]] += S;\n      const M = lt(ct(y(v(g, T, k)), w));\n      if (M && Math.sign(M) !== S)\n        break;\n      h = k;\n    }\n    return h;\n  })(d, u, n, Math.max(6, r), a, s, c, l)), d;\n}\nfunction zo(e, t, n, r, o) {\n  if (t === 6) {\n    const i = ((a) => a[0] + a[1] / se)(e);\n    return [Ht(i, n, r), 0];\n  }\n  return Bo(e, wr(t, n), r, o);\n}\nfunction Bo(e, t, n, r) {\n  let [o, i] = e;\n  r && i < 0 && (i += se, o -= 1);\n  const [a, s] = vt(Ht(i, t, n), se);\n  return is(o + a, s);\n}\nfunction Ht(e, t, n) {\n  return fd(e / t, n) * t;\n}\nfunction fd(e, t) {\n  return $g[t](e);\n}\nfunction Em(e, t, n, r, o, i) {\n  const a = Vt(e), s = we(e), c = zo(s, r, o, i), l = ct(s, c), f = Math.sign(c[0] - s[0]) === a, d = Hn(c, Math.min(n, 6));\n  return [{\n    ...e,\n    ...d\n  }, Rn(t, l), f];\n}\nfunction Sm(e, t, n, r, o, i, a, s, c, l) {\n  const f = Vt(e) || 1, d = lt(we(e, 5)), u = wr(r, o);\n  let b = Ht(d, u, i);\n  const [h, w] = bs(a, {\n    ...e,\n    ...Qs\n  }, 6, f, s, c, l), E = b - lt(ct(h, w));\n  let m = 0;\n  E && Math.sign(E) !== f ? t = an(h, b) : (m += f, b = Ht(E, u, i), t = an(w, b));\n  const g = Lo(b);\n  return [{\n    ...e,\n    ...g,\n    days: e.days + m\n  }, t, !!m];\n}\nfunction Tm(e, t, n, r, o, i, a, s, c, l) {\n  const f = Vt(e), d = oe[r], u = Xs(r, e);\n  r === 7 && (e = {\n    ...e,\n    weeks: e.weeks + Math.trunc(e.days / 7)\n  });\n  const b = Io(e[d], o) * o;\n  u[d] = b;\n  const [h, w] = bs(a, u, r, o * f, s, c, l), E = b + _s(t, h, w) * f * o, m = Ht(E, o, i), g = Math.sign(m - E) === f;\n  return u[d] = m, [u, g ? w : h, g];\n}\nfunction Jc(e, t, n, r) {\n  const [o, i, a, s] = ((l) => {\n    const f = hs(l = pt(l));\n    return [l.timeZone, ...f];\n  })(r), c = o !== void 0;\n  return ((l, f, d, u, b, h) => {\n    d = Bo(d, b, u, 1);\n    const w = f.R(d);\n    return Es(Fn(d, w), h) + (l ? Er(fo(w)) : \"Z\");\n  })(c, t(c ? e(o) : mn), n.epochNanoseconds, i, a, s);\n}\nfunction Qc(e, t, n) {\n  const [r, o, i, a, s, c] = ((l) => {\n    l = pt(l);\n    const f = oc(l), d = od(l), u = Hg(l), b = kr(l, 4), h = Pr(l, 4);\n    return [f, Lg(l), u, b, ...rd(h, d)];\n  })(n);\n  return ((l, f, d, u, b, h, w, E, m, g) => {\n    u = Bo(u, m, E, 1);\n    const T = l(d).R(u);\n    return Es(Fn(u, T), g) + Er(fo(T), w) + ((y, v) => v !== 1 ? \"[\" + (v === 2 ? \"!\" : \"\") + y + \"]\" : \"\")(d, h) + Ss(f, b);\n  })(e, t.calendar, t.timeZone, t.epochNanoseconds, r, o, i, a, s, c);\n}\nfunction Xc(e, t) {\n  const [n, r, o, i] = ((l) => (l = pt(l), [oc(l), ...hs(l)]))(t);\n  return a = e.calendar, s = n, c = i, Es(cd(e, o, r), c) + Ss(a, s);\n  var a, s, c;\n}\nfunction el(e, t) {\n  return n = e.calendar, r = e, o = ps(t), po(r) + Ss(n, o);\n  var n, r, o;\n}\nfunction tl(e, t) {\n  return dd(e.calendar, pd, e, ps(t));\n}\nfunction nl(e, t) {\n  return dd(e.calendar, Am, e, ps(t));\n}\nfunction rl(e, t) {\n  const [n, r, o] = nd(t);\n  return i = o, hd(ws(e, r, n)[0], i);\n  var i;\n}\nfunction ci(e, t) {\n  const [n, r, o] = nd(t, 3);\n  return r > 1 && dn(e = {\n    ...e,\n    ...wm(e, r, n)\n  }), ((i, a) => {\n    const { sign: s } = i, c = s === -1 ? Re(i) : i, { hours: l, minutes: f } = c, [d, u] = ss(we(c, 3), at, qt);\n    vd(d);\n    const b = Ts(u, a), h = a >= 0 || !s || b;\n    return (s < 0 ? \"-\" : \"\") + \"P\" + ol({\n      Y: rn(c.years),\n      M: rn(c.months),\n      W: rn(c.weeks),\n      D: rn(c.days)\n    }) + (l || f || d || h ? \"T\" + ol({\n      H: rn(l),\n      M: rn(f),\n      S: rn(d, h) + b\n    }) : \"\");\n  })(e, o);\n}\nfunction dd(e, t, n, r) {\n  const o = r > 1 || r === 0 && e !== X;\n  return r === 1 ? e === X ? t(n) : po(n) : o ? po(n) + md(e, r === 2) : t(n);\n}\nfunction ol(e) {\n  const t = [];\n  for (const n in e) {\n    const r = e[n];\n    r && t.push(r, n);\n  }\n  return t.join(\"\");\n}\nfunction Es(e, t) {\n  return po(e) + \"T\" + hd(e, t);\n}\nfunction po(e) {\n  return pd(e) + \"-\" + Ye(e.isoDay);\n}\nfunction pd(e) {\n  const { isoYear: t } = e;\n  return (t < 0 || t > 9999 ? gd(t) + so(6, Math.abs(t)) : so(4, t)) + \"-\" + Ye(e.isoMonth);\n}\nfunction Am(e) {\n  return Ye(e.isoMonth) + \"-\" + Ye(e.isoDay);\n}\nfunction hd(e, t) {\n  const n = [Ye(e.isoHour), Ye(e.isoMinute)];\n  return t !== -1 && n.push(Ye(e.isoSecond) + ((r, o, i, a) => Ts(r * Ot + o * jr + i, a))(e.isoMillisecond, e.isoMicrosecond, e.isoNanosecond, t)), n.join(\":\");\n}\nfunction Er(e, t = 0) {\n  if (t === 1)\n    return \"\";\n  const [n, r] = vt(Math.abs(e), Wo), [o, i] = vt(r, Yo), [a, s] = vt(i, at);\n  return gd(e) + Ye(n) + \":\" + Ye(o) + (a || s ? \":\" + Ye(a) + Ts(s) : \"\");\n}\nfunction Ss(e, t) {\n  return t !== 1 && (t > 1 || t === 0 && e !== X) ? md(e, t === 2) : \"\";\n}\nfunction md(e, t) {\n  return \"[\" + (t ? \"!\" : \"\") + \"u-ca=\" + e + \"]\";\n}\nfunction Ts(e, t) {\n  let n = so(9, e);\n  return n = t === void 0 ? n.replace(Gg, \"\") : n.slice(0, t), n ? \".\" + n : \"\";\n}\nfunction gd(e) {\n  return e < 0 ? \"-\" : \"+\";\n}\nfunction rn(e, t) {\n  return e || t ? e.toLocaleString(\"fullwide\", {\n    useGrouping: 0\n  }) : \"\";\n}\nfunction Im(e, t) {\n  const { epochNanoseconds: n } = e, r = (t.R ? t : t(e.timeZone)).R(n), o = Fn(n, r);\n  return {\n    calendar: e.calendar,\n    ...o,\n    offsetNanoseconds: r\n  };\n}\nfunction Ln(e, t, n, r = 0, o = 0, i, a) {\n  if (n !== void 0 && r === 1 && (r === 1 || a))\n    return ls(t, n);\n  const s = e.I(t);\n  if (n !== void 0 && r !== 3) {\n    const c = ((l, f, d, u) => {\n      const b = _e(f);\n      u && (d = fo(d));\n      for (const h of l) {\n        let w = lt(ct(h, b));\n        if (u && (w = fo(w)), w === d)\n          return h;\n      }\n    })(s, t, n, i);\n    if (c !== void 0)\n      return c;\n    if (r === 0)\n      throw new RangeError(ag);\n  }\n  return a ? _e(t) : Sr(e, t, o, s);\n}\nfunction Sr(e, t, n = 0, r = e.I(t)) {\n  if (r.length === 1)\n    return r[0];\n  if (n === 1)\n    throw new RangeError(sg);\n  if (r.length)\n    return r[n === 3 ? 1 : 0];\n  const o = _e(t), i = ((s, c) => {\n    const l = s.R(an(c, -se));\n    return ((f) => {\n      if (f > se)\n        throw new RangeError(ig);\n      return f;\n    })(s.R(an(c, se)) - l);\n  })(e, o), a = i * (n === 2 ? -1 : 1);\n  return (r = e.I(Fn(o, a)))[n === 2 ? 0 : r.length - 1];\n}\nfunction $t(e, t) {\n  const n = e.I(t);\n  if (n.length)\n    return n[0];\n  const r = an(_e(t), -se);\n  return e.O(r, 1);\n}\nfunction il(e, t, n) {\n  return It(dt(Rn(t.epochNanoseconds, ((r) => {\n    if (bd(r))\n      throw new RangeError(ug);\n    return we(r, 5);\n  })(e ? Re(n) : n))));\n}\nfunction al(e, t, n, r, o, i = /* @__PURE__ */ Object.create(null)) {\n  const a = t(r.timeZone), s = e(r.calendar);\n  return {\n    ...r,\n    ...As(a, s, r, n ? Re(o) : o, i)\n  };\n}\nfunction sl(e, t, n, r, o = /* @__PURE__ */ Object.create(null)) {\n  const { calendar: i } = n;\n  return Qe(Is(e(i), n, t ? Re(r) : r, o), i);\n}\nfunction cl(e, t, n, r, o) {\n  const { calendar: i } = n;\n  return jt(Fo(e(i), n, t ? Re(r) : r, o), i);\n}\nfunction ll(e, t, n, r, o) {\n  const i = n.calendar, a = e(i);\n  let s = Ve(dr(a, n));\n  t && (r = Ps(r)), r.sign < 0 && (s = a.P(s, {\n    ...Ee,\n    months: 1\n  }), s = fn(s, -1));\n  const c = a.P(s, r, o);\n  return fr(dr(a, c), i);\n}\nfunction ul(e, t, n) {\n  return ht(yd(t, e ? Re(n) : n)[0]);\n}\nfunction As(e, t, n, r, o) {\n  const i = we(r, 5);\n  let a = n.epochNanoseconds;\n  if (bd(r)) {\n    const s = $e(n, e);\n    a = Rn(Sr(e, {\n      ...Fo(t, s, {\n        ...r,\n        ...Qs\n      }, o),\n      ...Ze(Xe, s)\n    }), i);\n  } else\n    a = Rn(a, i), te(o);\n  return {\n    epochNanoseconds: dt(a)\n  };\n}\nfunction Is(e, t, n, r) {\n  const [o, i] = yd(t, n);\n  return ze({\n    ...Fo(e, t, {\n      ...n,\n      ...Qs,\n      days: n.days + i\n    }, r),\n    ...o\n  });\n}\nfunction Fo(e, t, n, r) {\n  if (n.years || n.months || n.weeks)\n    return e.P(t, n, r);\n  te(r);\n  const o = n.days + we(n, 5)[0];\n  return o ? Ve(fn(t, o)) : t;\n}\nfunction dr(e, t, n = 1) {\n  return fn(t, n - e.day(t));\n}\nfunction yd(e, t) {\n  const [n, r] = we(t, 5), [o, i] = Oo(Lt(e) + r);\n  return [o, n + i];\n}\nfunction fn(e, t) {\n  return t ? {\n    ...e,\n    ...Po(Oe(e) + t * xe)\n  } : e;\n}\nfunction Do(e, t, n) {\n  const r = e(n.calendar);\n  return Mn(n) ? [n, r, t(n.timeZone)] : [{\n    ...n,\n    ...Be\n  }, r];\n}\nfunction js(e) {\n  return e ? ad : _e;\n}\nfunction qo(e) {\n  return e ? J(As, e) : Is;\n}\nfunction Os(e) {\n  return e ? J(Zm, e) : Jm;\n}\nfunction Mn(e) {\n  return e && e.epochNanoseconds;\n}\nfunction pr(e, t) {\n  return e <= 6 - (Mn(t) ? 1 : 0);\n}\nfunction fl(e, t, n, r, o, i, a) {\n  const s = e(pt(a).relativeTo), c = Math.max(sn(o), sn(i));\n  if (pr(c, s))\n    return be(dn(((w, E, m, g) => {\n      const T = Rn(we(w), we(E), g ? -1 : 1);\n      if (!Number.isFinite(T[0]))\n        throw new RangeError(Qt);\n      return {\n        ...Ee,\n        ...Hn(T, m)\n      };\n    })(o, i, c, r)));\n  if (!s)\n    throw new RangeError(Vo);\n  r && (i = Re(i));\n  const [l, f, d] = Do(t, n, s), u = qo(d), b = Os(d), h = u(f, l, o);\n  return be(b(f, l, u(f, h, i), c));\n}\nfunction jm(e, t, n, r, o) {\n  const i = sn(r), [a, s, c, l, f] = ((S, I, k) => {\n    S = Co(S, go);\n    let M = _p(S);\n    const N = k(S[vp]);\n    let L = ms(S);\n    const V = kr(S, 7);\n    let ie = Pr(S);\n    if (M === void 0 && ie === void 0)\n      throw new RangeError(fg);\n    if (ie == null && (ie = 0), M == null && (M = Math.max(ie, I)), id(M, ie), L = gs(L, ie, 1), L > 1 && ie > 5 && M !== ie)\n      throw new RangeError(\"For calendar units with roundingIncrement > 1, use largestUnit = smallestUnit\");\n    return [M, ie, L, V, N];\n  })(o, i, e), d = Math.max(i, a);\n  if (!f && d <= 6)\n    return be(dn(((S, I, k, M, N) => {\n      const L = zo(we(S), k, M, N);\n      return {\n        ...Ee,\n        ...Hn(L, I)\n      };\n    })(r, a, s, c, l)));\n  if (!Mn(f) && !r.sign)\n    return r;\n  if (!f)\n    throw new RangeError(Vo);\n  const [u, b, h] = Do(t, n, f), w = js(h), E = qo(h), m = Os(h), g = E(b, u, r);\n  Mn(f) || (ze(u), ze(g));\n  let T = m(b, u, g, a);\n  const y = r.sign, v = Vt(T);\n  if (y && v && y !== v)\n    throw new RangeError(Kn);\n  return T = xo(T, w(g), a, s, c, l, b, u, w, E), be(T);\n}\nfunction Om(e) {\n  return e.sign === -1 ? Ps(e) : e;\n}\nfunction Ps(e) {\n  return be(Re(e));\n}\nfunction Re(e) {\n  const t = {};\n  for (const n of oe)\n    t[n] = -1 * e[n] || 0;\n  return t;\n}\nfunction Pm(e) {\n  return !e.sign;\n}\nfunction Vt(e, t = oe) {\n  let n = 0;\n  for (const r of t) {\n    const o = Math.sign(e[r]);\n    if (o) {\n      if (n && n !== o)\n        throw new RangeError(lg);\n      n = o;\n    }\n  }\n  return n;\n}\nfunction dn(e) {\n  for (const t of Eg)\n    Et(t, e[t], -El, El, 1);\n  return vd(lt(we(e), at)), e;\n}\nfunction vd(e) {\n  if (!Number.isSafeInteger(e))\n    throw new RangeError(cg);\n}\nfunction we(e, t = 6) {\n  return Lf(e, t, oe);\n}\nfunction Hn(e, t = 6) {\n  const [n, r] = e, o = jo(r, t, oe);\n  if (o[oe[t]] += n * (se / ut[t]), !Number.isFinite(o[oe[t]]))\n    throw new RangeError(Qt);\n  return o;\n}\nfunction Lo(e, t = 5) {\n  return jo(e, t, oe);\n}\nfunction bd(e) {\n  return !!Vt(e, mp);\n}\nfunction sn(e) {\n  let t = 9;\n  for (; t > 0 && !e[oe[t]]; t--)\n    ;\n  return t;\n}\nfunction km(e, t) {\n  return [e, t];\n}\nfunction dl(e) {\n  const t = Math.floor(e / ro) * ro;\n  return [t, t + ro];\n}\nfunction Rm(e) {\n  const t = Yt(e = to(e));\n  if (!t)\n    throw new RangeError(Ne(e));\n  let n;\n  if (t.j)\n    n = 0;\n  else {\n    if (!t.offset)\n      throw new RangeError(Ne(e));\n    n = pn(t.offset);\n  }\n  return t.timeZone && Ns(t.timeZone, 1), It(ls(ko(t), n));\n}\nfunction Mm(e) {\n  const t = Yt(Te(e));\n  if (!t)\n    throw new RangeError(Ne(e));\n  if (t.timeZone)\n    return _d(t, t.offset ? pn(t.offset) : void 0);\n  if (t.j)\n    throw new RangeError(Ne(e));\n  return Ed(t);\n}\nfunction Cm(e, t) {\n  const n = Yt(Te(e));\n  if (!n || !n.timeZone)\n    throw new RangeError(Ne(e));\n  const { offset: r } = n, o = r ? pn(r) : void 0, [, i, a] = Ro(t);\n  return _d(n, o, i, a);\n}\nfunction pn(e) {\n  const t = Ns(e);\n  if (t === void 0)\n    throw new RangeError(Ne(e));\n  return t;\n}\nfunction Nm(e) {\n  const t = Yt(Te(e));\n  if (!t || t.j)\n    throw new RangeError(Ne(e));\n  return Qe(wd(t));\n}\nfunction ks(e, t, n) {\n  let r = Yt(Te(e));\n  if (!r || r.j)\n    throw new RangeError(Ne(e));\n  return t ? r.calendar === X && (r = r.isoYear === -271821 && r.isoMonth === 4 ? {\n    ...r,\n    isoDay: 20,\n    ...Be\n  } : {\n    ...r,\n    isoDay: 1,\n    ...Be\n  }) : n && r.calendar === X && (r = {\n    ...r,\n    isoYear: _t\n  }), jt(r.C ? wd(r) : Ed(r));\n}\nfunction xm(e, t) {\n  const n = Ms(Te(t));\n  if (n)\n    return Rs(n), fr(cs(un(n)));\n  const r = ks(t, 1);\n  return fr(dr(e(r.calendar), r));\n}\nfunction Rs(e) {\n  if (e.calendar !== X)\n    throw new RangeError(bt(e.calendar));\n}\nfunction zm(e, t) {\n  const n = Cs(Te(t));\n  if (n)\n    return Rs(n), uo(un(n));\n  const r = ks(t, 0, 1), { calendar: o } = r, i = e(o), [a, s, c] = i.v(r), [l, f] = i.q(a, s), [d, u] = i.G(l, f, c);\n  return uo(Ve(i.V(d, u, c)), o);\n}\nfunction Bm(e) {\n  let t, n = ((r) => {\n    const o = Xg.exec(r);\n    return o ? (Ho(o[10]), Ad(o)) : void 0;\n  })(Te(e));\n  if (!n) {\n    if (n = Yt(e), !n)\n      throw new RangeError(Ne(e));\n    if (!n.C)\n      throw new RangeError(Ne(e));\n    if (n.j)\n      throw new RangeError(bt(\"Z\"));\n    Rs(n);\n  }\n  if ((t = Ms(e)) && Wc(t))\n    throw new RangeError(Ne(e));\n  if ((t = Cs(e)) && Wc(t))\n    throw new RangeError(Ne(e));\n  return ht(Dn(n, 1));\n}\nfunction Fm(e) {\n  const t = ((n) => {\n    const r = ny.exec(n);\n    return r ? ((o) => {\n      function i(f, d, u) {\n        let b = 0, h = 0;\n        if (u && ([b, c] = vt(c, ut[u])), f !== void 0) {\n          if (s)\n            throw new RangeError(bt(f));\n          h = ((w) => {\n            const E = parseInt(w);\n            if (!Number.isFinite(E))\n              throw new RangeError(bt(w));\n            return E;\n          })(f), a = 1, d && (c = xs(d) * (ut[u] / at), s = 1);\n        }\n        return b + h;\n      }\n      let a = 0, s = 0, c = 0, l = {\n        ...zn(oe, [i(o[2]), i(o[3]), i(o[4]), i(o[5]), i(o[6], o[7], 5), i(o[8], o[9], 4), i(o[10], o[11], 3)]),\n        ...jo(c, 2, oe)\n      };\n      if (!a)\n        throw new RangeError(Qd(oe));\n      return zs(o[1]) < 0 && (l = Re(l)), l;\n    })(r) : void 0;\n  })(Te(e));\n  if (!t)\n    throw new RangeError(Ne(e));\n  return be(dn(t));\n}\nfunction Dm(e) {\n  const t = Yt(e) || Ms(e) || Cs(e);\n  return t ? t.calendar : e;\n}\nfunction qm(e) {\n  const t = Yt(e);\n  return t && (t.timeZone || t.j && mn || t.offset) || e;\n}\nfunction _d(e, t, n = 0, r = 0) {\n  const o = Bs(e.timeZone), i = G(o);\n  let a;\n  return ko(e), a = e.C ? Ln(i, e, t, n, r, !i.$, e.j) : $t(i, e), Je(a, o, Go(e.calendar));\n}\nfunction wd(e) {\n  return Sd(ze(ko(e)));\n}\nfunction Ed(e) {\n  return Sd(Ve(un(e)));\n}\nfunction Sd(e) {\n  return {\n    ...e,\n    calendar: Go(e.calendar)\n  };\n}\nfunction Yt(e) {\n  const t = Qg.exec(e);\n  return t ? ((n) => {\n    const r = n[10], o = (r || \"\").toUpperCase() === \"Z\";\n    return {\n      isoYear: Td(n),\n      isoMonth: parseInt(n[4]),\n      isoDay: parseInt(n[5]),\n      ...Ad(n.slice(5)),\n      ...Ho(n[16]),\n      C: !!n[6],\n      j: o,\n      offset: o ? void 0 : r\n    };\n  })(t) : void 0;\n}\nfunction Ms(e) {\n  const t = Zg.exec(e);\n  return t ? ((n) => ({\n    isoYear: Td(n),\n    isoMonth: parseInt(n[4]),\n    isoDay: 1,\n    ...Ho(n[5])\n  }))(t) : void 0;\n}\nfunction Cs(e) {\n  const t = Jg.exec(e);\n  return t ? ((n) => ({\n    isoYear: _t,\n    isoMonth: parseInt(n[1]),\n    isoDay: parseInt(n[2]),\n    ...Ho(n[3])\n  }))(t) : void 0;\n}\nfunction Ns(e, t) {\n  const n = ey.exec(e);\n  return n ? ((r, o) => {\n    const i = r[4] || r[5];\n    if (o && i)\n      throw new RangeError(bt(i));\n    return ((a) => {\n      if (Math.abs(a) >= se)\n        throw new RangeError(og);\n      return a;\n    })((Pn(r[2]) * Wo + Pn(r[3]) * Yo + Pn(r[4]) * at + xs(r[5] || \"\")) * zs(r[1]));\n  })(n, t) : void 0;\n}\nfunction Td(e) {\n  const t = zs(e[1]), n = parseInt(e[2] || e[3]);\n  if (t < 0 && !n)\n    throw new RangeError(bt(-0));\n  return t * n;\n}\nfunction Ad(e) {\n  const t = Pn(e[3]);\n  return {\n    ...Oo(xs(e[4] || \"\"))[0],\n    isoHour: Pn(e[1]),\n    isoMinute: Pn(e[2]),\n    isoSecond: t === 60 ? 59 : t\n  };\n}\nfunction Ho(e) {\n  let t, n;\n  const r = [];\n  if (e.replace(ty, ((o, i, a) => {\n    const s = !!i, [c, l] = a.split(\"=\").reverse();\n    if (l) {\n      if (l === \"u-ca\")\n        r.push(c), t || (t = s);\n      else if (s || /[A-Z]/.test(l))\n        throw new RangeError(bt(o));\n    } else {\n      if (n)\n        throw new RangeError(bt(o));\n      n = c;\n    }\n    return \"\";\n  })), r.length > 1 && t)\n    throw new RangeError(bt(e));\n  return {\n    timeZone: n,\n    calendar: r[0] || X\n  };\n}\nfunction xs(e) {\n  return parseInt(e.padEnd(9, \"0\"));\n}\nfunction $n(e) {\n  return new RegExp(`^${e}$`, \"i\");\n}\nfunction zs(e) {\n  return e && e !== \"+\" ? -1 : 1;\n}\nfunction Pn(e) {\n  return e === void 0 ? 0 : parseInt(e);\n}\nfunction Lm(e) {\n  return Bs(Te(e));\n}\nfunction Bs(e) {\n  const t = Fs(e);\n  return typeof t == \"number\" ? Er(t) : t ? ((n) => {\n    if (iy.test(n))\n      throw new RangeError(rp(n));\n    if (oy.test(n))\n      throw new RangeError(rg);\n    return n.toLowerCase().split(\"/\").map(((r, o) => (r.length <= 3 || /\\d/.test(r)) && !/etc|yap/.test(r) ? r.toUpperCase() : r.replace(/baja|dumont|[a-z]+/g, ((i, a) => i.length <= 2 && !o || i === \"in\" || i === \"chat\" ? i.toUpperCase() : i.length > 2 || !a ? Gc(i).replace(/island|noronha|murdo|rivadavia|urville/, Gc) : i)))).join(\"/\");\n  })(e) : mn;\n}\nfunction pl(e) {\n  const t = Fs(e);\n  return typeof t == \"number\" ? t : t ? t.resolvedOptions().timeZone : mn;\n}\nfunction Fs(e) {\n  const t = Ns(e = e.toUpperCase(), 1);\n  return t !== void 0 ? t : e !== mn ? ry(e) : void 0;\n}\nfunction Id(e, t) {\n  return Le(e.epochNanoseconds, t.epochNanoseconds);\n}\nfunction jd(e, t) {\n  return Le(e.epochNanoseconds, t.epochNanoseconds);\n}\nfunction Hm(e, t, n, r, o, i) {\n  const a = e(pt(i).relativeTo), s = Math.max(sn(r), sn(o));\n  if (Df(oe, r, o))\n    return 0;\n  if (pr(s, a))\n    return Le(we(r), we(o));\n  if (!a)\n    throw new RangeError(Vo);\n  const [c, l, f] = Do(t, n, a), d = js(f), u = qo(f);\n  return Le(d(u(l, c, r)), d(u(l, c, o)));\n}\nfunction Od(e, t) {\n  return Un(e, t) || Ds(e, t);\n}\nfunction Un(e, t) {\n  return Bt(Oe(e), Oe(t));\n}\nfunction Ds(e, t) {\n  return Bt(Lt(e), Lt(t));\n}\nfunction $m(e, t) {\n  return !Id(e, t);\n}\nfunction Um(e, t) {\n  return !jd(e, t) && !!Pd(e.timeZone, t.timeZone) && e.calendar === t.calendar;\n}\nfunction Km(e, t) {\n  return !Od(e, t) && e.calendar === t.calendar;\n}\nfunction Gm(e, t) {\n  return !Un(e, t) && e.calendar === t.calendar;\n}\nfunction Vm(e, t) {\n  return !Un(e, t) && e.calendar === t.calendar;\n}\nfunction Ym(e, t) {\n  return !Un(e, t) && e.calendar === t.calendar;\n}\nfunction Wm(e, t) {\n  return !Ds(e, t);\n}\nfunction Pd(e, t) {\n  if (e === t)\n    return 1;\n  try {\n    return pl(e) === pl(t);\n  } catch {\n  }\n}\nfunction hl(e, t, n, r) {\n  const o = qn(e, r, 3, 5), i = $o(t.epochNanoseconds, n.epochNanoseconds, ...o);\n  return be(e ? Re(i) : i);\n}\nfunction ml(e, t, n, r, o, i) {\n  const a = Ko(r.calendar, o.calendar), [s, c, l, f] = qn(n, i, 5), d = r.epochNanoseconds, u = o.epochNanoseconds, b = Le(u, d);\n  let h;\n  if (b)\n    if (s < 6)\n      h = $o(d, u, s, c, l, f);\n    else {\n      const w = t(((m, g) => {\n        if (!Pd(m, g))\n          throw new RangeError(op);\n        return m;\n      })(r.timeZone, o.timeZone)), E = e(a);\n      h = Rd(E, w, r, o, b, s, i), h = xo(h, u, s, c, l, f, E, r, ad, J(As, w));\n    }\n  else\n    h = Ee;\n  return be(n ? Re(h) : h);\n}\nfunction gl(e, t, n, r, o) {\n  const i = Ko(n.calendar, r.calendar), [a, s, c, l] = qn(t, o, 6), f = _e(n), d = _e(r), u = Le(d, f);\n  let b;\n  if (u)\n    if (a <= 6)\n      b = $o(f, d, a, s, c, l);\n    else {\n      const h = e(i);\n      b = Md(h, n, r, u, a, o), b = xo(b, d, a, s, c, l, h, n, _e, Is);\n    }\n  else\n    b = Ee;\n  return be(t ? Re(b) : b);\n}\nfunction yl(e, t, n, r, o) {\n  const i = Ko(n.calendar, r.calendar);\n  return kd(t, (() => e(i)), n, r, ...qn(t, o, 6, 9, 6));\n}\nfunction vl(e, t, n, r, o) {\n  const i = Ko(n.calendar, r.calendar), a = qn(t, o, 9, 9, 8), s = e(i), c = dr(s, n), l = dr(s, r);\n  return c.isoYear === l.isoYear && c.isoMonth === l.isoMonth && c.isoDay === l.isoDay ? be(Ee) : kd(t, (() => s), Ve(c), Ve(l), ...a, 8);\n}\nfunction kd(e, t, n, r, o, i, a, s, c = 6) {\n  const l = _e(n), f = _e(r);\n  if (l === void 0 || f === void 0)\n    throw new RangeError(Qt);\n  let d;\n  if (Le(f, l))\n    if (o === 6)\n      d = $o(l, f, o, i, a, s);\n    else {\n      const u = t();\n      d = u.N(n, r, o), i === c && a === 1 || (d = xo(d, f, o, i, a, s, u, n, _e, Fo));\n    }\n  else\n    d = Ee;\n  return be(e ? Re(d) : d);\n}\nfunction bl(e, t, n, r) {\n  const [o, i, a, s] = qn(e, r, 5, 5), c = Ht(qs(t, n), wr(i, a), s), l = {\n    ...Ee,\n    ...Lo(c, o)\n  };\n  return be(e ? Re(l) : l);\n}\nfunction Zm(e, t, n, r, o, i) {\n  const a = Le(r.epochNanoseconds, n.epochNanoseconds);\n  return a ? o < 6 ? Cd(n.epochNanoseconds, r.epochNanoseconds, o) : Rd(t, e, n, r, a, o, i) : Ee;\n}\nfunction Jm(e, t, n, r, o) {\n  const i = _e(t), a = _e(n), s = Le(a, i);\n  return s ? r <= 6 ? Cd(i, a, r) : Md(e, t, n, s, r, o) : Ee;\n}\nfunction Rd(e, t, n, r, o, i, a) {\n  const [s, c, l] = ((u, b, h, w) => {\n    function E() {\n      return I = {\n        ...fn(T, v++ * -w),\n        ...g\n      }, k = Sr(u, I), Le(y, k) === -w;\n    }\n    const m = $e(b, u), g = Ze(Xe, m), T = $e(h, u), y = h.epochNanoseconds;\n    let v = 0;\n    const S = qs(m, T);\n    let I, k;\n    if (Math.sign(S) === -w && v++, E() && (w === -1 || E()))\n      throw new RangeError(Kn);\n    const M = lt(ct(k, y));\n    return [m, I, M];\n  })(t, n, r, o);\n  var f, d;\n  return {\n    ...i === 6 ? (f = s, d = c, {\n      ...Ee,\n      days: Nd(f, d)\n    }) : e.N(s, c, i, a),\n    ...Lo(l)\n  };\n}\nfunction Md(e, t, n, r, o, i) {\n  const [a, s, c] = ((l, f, d) => {\n    let u = f, b = qs(l, f);\n    return Math.sign(b) === -d && (u = fn(f, -d), b += se * d), [l, u, b];\n  })(t, n, r);\n  return {\n    ...e.N(a, s, o, i),\n    ...Lo(c)\n  };\n}\nfunction $o(e, t, n, r, o, i) {\n  return {\n    ...Ee,\n    ...Hn(zo(ct(e, t), r, o, i), n)\n  };\n}\nfunction Cd(e, t, n) {\n  return {\n    ...Ee,\n    ...Hn(ct(e, t), n)\n  };\n}\nfunction Nd(e, t) {\n  return Uo(Oe(e), Oe(t));\n}\nfunction Uo(e, t) {\n  return Math.trunc((t - e) / xe);\n}\nfunction qs(e, t) {\n  return Lt(t) - Lt(e);\n}\nfunction Ko(e, t) {\n  if (e !== t)\n    throw new RangeError(np);\n  return e;\n}\nfunction xd(e) {\n  return this.m(e)[0];\n}\nfunction zd(e) {\n  return this.m(e)[1];\n}\nfunction Ls(e) {\n  const [t] = this.v(e);\n  return Uo(this.p(t), Oe(e)) + 1;\n}\nfunction Hs(e) {\n  const t = ay.exec(e);\n  if (!t)\n    throw new RangeError(tg(e));\n  return [parseInt(t[1]), !!t[2]];\n}\nfunction Tr(e, t) {\n  return \"M\" + Ye(e) + (t ? \"L\" : \"\");\n}\nfunction ho(e, t, n) {\n  return e + (t || n && e >= n ? 1 : 0);\n}\nfunction $s(e, t) {\n  return e - (t && e >= t ? 1 : 0);\n}\nfunction Bd(e, t) {\n  return (t + e) * (Math.sign(t) || 1) || 0;\n}\nfunction Fa(e) {\n  return pp[Dd(e)];\n}\nfunction Fd(e) {\n  return vg[Dd(e)];\n}\nfunction Dd(e) {\n  return cn(e.id || X);\n}\nfunction Qm(e) {\n  function t(o) {\n    return ((i, a) => ({\n      ...qd(i, a),\n      o: i.month,\n      day: parseInt(i.day)\n    }))(us(n, o), r);\n  }\n  const n = pc(e), r = cn(e);\n  return {\n    id: e,\n    h: Xm(t),\n    l: e0(t)\n  };\n}\nfunction Xm(e) {\n  return qe(((t) => {\n    const n = Oe(t);\n    return e(n);\n  }), WeakMap);\n}\nfunction e0(e) {\n  const t = e(0).year - Og;\n  return qe(((n) => {\n    let r, o = Bn(n - t), i = 0;\n    const a = [], s = [];\n    do\n      o += 400 * xe;\n    while ((r = e(o)).year <= n);\n    do\n      if (o += (1 - r.day) * xe, r.year === n && (a.push(o), s.push(r.o)), o -= xe, ++i > 100 || o < -rc)\n        throw new RangeError(Kn);\n    while ((r = e(o)).year >= n);\n    return {\n      i: a.reverse(),\n      u: ip(s.reverse())\n    };\n  }));\n}\nfunction qd(e, t) {\n  let n, r, o = Ld(e);\n  if (e.era) {\n    const i = pp[t], a = hp[t] || {};\n    i !== void 0 && (n = t === \"islamic\" ? \"ah\" : e.era.normalize(\"NFD\").toLowerCase().replace(/[^a-z0-9]/g, \"\"), n === \"bc\" || n === \"b\" ? n = \"bce\" : n === \"ad\" || n === \"a\" ? n = \"ce\" : n === \"beforeroc\" && (n = \"broc\"), n = a[n] || n, r = o, o = Bd(r, i[n] || 0));\n  }\n  return {\n    era: n,\n    eraYear: r,\n    year: o\n  };\n}\nfunction Ld(e) {\n  return parseInt(e.relatedYear || e.year);\n}\nfunction mo(e) {\n  const { year: t, o: n, day: r } = this.h(e), { u: o } = this.l(t);\n  return [t, o[n] + 1, r];\n}\nfunction hr(e, t = 1, n = 1) {\n  return this.l(e).i[t - 1] + (n - 1) * xe;\n}\nfunction Hd(e, t) {\n  const n = no.call(this, e);\n  return [$s(t, n), n === t];\n}\nfunction no(e) {\n  const t = wl(this, e), n = wl(this, e - 1), r = t.length;\n  if (r > n.length) {\n    const o = Fd(this);\n    if (o < 0)\n      return -o;\n    for (let i = 0; i < r; i++)\n      if (t[i] !== n[i])\n        return i + 1;\n  }\n}\nfunction Ur(e) {\n  return Uo(hr.call(this, e), hr.call(this, e + 1));\n}\nfunction _l(e, t) {\n  const { i: n } = this.l(e);\n  let r = t + 1, o = n;\n  return r > n.length && (r = 1, o = this.l(e + 1).i), Uo(n[t - 1], o[r - 1]);\n}\nfunction Kr(e) {\n  return this.l(e).i.length;\n}\nfunction $d(e) {\n  const t = this.h(e);\n  return [t.era, t.eraYear];\n}\nfunction wl(e, t) {\n  return Object.keys(e.l(t).u);\n}\nfunction Ar(e) {\n  return Go(Te(e));\n}\nfunction Go(e) {\n  if ((e = e.toLowerCase()) !== X && e !== Gn) {\n    const t = pc(e).resolvedOptions().calendar;\n    if (cn(e) !== cn(t))\n      throw new RangeError(tp(e));\n    return t;\n  }\n  return e;\n}\nfunction cn(e) {\n  return e === \"islamicc\" && (e = \"islamic\"), e.split(\"-\")[0];\n}\nfunction Ud(e, t) {\n  return (n) => n === X ? e : n === Gn || n === Ut ? Object.assign(Object.create(e), {\n    id: n\n  }) : Object.assign(Object.create(t), sy(n));\n}\nfunction t0(e, t, n, r) {\n  const o = Wt(n, r, kt, [], lp);\n  if (o.timeZone !== void 0) {\n    const i = n.F(o), a = Ir(o), s = e(o.timeZone);\n    return {\n      epochNanoseconds: Ln(t(s), {\n        ...i,\n        ...a\n      }, o.offset !== void 0 ? pn(o.offset) : void 0),\n      timeZone: s\n    };\n  }\n  return {\n    ...n.F(o),\n    ...Be\n  };\n}\nfunction n0(e, t, n, r, o, i) {\n  const a = Wt(n, o, kt, sp, lp), s = e(a.timeZone), [c, l, f] = Ro(i), d = n.F(a, No(c)), u = Ir(a, c);\n  return Je(Ln(t(s), {\n    ...d,\n    ...u\n  }, a.offset !== void 0 ? pn(a.offset) : void 0, l, f), s, r);\n}\nfunction r0(e, t, n) {\n  const r = Wt(e, t, kt, [], Pt), o = te(n);\n  return Qe(ze({\n    ...e.F(r, No(o)),\n    ...Ir(r, o)\n  }));\n}\nfunction o0(e, t, n, r = []) {\n  const o = Wt(e, t, kt, r);\n  return e.F(o, n);\n}\nfunction i0(e, t, n, r) {\n  const o = Wt(e, t, Zs, r);\n  return e.K(o, n);\n}\nfunction a0(e, t, n, r) {\n  const o = Wt(e, n, kt, Or);\n  return t && o.month !== void 0 && o.monthCode === void 0 && o.year === void 0 && (o.year = _t), e._(o, r);\n}\nfunction s0(e, t) {\n  return ht(Ir(He(e, Ha, [], 1), te(t)));\n}\nfunction c0(e) {\n  const t = He(e, Js);\n  return be(dn({\n    ...Ee,\n    ...t\n  }));\n}\nfunction Wt(e, t, n, r = [], o = []) {\n  return He(t, [...e.fields(n), ...o].sort(), r);\n}\nfunction He(e, t, n, r = !n) {\n  const o = {};\n  let i, a = 0;\n  for (const s of t) {\n    if (s === i)\n      throw new RangeError(V0(s));\n    if (s === \"constructor\" || s === \"__proto__\")\n      throw new RangeError(G0(s));\n    let c = e[s];\n    if (c !== void 0)\n      a = 1, Sl[s] && (c = Sl[s](c, s)), o[s] = c;\n    else if (n) {\n      if (n.includes(s))\n        throw new TypeError(Ks(s));\n      o[s] = dp[s];\n    }\n    i = s;\n  }\n  if (r && !a)\n    throw new TypeError(Qd(t));\n  return o;\n}\nfunction Ir(e, t) {\n  return Dn(hc({\n    ...dp,\n    ...e\n  }), t);\n}\nfunction l0(e, t, n, r, o) {\n  const { calendar: i, timeZone: a } = n, s = e(i), c = t(a), l = [...s.fields(kt), ...cp].sort(), f = ((m) => {\n    const g = $e(m, G), T = Er(g.offsetNanoseconds), y = Qo(m.calendar), [v, S, I] = y.v(g), [k, M] = y.q(v, S), N = Tr(k, M);\n    return {\n      ...my(g),\n      year: v,\n      monthCode: N,\n      day: I,\n      offset: T\n    };\n  })(n), d = He(r, l), u = s.k(f, d), b = {\n    ...f,\n    ...d\n  }, [h, w, E] = Ro(o, 2);\n  return Je(Ln(c, {\n    ...s.F(u, No(h)),\n    ...Dn(hc(b), h)\n  }, pn(b.offset), w, E), a, i);\n}\nfunction u0(e, t, n, r) {\n  const o = e(t.calendar), i = [...o.fields(kt), ...Pt].sort(), a = {\n    ...Gd(s = t),\n    hour: s.isoHour,\n    minute: s.isoMinute,\n    second: s.isoSecond,\n    millisecond: s.isoMillisecond,\n    microsecond: s.isoMicrosecond,\n    nanosecond: s.isoNanosecond\n  };\n  var s;\n  const c = He(n, i), l = te(r), f = o.k(a, c), d = {\n    ...a,\n    ...c\n  };\n  return Qe(ze({\n    ...o.F(f, No(l)),\n    ...Dn(hc(d), l)\n  }));\n}\nfunction f0(e, t, n, r) {\n  const o = e(t.calendar), i = o.fields(kt).sort(), a = Gd(t), s = He(n, i), c = o.k(a, s);\n  return o.F(c, r);\n}\nfunction d0(e, t, n, r) {\n  const o = e(t.calendar), i = o.fields(Zs).sort(), a = ((l) => {\n    const f = Qo(l.calendar), [d, u] = f.v(l), [b, h] = f.q(d, u);\n    return {\n      year: d,\n      monthCode: Tr(b, h)\n    };\n  })(t), s = He(n, i), c = o.k(a, s);\n  return o.K(c, r);\n}\nfunction p0(e, t, n, r) {\n  const o = e(t.calendar), i = o.fields(kt).sort(), a = ((l) => {\n    const f = Qo(l.calendar), [d, u, b] = f.v(l), [h, w] = f.q(d, u);\n    return {\n      monthCode: Tr(h, w),\n      day: b\n    };\n  })(t), s = He(n, i), c = o.k(a, s);\n  return o._(c, r);\n}\nfunction h0(e, t, n) {\n  return ht(((r, o, i) => Ir({\n    ...Ze(Ha, r),\n    ...He(o, Ha)\n  }, te(i)))(e, t, n));\n}\nfunction m0(e, t) {\n  return be((n = e, r = t, dn({\n    ...n,\n    ...He(r, Js)\n  })));\n  var n, r;\n}\nfunction Kd(e, t, n, r, o) {\n  t = Ze(n = e.fields(n), t), r = He(r, o = e.fields(o), []);\n  let i = e.k(t, r);\n  return i = He(i, [...n, ...o].sort(), []), e.F(i);\n}\nfunction li(e, t) {\n  const n = Fa(e), r = hp[e.id || \"\"] || {};\n  let { era: o, eraYear: i, year: a } = t;\n  if (o !== void 0 || i !== void 0) {\n    if (o === void 0 || i === void 0)\n      throw new TypeError(J0);\n    if (!n)\n      throw new RangeError(Z0);\n    const s = n[r[o] || o];\n    if (s === void 0)\n      throw new RangeError(X0(o));\n    const c = Bd(i, s);\n    if (a !== void 0 && a !== c)\n      throw new RangeError(Q0);\n    a = c;\n  } else if (a === void 0)\n    throw new TypeError(eg(n));\n  return a;\n}\nfunction Gr(e, t, n, r) {\n  let { month: o, monthCode: i } = t;\n  if (i !== void 0) {\n    const a = ((s, c, l, f) => {\n      const d = s.L(l), [u, b] = Hs(c);\n      let h = ho(u, b, d);\n      if (b) {\n        const w = Fd(s);\n        if (w === void 0)\n          throw new RangeError(er);\n        if (w > 0) {\n          if (h > w)\n            throw new RangeError(er);\n          if (d === void 0) {\n            if (f === 1)\n              throw new RangeError(er);\n            h--;\n          }\n        } else {\n          if (h !== -w)\n            throw new RangeError(er);\n          if (d === void 0 && f === 1)\n            throw new RangeError(er);\n        }\n      }\n      return h;\n    })(e, i, n, r);\n    if (o !== void 0 && o !== a)\n      throw new RangeError(ng);\n    o = a, r = 1;\n  } else if (o === void 0)\n    throw new TypeError(ep);\n  return Et(\"month\", o, 1, e.B(n), r);\n}\nfunction ui(e, t, n, r, o) {\n  return Ce(t, \"day\", 1, e.U(r, n), o);\n}\nfunction fi(e, t, n, r) {\n  let o = 0;\n  const i = [];\n  for (const a of n)\n    t[a] !== void 0 ? o = 1 : i.push(a);\n  if (Object.assign(e, t), o)\n    for (const a of r || i)\n      delete e[a];\n}\nfunction Gd(e) {\n  const t = Qo(e.calendar), [n, r, o] = t.v(e), [i, a] = t.q(n, r);\n  return {\n    year: n,\n    monthCode: Tr(i, a),\n    day: o\n  };\n}\nfunction g0(e) {\n  return It(dt(as(rs(e))));\n}\nfunction y0(e, t, n, r, o = X) {\n  return Je(dt(as(rs(n))), t(r), e(o));\n}\nfunction v0(e, t, n, r, o = 0, i = 0, a = 0, s = 0, c = 0, l = 0, f = X) {\n  return Qe(ze(ko(St(je, zn(Zo, [t, n, r, o, i, a, s, c, l])))), e(f));\n}\nfunction b0(e, t, n, r, o = X) {\n  return jt(Ve(un(St(je, {\n    isoYear: t,\n    isoMonth: n,\n    isoDay: r\n  }))), e(o));\n}\nfunction _0(e, t, n, r = X, o = 1) {\n  const i = je(t), a = je(n), s = e(r);\n  return fr(cs(un({\n    isoYear: i,\n    isoMonth: a,\n    isoDay: je(o)\n  })), s);\n}\nfunction w0(e, t, n, r = X, o = _t) {\n  const i = je(t), a = je(n), s = e(r);\n  return uo(Ve(un({\n    isoYear: je(o),\n    isoMonth: i,\n    isoDay: a\n  })), s);\n}\nfunction E0(e = 0, t = 0, n = 0, r = 0, o = 0, i = 0) {\n  return ht(Dn(St(je, zn(Xe, [e, t, n, r, o, i])), 1));\n}\nfunction S0(e = 0, t = 0, n = 0, r = 0, o = 0, i = 0, a = 0, s = 0, c = 0, l = 0) {\n  return be(dn(St(os, zn(oe, [e, t, n, r, o, i, a, s, c, l]))));\n}\nfunction T0(e, t, n = X) {\n  return Je(e.epochNanoseconds, t, n);\n}\nfunction A0(e) {\n  return It(e.epochNanoseconds);\n}\nfunction Vd(e, t) {\n  return Qe($e(t, e));\n}\nfunction Yd(e, t) {\n  return jt($e(t, e));\n}\nfunction Wd(e, t) {\n  return ht($e(t, e));\n}\nfunction I0(e, t, n, r) {\n  const o = ((i, a, s, c) => {\n    const l = ((f) => Ep(pt(f)))(c);\n    return Sr(i(a), s, l);\n  })(e, n, t, r);\n  return Je(dt(o), n, t.calendar);\n}\nfunction j0(e, t, n, r, o) {\n  const i = e(o.timeZone), a = o.plainTime, s = a !== void 0 ? t(a) : void 0, c = n(i);\n  let l;\n  return l = s ? Sr(c, {\n    ...r,\n    ...s\n  }) : $t(c, {\n    ...r,\n    ...Be\n  }), Je(l, i, r.calendar);\n}\nfunction O0(e, t = Be) {\n  return Qe(ze({\n    ...e,\n    ...t\n  }));\n}\nfunction P0(e, t, n) {\n  return ((r, o) => {\n    const i = Wt(r, o, up);\n    return r.K(i, void 0);\n  })(e(t.calendar), n);\n}\nfunction k0(e, t, n) {\n  return ((r, o) => {\n    const i = Wt(r, o, fp);\n    return r._(i);\n  })(e(t.calendar), n);\n}\nfunction R0(e, t, n, r) {\n  return ((o, i, a) => Kd(o, i, up, _r(a), Or))(e(t.calendar), n, r);\n}\nfunction M0(e, t, n, r) {\n  return ((o, i, a) => Kd(o, i, fp, _r(a), Vs))(e(t.calendar), n, r);\n}\nfunction C0(e) {\n  return It(dt(co(os(e), Ot)));\n}\nfunction N0(e) {\n  return It(dt(as(rs(e))));\n}\nfunction hn(e, t, n) {\n  const r = new Set(n);\n  return (o, i) => {\n    const a = n && Kc(o, n);\n    if (!Kc(o = ((s, c) => {\n      const l = {};\n      for (const f in c)\n        s.has(f) || (l[f] = c[f]);\n      return l;\n    })(r, o), e)) {\n      if (i && a)\n        throw new TypeError(\"Invalid formatting options\");\n      o = {\n        ...t,\n        ...o\n      };\n    }\n    return n && (o.timeZone = mn, [\"full\", \"long\"].includes(o.J) && (o.J = \"medium\")), o;\n  };\n}\nfunction Zt(e, t = Zd, n = 0) {\n  const [r, , , o] = e;\n  return (i, a = Ny, ...s) => {\n    const c = t(o && o(...s), i, a, r, n), l = c.resolvedOptions();\n    return [c, ...x0(e, l, s)];\n  };\n}\nfunction Zd(e, t, n, r, o) {\n  if (n = r(n, o), e) {\n    if (n.timeZone !== void 0)\n      throw new TypeError(hg);\n    n.timeZone = e;\n  }\n  return new Ft(t, n);\n}\nfunction x0(e, t, n) {\n  const [, r, o] = e;\n  return n.map(((i) => (i.calendar && ((a, s, c) => {\n    if ((c || a !== X) && a !== s)\n      throw new RangeError(np);\n  })(i.calendar, t.calendar, o), r(i, t))));\n}\nfunction z0(e, t, n) {\n  const r = t.timeZone, o = e(r), i = {\n    ...$e(t, o),\n    ...n || Be\n  };\n  let a;\n  return a = n ? Ln(o, i, i.offsetNanoseconds, 2) : $t(o, i), Je(a, r, t.calendar);\n}\nfunction B0(e, t = Be) {\n  return Qe(ze({\n    ...e,\n    ...t\n  }));\n}\nfunction Us(e, t) {\n  return {\n    ...e,\n    calendar: t\n  };\n}\nfunction F0(e, t) {\n  return {\n    ...e,\n    timeZone: t\n  };\n}\nfunction di(e) {\n  const t = Da();\n  return Fn(t, e.R(t));\n}\nfunction Da() {\n  return co(Date.now(), Ot);\n}\nfunction Xn() {\n  return Tl || (Tl = new Ft().resolvedOptions().timeZone);\n}\nconst D0 = (e, t) => `Non-integer ${e}: ${t}`, q0 = (e, t) => `Non-positive ${e}: ${t}`, L0 = (e, t) => `Non-finite ${e}: ${t}`, H0 = (e) => `Cannot convert bigint to ${e}`, $0 = (e) => `Invalid bigint: ${e}`, U0 = \"Cannot convert Symbol to string\", K0 = \"Invalid object\", Jd = (e, t, n, r, o) => o ? Jd(e, o[t], o[n], o[r]) : Jt(e, t) + `; must be between ${n}-${r}`, Jt = (e, t) => `Invalid ${e}: ${t}`, Ks = (e) => `Missing ${e}`, G0 = (e) => `Invalid field ${e}`, V0 = (e) => `Duplicate field ${e}`, Qd = (e) => \"No valid fields: \" + e.join(), Y0 = \"Invalid bag\", Xd = (e, t, n) => Jt(e, t) + \"; must be \" + Object.keys(n).join(), W0 = \"Cannot use valueOf\", qa = \"Invalid calling context\", Z0 = \"Forbidden era/eraYear\", J0 = \"Mismatching era/eraYear\", Q0 = \"Mismatching year/eraYear\", X0 = (e) => `Invalid era: ${e}`, eg = (e) => \"Missing year\" + (e ? \"/era/eraYear\" : \"\"), tg = (e) => `Invalid monthCode: ${e}`, ng = \"Mismatching month/monthCode\", ep = \"Missing month/monthCode\", er = \"Invalid leap month\", Kn = \"Invalid protocol results\", tp = (e) => Jt(\"Calendar\", e), np = \"Mismatching Calendars\", rp = (e) => Jt(\"TimeZone\", e), op = \"Mismatching TimeZones\", rg = \"Forbidden ICU TimeZone\", og = \"Out-of-bounds offset\", ig = \"Out-of-bounds TimeZone gap\", ag = \"Invalid TimeZone offset\", sg = \"Ambiguous offset\", Qt = \"Out-of-bounds date\", cg = \"Out-of-bounds duration\", lg = \"Cannot mix duration signs\", Vo = \"Missing relativeTo\", ug = \"Cannot use large units\", fg = \"Required smallestUnit or largestUnit\", dg = \"smallestUnit > largestUnit\", Ne = (e) => `Cannot parse: ${e}`, bt = (e) => `Invalid substring: ${e}`, pg = (e) => `Cannot format ${e}`, pi = \"Mismatching types for formatting\", hg = \"Cannot specify TimeZone\", ip = /* @__PURE__ */ J(Ao, ((e, t) => t)), Cn = /* @__PURE__ */ J(Ao, ((e, t, n) => n)), Ye = /* @__PURE__ */ J(so, 2), La = {\n  nanosecond: 0,\n  microsecond: 1,\n  millisecond: 2,\n  second: 3,\n  minute: 4,\n  hour: 5,\n  day: 6,\n  week: 7,\n  month: 8,\n  year: 9\n}, Gs = /* @__PURE__ */ Object.keys(La), xe = 864e5, ap = 1e3, jr = 1e3, Ot = 1e6, at = 1e9, Yo = 6e10, Wo = 36e11, se = 864e11, ut = [1, jr, Ot, at, Yo, Wo, se], Pt = /* @__PURE__ */ Gs.slice(0, 6), Ha = /* @__PURE__ */ br(Pt), mg = [\"offset\"], sp = [\"timeZone\"], cp = /* @__PURE__ */ Pt.concat(mg), lp = /* @__PURE__ */ cp.concat(sp), $a = [\"era\", \"eraYear\"], gg = /* @__PURE__ */ $a.concat([\"year\"]), Vs = [\"year\"], Ys = [\"monthCode\"], Ws = /* @__PURE__ */ [\"month\"].concat(Ys), Or = [\"day\"], Zs = /* @__PURE__ */ Ws.concat(Vs), up = /* @__PURE__ */ Ys.concat(Vs), kt = /* @__PURE__ */ Or.concat(Zs), yg = /* @__PURE__ */ Or.concat(Ws), fp = /* @__PURE__ */ Or.concat(Ys), dp = /* @__PURE__ */ Cn(Pt, 0), X = \"iso8601\", Gn = \"gregory\", Ut = \"japanese\", pp = {\n  [Gn]: {\n    \"gregory-inverse\": -1,\n    gregory: 0\n  },\n  [Ut]: {\n    \"japanese-inverse\": -1,\n    japanese: 0,\n    meiji: 1867,\n    taisho: 1911,\n    showa: 1925,\n    heisei: 1988,\n    reiwa: 2018\n  },\n  ethiopic: {\n    ethioaa: 0,\n    ethiopic: 5500\n  },\n  coptic: {\n    \"coptic-inverse\": -1,\n    coptic: 0\n  },\n  roc: {\n    \"roc-inverse\": -1,\n    roc: 0\n  },\n  buddhist: {\n    be: 0\n  },\n  islamic: {\n    ah: 0\n  },\n  indian: {\n    saka: 0\n  },\n  persian: {\n    ap: 0\n  }\n}, hp = {\n  [Gn]: {\n    bce: \"gregory-inverse\",\n    ce: \"gregory\"\n  },\n  [Ut]: {\n    bce: \"japanese-inverse\",\n    ce: \"japanese\"\n  },\n  ethiopic: {\n    era0: \"ethioaa\",\n    era1: \"ethiopic\"\n  },\n  coptic: {\n    era0: \"coptic-inverse\",\n    era1: \"coptic\"\n  },\n  roc: {\n    broc: \"roc-inverse\",\n    minguo: \"roc\"\n  }\n}, vg = {\n  chinese: 13,\n  dangi: 13,\n  hebrew: -6\n}, Te = /* @__PURE__ */ J(ts, \"string\"), bg = /* @__PURE__ */ J(ts, \"boolean\"), _g = /* @__PURE__ */ J(ts, \"number\"), oe = /* @__PURE__ */ Gs.map(((e) => e + \"s\")), Js = /* @__PURE__ */ br(oe), wg = /* @__PURE__ */ oe.slice(0, 6), mp = /* @__PURE__ */ oe.slice(6), Eg = /* @__PURE__ */ mp.slice(1), Sg = /* @__PURE__ */ ip(oe), Ee = /* @__PURE__ */ Cn(oe, 0), Qs = /* @__PURE__ */ Cn(wg, 0), Xs = /* @__PURE__ */ J(qf, oe), Xe = [\"isoNanosecond\", \"isoMicrosecond\", \"isoMillisecond\", \"isoSecond\", \"isoMinute\", \"isoHour\"], ec = [\"isoDay\", \"isoMonth\", \"isoYear\"], Zo = /* @__PURE__ */ Xe.concat(ec), tc = /* @__PURE__ */ br(ec), gp = /* @__PURE__ */ br(Xe), Tg = /* @__PURE__ */ br(Zo), Be = /* @__PURE__ */ Cn(gp, 0), Ag = /* @__PURE__ */ J(qf, Zo), nc = 1e8, rc = nc * xe, Ig = [nc, 0], jg = [-nc, 0], mr = 275760, gr = -271821, Ft = Intl.DateTimeFormat, yp = \"en-GB\", Og = 1970, _t = 1972, Ct = 12, Pg = /* @__PURE__ */ Bn(1868, 9, 8), kg = /* @__PURE__ */ qe(fm, WeakMap), go = \"smallestUnit\", Ua = \"unit\", sr = \"roundingIncrement\", hi = \"fractionalSecondDigits\", vp = \"relativeTo\", mi = \"direction\", bp = {\n  constrain: 0,\n  reject: 1\n}, Rg = /* @__PURE__ */ Object.keys(bp), Mg = {\n  compatible: 0,\n  reject: 1,\n  earlier: 2,\n  later: 3\n}, Cg = {\n  reject: 0,\n  use: 1,\n  prefer: 2,\n  ignore: 3\n}, Ng = {\n  auto: 0,\n  never: 1,\n  critical: 2,\n  always: 3\n}, xg = {\n  auto: 0,\n  never: 1,\n  critical: 2\n}, zg = {\n  auto: 0,\n  never: 1\n}, Bg = {\n  floor: 0,\n  halfFloor: 1,\n  ceil: 2,\n  halfCeil: 3,\n  trunc: 4,\n  halfTrunc: 5,\n  expand: 6,\n  halfExpand: 7,\n  halfEven: 8\n}, Fg = {\n  previous: -1,\n  next: 1\n}, Pr = /* @__PURE__ */ J(ys, go), _p = /* @__PURE__ */ J(ys, \"largestUnit\"), Dg = /* @__PURE__ */ J(ys, Ua), wp = /* @__PURE__ */ J(Gt, \"overflow\", bp), Ep = /* @__PURE__ */ J(Gt, \"disambiguation\", Mg), qg = /* @__PURE__ */ J(Gt, \"offset\", Cg), oc = /* @__PURE__ */ J(Gt, \"calendarName\", Ng), Lg = /* @__PURE__ */ J(Gt, \"timeZoneName\", xg), Hg = /* @__PURE__ */ J(Gt, \"offset\", zg), kr = /* @__PURE__ */ J(Gt, \"roundingMode\", Bg), ic = \"PlainYearMonth\", ac = \"PlainMonthDay\", Rr = \"PlainDate\", Vn = \"PlainDateTime\", sc = \"PlainTime\", Xt = \"ZonedDateTime\", cc = \"Instant\", lc = \"Duration\", $g = [Math.floor, (e) => $r(e) ? Math.floor(e) : Math.round(e), Math.ceil, (e) => $r(e) ? Math.ceil(e) : Math.round(e), Math.trunc, (e) => $r(e) ? Math.trunc(e) || 0 : Math.round(e), (e) => e < 0 ? Math.floor(e) : Math.ceil(e), (e) => Math.sign(e) * Math.round(Math.abs(e)) || 0, (e) => $r(e) ? (e = Math.trunc(e) || 0) + e % 2 : Math.round(e)], mn = \"UTC\", ro = 5184e3, Ug = /* @__PURE__ */ lo(1847), Kg = /* @__PURE__ */ lo(/* @__PURE__ */ (/* @__PURE__ */ new Date()).getUTCFullYear() + 10), Gg = /0+$/, $e = /* @__PURE__ */ qe(Im, WeakMap), El = 2 ** 32 - 1, G = /* @__PURE__ */ qe(((e) => {\n  const t = Fs(e);\n  return typeof t == \"object\" ? new Yg(t) : new Vg(t || 0);\n}));\nclass Vg {\n  constructor(t) {\n    this.$ = t;\n  }\n  R() {\n    return this.$;\n  }\n  I(t) {\n    return ((n) => {\n      const r = _e({\n        ...n,\n        ...Be\n      });\n      if (!r || Math.abs(r[0]) > 1e8)\n        throw new RangeError(Qt);\n    })(t), [ls(t, this.$)];\n  }\n  O() {\n  }\n}\nclass Yg {\n  constructor(t) {\n    this.nn = ((n) => {\n      function r(l) {\n        const f = ur(l, s, c), [d, u] = dl(f), b = i(d), h = i(u);\n        return b === h ? b : o(a(d, u), b, h, l);\n      }\n      function o(l, f, d, u) {\n        let b, h;\n        for (; (u === void 0 || (b = u < l[0] ? f : u >= l[1] ? d : void 0) === void 0) && (h = l[1] - l[0]); ) {\n          const w = l[0] + Math.floor(h / 2);\n          n(w) === d ? l[1] = w : l[0] = w + 1;\n        }\n        return b;\n      }\n      const i = qe(n), a = qe(km);\n      let s = Ug, c = Kg;\n      return {\n        tn(l) {\n          const f = r(l - 86400), d = r(l + 86400), u = l - f, b = l - d;\n          if (f === d)\n            return [u];\n          const h = r(u);\n          return h === r(b) ? [l - h] : f > d ? [u, b] : [];\n        },\n        rn: r,\n        O(l, f) {\n          const d = ur(l, s, c);\n          let [u, b] = dl(d);\n          const h = ro * f, w = f < 0 ? () => b > s || (s = d, 0) : () => u < c || (c = d, 0);\n          for (; w(); ) {\n            const E = i(u), m = i(b);\n            if (E !== m) {\n              const g = a(u, b);\n              o(g, E, m);\n              const T = g[0];\n              if ((Bt(T, l) || 1) === f)\n                return T;\n            }\n            u += h, b += h;\n          }\n        }\n      };\n    })(/* @__PURE__ */ ((n) => (r) => {\n      const o = us(n, r * ap);\n      return lo(Ld(o), parseInt(o.month), parseInt(o.day), parseInt(o.hour), parseInt(o.minute), parseInt(o.second)) - r;\n    })(t));\n  }\n  R(t) {\n    return this.nn.rn(((n) => Yc(n)[0])(t)) * at;\n  }\n  I(t) {\n    const [n, r] = [lo((o = t).isoYear, o.isoMonth, o.isoDay, o.isoHour, o.isoMinute, o.isoSecond), o.isoMillisecond * Ot + o.isoMicrosecond * jr + o.isoNanosecond];\n    var o;\n    return this.nn.tn(n).map(((i) => dt(an(co(i, at), r))));\n  }\n  O(t, n) {\n    const [r, o] = Yc(t), i = this.nn.O(r + (n > 0 || o ? 1 : 0), n);\n    if (i !== void 0)\n      return co(i, at);\n  }\n}\nconst uc = \"([+-])\", oo = \"(?:[.,](\\\\d{1,9}))?\", Sp = `(?:(?:${uc}(\\\\d{6}))|(\\\\d{4}))-?(\\\\d{2})`, fc = \"(\\\\d{2})(?::?(\\\\d{2})(?::?(\\\\d{2})\" + oo + \")?)?\", dc = uc + fc, Wg = Sp + \"-?(\\\\d{2})(?:[T ]\" + fc + \"(Z|\" + dc + \")?)?\", Tp = \"\\\\[(!?)([^\\\\]]*)\\\\]\", Jo = `((?:${Tp}){0,9})`, Zg = /* @__PURE__ */ $n(Sp + Jo), Jg = /* @__PURE__ */ $n(\"(?:--)?(\\\\d{2})-?(\\\\d{2})\" + Jo), Qg = /* @__PURE__ */ $n(Wg + Jo), Xg = /* @__PURE__ */ $n(\"T?\" + fc + \"(?:\" + dc + \")?\" + Jo), ey = /* @__PURE__ */ $n(dc), ty = /* @__PURE__ */ new RegExp(Tp, \"g\"), ny = /* @__PURE__ */ $n(`${uc}?P(\\\\d+Y)?(\\\\d+M)?(\\\\d+W)?(\\\\d+D)?(?:T(?:(\\\\d+)${oo}H)?(?:(\\\\d+)${oo}M)?(?:(\\\\d+)${oo}S)?)?`), ry = /* @__PURE__ */ qe(((e) => new Ft(yp, {\n  timeZone: e,\n  era: \"short\",\n  year: \"numeric\",\n  month: \"numeric\",\n  day: \"numeric\",\n  hour: \"numeric\",\n  minute: \"numeric\",\n  second: \"numeric\"\n}))), oy = /^(AC|AE|AG|AR|AS|BE|BS|CA|CN|CS|CT|EA|EC|IE|IS|JS|MI|NE|NS|PL|PN|PR|PS|SS|VS)T$/, iy = /[^\\w\\/:+-]+/, ay = /^M(\\d{2})(L?)$/, sy = /* @__PURE__ */ qe(Qm), pc = /* @__PURE__ */ qe(((e) => new Ft(yp, {\n  calendar: e,\n  timeZone: mn,\n  era: \"short\",\n  year: \"numeric\",\n  month: \"short\",\n  day: \"numeric\"\n}))), Ap = {\n  P(e, t, n) {\n    const r = te(n);\n    let o, { years: i, months: a, weeks: s, days: c } = t;\n    if (c += we(t, 5)[0], i || a)\n      o = ((l, f, d, u, b) => {\n        let [h, w, E] = l.v(f);\n        if (d) {\n          const [m, g] = l.q(h, w);\n          h += d, w = ho(m, g, l.L(h)), w = Et(\"month\", w, 1, l.B(h), b);\n        }\n        return u && ([h, w] = l.un(h, w, u)), E = Et(\"day\", E, 1, l.U(h, w), b), l.p(h, w, E);\n      })(this, e, i, a, r);\n    else {\n      if (!s && !c)\n        return e;\n      o = Oe(e);\n    }\n    if (o === void 0)\n      throw new RangeError(Qt);\n    return o += (7 * s + c) * xe, Ve(Po(o));\n  },\n  N(e, t, n) {\n    if (n <= 7) {\n      let c = 0, l = Nd({\n        ...e,\n        ...Be\n      }, {\n        ...t,\n        ...Be\n      });\n      return n === 7 && ([c, l] = qt(l, 7)), {\n        ...Ee,\n        weeks: c,\n        days: l\n      };\n    }\n    const r = this.v(e), o = this.v(t);\n    let [i, a, s] = ((c, l, f, d, u, b, h) => {\n      let w = u - l, E = b - f, m = h - d;\n      if (w || E) {\n        const g = Math.sign(w || E);\n        let T = c.U(u, b), y = 0;\n        if (Math.sign(m) === -g) {\n          const v = T;\n          [u, b] = c.un(u, b, -g), w = u - l, E = b - f, T = c.U(u, b), y = g < 0 ? -v : T;\n        }\n        if (m = h - Math.min(d, T) + y, w) {\n          const [v, S] = c.q(l, f), [I, k] = c.q(u, b);\n          if (E = I - v || Number(k) - Number(S), Math.sign(E) === -g) {\n            const M = g < 0 && -c.B(u);\n            w = (u -= g) - l, E = b - ho(v, S, c.L(u)) + (M || c.B(u));\n          }\n        }\n      }\n      return [w, E, m];\n    })(this, ...r, ...o);\n    return n === 8 && (a += this.cn(i, r[0]), i = 0), {\n      ...Ee,\n      years: i,\n      months: a,\n      days: s\n    };\n  },\n  F(e, t) {\n    const n = te(t), r = li(this, e), o = Gr(this, e, r, n), i = ui(this, e, o, r, n);\n    return jt(Ve(this.V(r, o, i)), this.id || X);\n  },\n  K(e, t) {\n    const n = te(t), r = li(this, e), o = Gr(this, e, r, n);\n    return fr(cs(this.V(r, o, 1)), this.id || X);\n  },\n  _(e, t) {\n    const n = te(t);\n    let r, o, i, a = e.eraYear !== void 0 || e.year !== void 0 ? li(this, e) : void 0;\n    const s = !this.id;\n    if (a === void 0 && s && (a = _t), a !== void 0) {\n      const d = Gr(this, e, a, n);\n      r = ui(this, e, d, a, n);\n      const u = this.L(a);\n      o = $s(d, u), i = d === u;\n    } else {\n      if (e.monthCode === void 0)\n        throw new TypeError(ep);\n      if ([o, i] = Hs(e.monthCode), this.id && this.id !== Gn && this.id !== Ut)\n        if (this.id && cn(this.id) === \"coptic\" && n === 0) {\n          const d = i || o !== 13 ? 30 : 6;\n          r = e.day, r = ur(r, 1, d);\n        } else if (this.id && cn(this.id) === \"chinese\" && n === 0) {\n          const d = !i || o !== 1 && o !== 9 && o !== 10 && o !== 11 && o !== 12 ? 30 : 29;\n          r = e.day, r = ur(r, 1, d);\n        } else\n          r = e.day;\n      else\n        r = ui(this, e, Gr(this, e, _t, n), _t, n);\n    }\n    const c = this.G(o, i, r);\n    if (!c)\n      throw new RangeError(\"Cannot guess year\");\n    const [l, f] = c;\n    return uo(Ve(this.V(l, f, r)), this.id || X);\n  },\n  fields(e) {\n    return Fa(this) && e.includes(\"year\") ? [...e, ...$a] : e;\n  },\n  k(e, t) {\n    const n = Object.assign(/* @__PURE__ */ Object.create(null), e);\n    return fi(n, t, Ws), Fa(this) && (fi(n, t, gg), this.id === Ut && fi(n, t, yg, $a)), n;\n  },\n  inLeapYear(e) {\n    const [t] = this.v(e);\n    return this.sn(t);\n  },\n  monthsInYear(e) {\n    const [t] = this.v(e);\n    return this.B(t);\n  },\n  daysInMonth(e) {\n    const [t, n] = this.v(e);\n    return this.U(t, n);\n  },\n  daysInYear(e) {\n    const [t] = this.v(e);\n    return this.fn(t);\n  },\n  dayOfYear: Ls,\n  era(e) {\n    return this.hn(e)[0];\n  },\n  eraYear(e) {\n    return this.hn(e)[1];\n  },\n  monthCode(e) {\n    const [t, n] = this.v(e), [r, o] = this.q(t, n);\n    return Tr(r, o);\n  },\n  dayOfWeek: Xf,\n  daysInWeek() {\n    return 7;\n  }\n}, cy = {\n  v: fs,\n  hn: ed,\n  q: Wf\n}, ly = {\n  dayOfYear: Ls,\n  v: fs,\n  p: Bn\n}, uy = /* @__PURE__ */ Object.assign({}, ly, {\n  weekOfYear: xd,\n  yearOfWeek: zd,\n  m(e) {\n    function t(b) {\n      return (7 - b < r ? 7 : 0) - b;\n    }\n    function n(b) {\n      const h = Qf(u + b), w = b || 1, E = t(ar(c + h * w, 7));\n      return f = (h + (E - l) * w) / 7;\n    }\n    const r = this.id ? 1 : 4, o = Xf(e), i = this.dayOfYear(e), a = ar(o - 1, 7), s = i - 1, c = ar(a - s, 7), l = t(c);\n    let f, d = Math.floor((s - l) / 7) + 1, u = e.isoYear;\n    return d ? d > n(0) && (d = 1, u++) : (d = n(-1), u--), [d, u, f];\n  }\n}), fy = /* @__PURE__ */ Object.assign({}, Ap, uy, {\n  v: fs,\n  hn: ed,\n  q: Wf,\n  G(e, t) {\n    if (!t)\n      return [_t, e];\n  },\n  sn: ds,\n  L() {\n  },\n  B: Zf,\n  cn: (e) => e * Ct,\n  U: Jf,\n  fn: Qf,\n  V: (e, t, n) => ({\n    isoYear: e,\n    isoMonth: t,\n    isoDay: n\n  }),\n  p: Bn,\n  un: (e, t, n) => (e += Io(n, Ct), (t += Xa(n, Ct)) < 1 ? (e--, t += Ct) : t > Ct && (e++, t -= Ct), [e, t]),\n  year(e) {\n    return e.isoYear;\n  },\n  month(e) {\n    return e.isoMonth;\n  },\n  day: (e) => e.isoDay\n}), dy = {\n  v: mo,\n  hn: $d,\n  q: Hd\n}, py = {\n  dayOfYear: Ls,\n  v: mo,\n  p: hr,\n  weekOfYear: xd,\n  yearOfWeek: zd,\n  m() {\n    return [];\n  }\n}, hy = /* @__PURE__ */ Object.assign({}, Ap, py, {\n  v: mo,\n  hn: $d,\n  q: Hd,\n  G(e, t, n) {\n    const r = this.id && cn(this.id) === \"chinese\" ? ((l, f, d) => {\n      if (f)\n        switch (l) {\n          case 1:\n            return 1651;\n          case 2:\n            return d < 30 ? 1947 : 1765;\n          case 3:\n            return d < 30 ? 1966 : 1955;\n          case 4:\n            return d < 30 ? 1963 : 1944;\n          case 5:\n            return d < 30 ? 1971 : 1952;\n          case 6:\n            return d < 30 ? 1960 : 1941;\n          case 7:\n            return d < 30 ? 1968 : 1938;\n          case 8:\n            return d < 30 ? 1957 : 1718;\n          case 9:\n            return 1832;\n          case 10:\n            return 1870;\n          case 11:\n            return 1814;\n          case 12:\n            return 1890;\n        }\n      return 1972;\n    })(e, t, n) : _t;\n    let [o, i, a] = mo.call(this, {\n      isoYear: r,\n      isoMonth: Ct,\n      isoDay: 31\n    });\n    const s = no.call(this, o), c = i === s;\n    (Bt(e, $s(i, s)) || Bt(Number(t), Number(c)) || Bt(n, a)) === 1 && o--;\n    for (let l = 0; l < 100; l++) {\n      const f = o - l, d = no.call(this, f), u = ho(e, t, d);\n      if (t === (u === d) && n <= _l.call(this, f, u))\n        return [f, u];\n    }\n  },\n  sn(e) {\n    const t = Ur.call(this, e);\n    return t > Ur.call(this, e - 1) && t > Ur.call(this, e + 1);\n  },\n  L: no,\n  B: Kr,\n  cn(e, t) {\n    const n = t + e, r = Math.sign(e), o = r < 0 ? -1 : 0;\n    let i = 0;\n    for (let a = t; a !== n; a += r)\n      i += Kr.call(this, a + o);\n    return i;\n  },\n  U: _l,\n  fn: Ur,\n  V(e, t, n) {\n    return Po(hr.call(this, e, t, n));\n  },\n  p: hr,\n  un(e, t, n) {\n    if (n) {\n      if (t += n, !Number.isSafeInteger(t))\n        throw new RangeError(Qt);\n      if (n < 0)\n        for (; t < 1; )\n          t += Kr.call(this, --e);\n      else {\n        let r;\n        for (; t > (r = Kr.call(this, e)); )\n          t -= r, e++;\n      }\n    }\n    return [e, t];\n  },\n  year(e) {\n    return this.h(e).year;\n  },\n  month(e) {\n    const { year: t, o: n } = this.h(e), { u: r } = this.l(t);\n    return r[n] + 1;\n  },\n  day(e) {\n    return this.h(e).day;\n  }\n}), Qo = /* @__PURE__ */ Ud(cy, dy), H = /* @__PURE__ */ Ud(fy, hy), Sl = {\n  era: to,\n  eraYear: je,\n  year: je,\n  month: Vc,\n  monthCode(e) {\n    const t = to(e);\n    return Hs(t), t;\n  },\n  day: Vc,\n  .../* @__PURE__ */ Cn(Pt, je),\n  .../* @__PURE__ */ Cn(oe, os),\n  offset(e) {\n    const t = to(e);\n    return pn(t), t;\n  }\n}, hc = /* @__PURE__ */ J(Ff, Pt, Xe), my = /* @__PURE__ */ J(Ff, Xe, Pt), Dt = \"numeric\", Mr = [\"timeZoneName\"], Ip = {\n  month: Dt,\n  day: Dt\n}, mc = {\n  year: Dt,\n  month: Dt\n}, gc = /* @__PURE__ */ Object.assign({}, mc, {\n  day: Dt\n}), yc = {\n  hour: Dt,\n  minute: Dt,\n  second: Dt\n}, vc = /* @__PURE__ */ Object.assign({}, gc, yc), gy = /* @__PURE__ */ Object.assign({}, vc, {\n  timeZoneName: \"short\"\n}), yy = /* @__PURE__ */ Object.keys(mc), vy = /* @__PURE__ */ Object.keys(Ip), by = /* @__PURE__ */ Object.keys(gc), _y = /* @__PURE__ */ Object.keys(yc), bc = [\"dateStyle\"], wy = /* @__PURE__ */ yy.concat(bc), Ey = /* @__PURE__ */ vy.concat(bc), _c = /* @__PURE__ */ by.concat(bc, [\"weekday\"]), Cr = /* @__PURE__ */ _y.concat([\"dayPeriod\", \"timeStyle\", \"fractionalSecondDigits\"]), wc = /* @__PURE__ */ _c.concat(Cr), Sy = /* @__PURE__ */ Mr.concat(Cr), Ty = /* @__PURE__ */ Mr.concat(_c), Ay = /* @__PURE__ */ Mr.concat([\"day\", \"weekday\"], Cr), Iy = /* @__PURE__ */ Mr.concat([\"year\", \"weekday\"], Cr), jy = /* @__PURE__ */ hn(wc, vc), Oy = /* @__PURE__ */ hn(wc, gy), Py = /* @__PURE__ */ hn(wc, vc, Mr), ky = /* @__PURE__ */ hn(_c, gc, Sy), Ry = /* @__PURE__ */ hn(Cr, yc, Ty), My = /* @__PURE__ */ hn(wy, mc, Ay), Cy = /* @__PURE__ */ hn(Ey, Ip, Iy), Ny = {}, jp = new Ft(void 0, {\n  calendar: X\n}).resolvedOptions().calendar === X, Op = [jy, vs], xy = [Oy, vs, 0, (e, t) => {\n  const n = e.timeZone;\n  if (t && t.timeZone !== n)\n    throw new RangeError(op);\n  return n;\n}], Pp = [Py, Oe], kp = [ky, Oe], Rp = [Ry, (e) => Lt(e) / Ot], Mp = [My, Oe, jp], Cp = [Cy, Oe, jp];\nlet Tl;\nfunction en(e, t, n, r, o) {\n  function i(...c) {\n    if (!(this instanceof i))\n      throw new TypeError(qa);\n    jl(this, t(...c));\n  }\n  function a(c, l) {\n    return Object.defineProperties((function(...f) {\n      return c.call(this, s(this), ...f);\n    }), lr(l));\n  }\n  function s(c) {\n    const l = Me(c);\n    if (!l || l.branding !== e)\n      throw new TypeError(qa);\n    return l;\n  }\n  return Object.defineProperties(i.prototype, {\n    ...cm(St(a, n)),\n    ...kn(St(a, r)),\n    ...Qa(\"Temporal.\" + e)\n  }), Object.defineProperties(i, {\n    ...kn(o),\n    ...lr(e)\n  }), [i, (c) => {\n    const l = Object.create(i.prototype);\n    return jl(l, c), l;\n  }, s];\n}\nfunction Yn(e) {\n  if (Me(e) || e.calendar !== void 0 || e.timeZone !== void 0)\n    throw new TypeError(Y0);\n  return e;\n}\nfunction Nr(e) {\n  return Np(e) || X;\n}\nfunction Np(e) {\n  const { calendar: t } = e;\n  if (t !== void 0)\n    return Xo(t);\n}\nfunction Xo(e) {\n  if (ke(e)) {\n    const { calendar: t } = Me(e) || {};\n    if (!t)\n      throw new TypeError(tp(e));\n    return t;\n  }\n  return ((t) => Go(Dm(Te(t))))(e);\n}\nfunction Ec(e) {\n  const t = {};\n  for (const n in e)\n    t[n] = (r) => {\n      const { calendar: o } = r;\n      return H(o)[n](r);\n    };\n  return t;\n}\nfunction tn() {\n  throw new TypeError(W0);\n}\nfunction De(e) {\n  if (ke(e)) {\n    const { timeZone: t } = Me(e) || {};\n    if (!t)\n      throw new TypeError(rp(e));\n    return t;\n  }\n  return ((t) => Bs(qm(Te(t))))(e);\n}\nfunction ve(e) {\n  if (ke(e)) {\n    const t = Me(e);\n    return t && t.branding === lc ? t : c0(e);\n  }\n  return Fm(e);\n}\nfunction tr(e) {\n  if (e !== void 0) {\n    if (ke(e)) {\n      const t = Me(e) || {};\n      switch (t.branding) {\n        case Xt:\n        case Rr:\n          return t;\n        case Vn:\n          return jt(t);\n      }\n      const n = Nr(e);\n      return {\n        ...t0(De, G, H(n), e),\n        calendar: n\n      };\n    }\n    return Mm(e);\n  }\n}\nfunction Nt(e, t) {\n  if (ke(e)) {\n    const r = Me(e) || {};\n    switch (r.branding) {\n      case sc:\n        return te(t), r;\n      case Vn:\n        return te(t), ht(r);\n      case Xt:\n        return te(t), Wd(G, r);\n    }\n    return s0(e, t);\n  }\n  const n = Bm(e);\n  return te(t), n;\n}\nfunction Sc(e) {\n  return e === void 0 ? void 0 : Nt(e);\n}\nfunction wn(e, t) {\n  if (ke(e)) {\n    const r = Me(e) || {};\n    switch (r.branding) {\n      case Vn:\n        return te(t), r;\n      case Rr:\n        return te(t), Qe({\n          ...r,\n          ...Be\n        });\n      case Xt:\n        return te(t), Vd(G, r);\n    }\n    return r0(H(Nr(e)), e, t);\n  }\n  const n = Nm(e);\n  return te(t), n;\n}\nfunction Al(e, t) {\n  if (ke(e)) {\n    const r = Me(e);\n    if (r && r.branding === ac)\n      return te(t), r;\n    const o = Np(e);\n    return a0(H(o || X), !o, e, t);\n  }\n  const n = zm(H, e);\n  return te(t), n;\n}\nfunction En(e, t) {\n  if (ke(e)) {\n    const r = Me(e);\n    return r && r.branding === ic ? (te(t), r) : i0(H(Nr(e)), e, t);\n  }\n  const n = xm(H, e);\n  return te(t), n;\n}\nfunction Sn(e, t) {\n  if (ke(e)) {\n    const r = Me(e) || {};\n    switch (r.branding) {\n      case Rr:\n        return te(t), r;\n      case Vn:\n        return te(t), jt(r);\n      case Xt:\n        return te(t), Yd(G, r);\n    }\n    return o0(H(Nr(e)), e, t);\n  }\n  const n = ks(e);\n  return te(t), n;\n}\nfunction Tn(e, t) {\n  if (ke(e)) {\n    const n = Me(e);\n    if (n && n.branding === Xt)\n      return Ro(t), n;\n    const r = Nr(e);\n    return n0(De, G, H(r), r, e, t);\n  }\n  return Cm(e, t);\n}\nfunction Il(e) {\n  return St(((t) => (n) => t(Ka(n))), e);\n}\nfunction Ka(e) {\n  return $e(e, G);\n}\nfunction An(e) {\n  if (ke(e)) {\n    const t = Me(e);\n    if (t)\n      switch (t.branding) {\n        case cc:\n          return t;\n        case Xt:\n          return It(t.epochNanoseconds);\n      }\n  }\n  return Rm(e);\n}\nfunction zy() {\n  function e(i, a) {\n    return new t(i, a);\n  }\n  function t(i, a = /* @__PURE__ */ Object.create(null)) {\n    vo.set(this, ((s, c) => {\n      const l = new Ft(s, c), f = l.resolvedOptions(), d = f.locale, u = Ze(Object.keys(c), f), b = qe(Dy), h = (w, ...E) => {\n        if (w) {\n          if (E.length !== 2)\n            throw new TypeError(pi);\n          for (const y of E)\n            if (y === void 0)\n              throw new TypeError(pi);\n        }\n        w || E[0] !== void 0 || (E = []);\n        const m = E.map(((y) => Me(y) || Number(y)));\n        let g, T = 0;\n        for (const y of m) {\n          const v = typeof y == \"object\" ? y.branding : void 0;\n          if (T++ && v !== g)\n            throw new TypeError(pi);\n          g = v;\n        }\n        return g ? b(g)(d, u, ...m) : [l, ...m];\n      };\n      return h.X = l, h;\n    })(i, a));\n  }\n  const n = Ft.prototype, r = Object.getOwnPropertyDescriptors(n), o = Object.getOwnPropertyDescriptors(Ft);\n  for (const i in r) {\n    const a = r[i], s = i.startsWith(\"format\") && By(i);\n    typeof a.value == \"function\" ? a.value = i === \"constructor\" ? e : s || Fy(i) : s && (a.get = function() {\n      if (!vo.has(this))\n        throw new TypeError(qa);\n      return (...c) => s.apply(this, c);\n    }, Object.defineProperties(a.get, lr(`get ${i}`)));\n  }\n  return o.prototype.value = t.prototype = Object.create({}, r), Object.defineProperties(e, o), e;\n}\nfunction By(e) {\n  return Object.defineProperties((function(...t) {\n    const n = vo.get(this), [r, ...o] = n(e.includes(\"Range\"), ...t);\n    return r[e](...o);\n  }), lr(e));\n}\nfunction Fy(e) {\n  return Object.defineProperties((function(...t) {\n    return vo.get(this).X[e](...t);\n  }), lr(e));\n}\nfunction Dy(e) {\n  const t = Ky[e];\n  if (!t)\n    throw new TypeError(pg(e));\n  return Zt(t, qe(Zd), 1);\n}\nconst yo = /* @__PURE__ */ new WeakMap(), Me = /* @__PURE__ */ yo.get.bind(yo), jl = /* @__PURE__ */ yo.set.bind(yo), xp = {\n  era: lm,\n  eraYear: Hf,\n  year: es,\n  month: gt,\n  daysInMonth: gt,\n  daysInYear: gt,\n  inLeapYear: bg,\n  monthsInYear: gt\n}, Tc = {\n  monthCode: Te\n}, zp = {\n  day: gt\n}, qy = {\n  dayOfWeek: gt,\n  dayOfYear: gt,\n  weekOfYear: um,\n  yearOfWeek: Hf,\n  daysInWeek: gt\n}, Ac = /* @__PURE__ */ Ec(/* @__PURE__ */ Object.assign({}, xp, Tc, zp, qy)), Ly = /* @__PURE__ */ Ec({\n  ...xp,\n  ...Tc\n}), Hy = /* @__PURE__ */ Ec({\n  ...Tc,\n  ...zp\n}), xr = {\n  calendarId: (e) => e.calendar\n}, $y = /* @__PURE__ */ Ao(((e) => (t) => t[e]), oe.concat(\"sign\")), Ic = /* @__PURE__ */ Ao(((e, t) => (n) => n[Xe[t]]), Pt), Bp = {\n  epochMilliseconds: vs,\n  epochNanoseconds: pm\n}, [Uy, de] = en(lc, S0, {\n  ...$y,\n  blank: Pm\n}, {\n  with: (e, t) => de(m0(e, t)),\n  negated: (e) => de(Ps(e)),\n  abs: (e) => de(Om(e)),\n  add: (e, t, n) => de(fl(tr, H, G, 0, e, ve(t), n)),\n  subtract: (e, t, n) => de(fl(tr, H, G, 1, e, ve(t), n)),\n  round: (e, t) => de(jm(tr, H, G, e, t)),\n  total: (e, t) => hm(tr, H, G, e, t),\n  toLocaleString(e, t, n) {\n    return Intl.DurationFormat ? new Intl.DurationFormat(t, n).format(this) : ci(e);\n  },\n  toString: ci,\n  toJSON: (e) => ci(e),\n  valueOf: tn\n}, {\n  from: (e) => de(ve(e)),\n  compare: (e, t, n) => Hm(tr, H, G, ve(e), ve(t), n)\n}), Ky = {\n  Instant: Op,\n  PlainDateTime: Pp,\n  PlainDate: kp,\n  PlainTime: Rp,\n  PlainYearMonth: Mp,\n  PlainMonthDay: Cp\n}, Gy = /* @__PURE__ */ Zt(Op), Vy = /* @__PURE__ */ Zt(xy), Yy = /* @__PURE__ */ Zt(Pp), Wy = /* @__PURE__ */ Zt(kp), Zy = /* @__PURE__ */ Zt(Rp), Jy = /* @__PURE__ */ Zt(Mp), Qy = /* @__PURE__ */ Zt(Cp), [Xy, zt] = en(sc, E0, Ic, {\n  with(e, t, n) {\n    return zt(h0(this, Yn(t), n));\n  },\n  add: (e, t) => zt(ul(0, e, ve(t))),\n  subtract: (e, t) => zt(ul(1, e, ve(t))),\n  until: (e, t, n) => de(bl(0, e, Nt(t), n)),\n  since: (e, t, n) => de(bl(1, e, Nt(t), n)),\n  round: (e, t) => zt(vm(e, t)),\n  equals: (e, t) => Wm(e, Nt(t)),\n  toLocaleString(e, t, n) {\n    const [r, o] = Zy(t, n, e);\n    return r.format(o);\n  },\n  toString: rl,\n  toJSON: (e) => rl(e),\n  valueOf: tn\n}, {\n  from: (e, t) => zt(Nt(e, t)),\n  compare: (e, t) => Ds(Nt(e), Nt(t))\n}), [ev, ot] = en(Vn, J(v0, Ar), {\n  ...xr,\n  ...Ac,\n  ...Ic\n}, {\n  with: (e, t, n) => ot(u0(H, e, Yn(t), n)),\n  withCalendar: (e, t) => ot(Us(e, Xo(t))),\n  withPlainTime: (e, t) => ot(B0(e, Sc(t))),\n  add: (e, t, n) => ot(sl(H, 0, e, ve(t), n)),\n  subtract: (e, t, n) => ot(sl(H, 1, e, ve(t), n)),\n  until: (e, t, n) => de(gl(H, 0, e, wn(t), n)),\n  since: (e, t, n) => de(gl(H, 1, e, wn(t), n)),\n  round: (e, t) => ot(ym(e, t)),\n  equals: (e, t) => Km(e, wn(t)),\n  toZonedDateTime: (e, t, n) => Ie(I0(G, e, De(t), n)),\n  toPlainDate: (e) => it(jt(e)),\n  toPlainTime: (e) => zt(ht(e)),\n  toLocaleString(e, t, n) {\n    const [r, o] = Yy(t, n, e);\n    return r.format(o);\n  },\n  toString: Xc,\n  toJSON: (e) => Xc(e),\n  valueOf: tn\n}, {\n  from: (e, t) => ot(wn(e, t)),\n  compare: (e, t) => Od(wn(e), wn(t))\n}), [tv, Ga] = en(ac, J(w0, Ar), {\n  ...xr,\n  ...Hy\n}, {\n  with: (e, t, n) => Ga(p0(H, e, Yn(t), n)),\n  equals: (e, t) => Ym(e, Al(t)),\n  toPlainDate(e, t) {\n    return it(M0(H, e, this, t));\n  },\n  toLocaleString(e, t, n) {\n    const [r, o] = Qy(t, n, e);\n    return r.format(o);\n  },\n  toString: nl,\n  toJSON: (e) => nl(e),\n  valueOf: tn\n}, {\n  from: (e, t) => Ga(Al(e, t))\n}), [nv, ir] = en(ic, J(_0, Ar), {\n  ...xr,\n  ...Ly\n}, {\n  with: (e, t, n) => ir(d0(H, e, Yn(t), n)),\n  add: (e, t, n) => ir(ll(H, 0, e, ve(t), n)),\n  subtract: (e, t, n) => ir(ll(H, 1, e, ve(t), n)),\n  until: (e, t, n) => de(vl(H, 0, e, En(t), n)),\n  since: (e, t, n) => de(vl(H, 1, e, En(t), n)),\n  equals: (e, t) => Vm(e, En(t)),\n  toPlainDate(e, t) {\n    return it(R0(H, e, this, t));\n  },\n  toLocaleString(e, t, n) {\n    const [r, o] = Jy(t, n, e);\n    return r.format(o);\n  },\n  toString: tl,\n  toJSON: (e) => tl(e),\n  valueOf: tn\n}, {\n  from: (e, t) => ir(En(e, t)),\n  compare: (e, t) => Un(En(e), En(t))\n}), [rv, it] = en(Rr, J(b0, Ar), {\n  ...xr,\n  ...Ac\n}, {\n  with: (e, t, n) => it(f0(H, e, Yn(t), n)),\n  withCalendar: (e, t) => it(Us(e, Xo(t))),\n  add: (e, t, n) => it(cl(H, 0, e, ve(t), n)),\n  subtract: (e, t, n) => it(cl(H, 1, e, ve(t), n)),\n  until: (e, t, n) => de(yl(H, 0, e, Sn(t), n)),\n  since: (e, t, n) => de(yl(H, 1, e, Sn(t), n)),\n  equals: (e, t) => Gm(e, Sn(t)),\n  toZonedDateTime(e, t) {\n    const n = ke(t) ? t : {\n      timeZone: t\n    };\n    return Ie(j0(De, Nt, G, e, n));\n  },\n  toPlainDateTime: (e, t) => ot(O0(e, Sc(t))),\n  toPlainYearMonth(e) {\n    return ir(P0(H, e, this));\n  },\n  toPlainMonthDay(e) {\n    return Ga(k0(H, e, this));\n  },\n  toLocaleString(e, t, n) {\n    const [r, o] = Wy(t, n, e);\n    return r.format(o);\n  },\n  toString: el,\n  toJSON: (e) => el(e),\n  valueOf: tn\n}, {\n  from: (e, t) => it(Sn(e, t)),\n  compare: (e, t) => Un(Sn(e), Sn(t))\n}), [ov, Ie] = en(Xt, J(y0, Ar, Lm), {\n  ...Bp,\n  ...xr,\n  ...Il(Ac),\n  ...Il(Ic),\n  offset: (e) => Er(Ka(e).offsetNanoseconds),\n  offsetNanoseconds: (e) => Ka(e).offsetNanoseconds,\n  timeZoneId: (e) => e.timeZone,\n  hoursInDay: (e) => bm(G, e)\n}, {\n  with: (e, t, n) => Ie(l0(H, G, e, Yn(t), n)),\n  withCalendar: (e, t) => Ie(Us(e, Xo(t))),\n  withTimeZone: (e, t) => Ie(F0(e, De(t))),\n  withPlainTime: (e, t) => Ie(z0(G, e, Sc(t))),\n  add: (e, t, n) => Ie(al(H, G, 0, e, ve(t), n)),\n  subtract: (e, t, n) => Ie(al(H, G, 1, e, ve(t), n)),\n  until: (e, t, n) => de(be(ml(H, G, 0, e, Tn(t), n))),\n  since: (e, t, n) => de(be(ml(H, G, 1, e, Tn(t), n))),\n  round: (e, t) => Ie(gm(G, e, t)),\n  startOfDay: (e) => Ie(_m(G, e)),\n  equals: (e, t) => Um(e, Tn(t)),\n  toInstant: (e) => xt(A0(e)),\n  toPlainDateTime: (e) => ot(Vd(G, e)),\n  toPlainDate: (e) => it(Yd(G, e)),\n  toPlainTime: (e) => zt(Wd(G, e)),\n  toLocaleString(e, t, n = {}) {\n    const [r, o] = Vy(t, n, e);\n    return r.format(o);\n  },\n  toString: (e, t) => Qc(G, e, t),\n  toJSON: (e) => Qc(G, e),\n  valueOf: tn,\n  getTimeZoneTransition(e, t) {\n    const { timeZone: n, epochNanoseconds: r } = e, o = dm(t), i = G(n).O(r, o);\n    return i ? Ie({\n      ...e,\n      epochNanoseconds: i\n    }) : null;\n  }\n}, {\n  from: (e, t) => Ie(Tn(e, t)),\n  compare: (e, t) => jd(Tn(e), Tn(t))\n}), [iv, xt] = en(cc, g0, Bp, {\n  add: (e, t) => xt(il(0, e, ve(t))),\n  subtract: (e, t) => xt(il(1, e, ve(t))),\n  until: (e, t, n) => de(hl(0, e, An(t), n)),\n  since: (e, t, n) => de(hl(1, e, An(t), n)),\n  round: (e, t) => xt(mm(e, t)),\n  equals: (e, t) => $m(e, An(t)),\n  toZonedDateTimeISO: (e, t) => Ie(T0(e, De(t))),\n  toLocaleString(e, t, n) {\n    const [r, o] = Gy(t, n, e);\n    return r.format(o);\n  },\n  toString: (e, t) => Jc(De, G, e, t),\n  toJSON: (e) => Jc(De, G, e),\n  valueOf: tn\n}, {\n  from: (e) => xt(An(e)),\n  fromEpochMilliseconds: (e) => xt(C0(e)),\n  fromEpochNanoseconds: (e) => xt(N0(e)),\n  compare: (e, t) => Id(An(e), An(t))\n}), av = /* @__PURE__ */ Object.defineProperties({}, {\n  ...Qa(\"Temporal.Now\"),\n  ...kn({\n    timeZoneId: () => Xn(),\n    instant: () => xt(It(Da())),\n    zonedDateTimeISO: (e = Xn()) => Ie(Je(Da(), De(e), X)),\n    plainDateTimeISO: (e = Xn()) => ot(Qe(di(G(De(e))), X)),\n    plainDateISO: (e = Xn()) => it(jt(di(G(De(e))), X)),\n    plainTimeISO: (e = Xn()) => zt(ht(di(G(De(e)))))\n  })\n}), sv = /* @__PURE__ */ Object.defineProperties({}, {\n  ...Qa(\"Temporal\"),\n  ...kn({\n    PlainYearMonth: nv,\n    PlainMonthDay: tv,\n    PlainDate: rv,\n    PlainTime: Xy,\n    PlainDateTime: ev,\n    ZonedDateTime: ov,\n    Instant: iv,\n    Duration: Uy,\n    Now: av\n  })\n}), cv = /* @__PURE__ */ zy(), vo = /* @__PURE__ */ new WeakMap();\nObject.create(Intl), kn({\n  DateTimeFormat: cv\n});\nfunction lv(e) {\n  const t = e < 0;\n  e = Math.abs(e);\n  const n = Math.floor(e / 3600).toFixed(0).padStart(2, \"0\"), r = Math.floor(e % 3600 / 60).toFixed(0).padStart(2, \"0\"), o = Math.floor(e % 3600 % 60).toFixed(0).padStart(2, \"0\");\n  let i = \"\";\n  return n !== \"00\" && (i += `${n}:`), i += `${r}:${o}`, t && (i = \"-\" + i), i;\n}\nfunction Ol({ seconds: e, className: t, ...n }) {\n  const r = st(() => Math.floor(e), [e]), o = st(() => uv(r), [r]);\n  return /* @__PURE__ */ p.createElement(\n    \"time\",\n    {\n      dateTime: o,\n      className: pe(\"mx_Clock\", t),\n      ...n\n    },\n    lv(e)\n  );\n}\nfunction uv(e) {\n  if (!isNaN(e))\n    return new sv.Duration(0, 0, 0, 0, 0, 0, Math.round(e)).round({ smallestUnit: \"seconds\", largestUnit: \"hours\" }).toString();\n}\nvar Fp = typeof global == \"object\" && global && global.Object === Object && global, fv = typeof self == \"object\" && self && self.Object === Object && self, et = Fp || fv || Function(\"return this\")(), Ue = et.Symbol, Dp = Object.prototype, dv = Dp.hasOwnProperty, pv = Dp.toString, nr = Ue ? Ue.toStringTag : void 0;\nfunction hv(e) {\n  var t = dv.call(e, nr), n = e[nr];\n  try {\n    e[nr] = void 0;\n    var r = !0;\n  } catch {\n  }\n  var o = pv.call(e);\n  return r && (t ? e[nr] = n : delete e[nr]), o;\n}\nvar mv = Object.prototype, gv = mv.toString;\nfunction yv(e) {\n  return gv.call(e);\n}\nvar vv = \"[object Null]\", bv = \"[object Undefined]\", Pl = Ue ? Ue.toStringTag : void 0;\nfunction gn(e) {\n  return e == null ? e === void 0 ? bv : vv : Pl && Pl in Object(e) ? hv(e) : yv(e);\n}\nfunction Tt(e) {\n  return e != null && typeof e == \"object\";\n}\nvar _v = \"[object Symbol]\";\nfunction ei(e) {\n  return typeof e == \"symbol\" || Tt(e) && gn(e) == _v;\n}\nfunction qp(e, t) {\n  for (var n = -1, r = e == null ? 0 : e.length, o = Array(r); ++n < r; )\n    o[n] = t(e[n], n, e);\n  return o;\n}\nvar At = Array.isArray, kl = Ue ? Ue.prototype : void 0, Rl = kl ? kl.toString : void 0;\nfunction Lp(e) {\n  if (typeof e == \"string\")\n    return e;\n  if (At(e))\n    return qp(e, Lp) + \"\";\n  if (ei(e))\n    return Rl ? Rl.call(e) : \"\";\n  var t = e + \"\";\n  return t == \"0\" && 1 / e == -1 / 0 ? \"-0\" : t;\n}\nvar wv = /\\s/;\nfunction Ev(e) {\n  for (var t = e.length; t-- && wv.test(e.charAt(t)); )\n    ;\n  return t;\n}\nvar Sv = /^\\s+/;\nfunction Tv(e) {\n  return e && e.slice(0, Ev(e) + 1).replace(Sv, \"\");\n}\nfunction Kt(e) {\n  var t = typeof e;\n  return e != null && (t == \"object\" || t == \"function\");\n}\nvar Ml = NaN, Av = /^[-+]0x[0-9a-f]+$/i, Iv = /^0b[01]+$/i, jv = /^0o[0-7]+$/i, Ov = parseInt;\nfunction Cl(e) {\n  if (typeof e == \"number\")\n    return e;\n  if (ei(e))\n    return Ml;\n  if (Kt(e)) {\n    var t = typeof e.valueOf == \"function\" ? e.valueOf() : e;\n    e = Kt(t) ? t + \"\" : t;\n  }\n  if (typeof e != \"string\")\n    return e === 0 ? e : +e;\n  e = Tv(e);\n  var n = Iv.test(e);\n  return n || jv.test(e) ? Ov(e.slice(2), n ? 2 : 8) : Av.test(e) ? Ml : +e;\n}\nfunction Pv(e) {\n  return e;\n}\nvar kv = \"[object AsyncFunction]\", Rv = \"[object Function]\", Mv = \"[object GeneratorFunction]\", Cv = \"[object Proxy]\";\nfunction Hp(e) {\n  if (!Kt(e))\n    return !1;\n  var t = gn(e);\n  return t == Rv || t == Mv || t == kv || t == Cv;\n}\nvar gi = et[\"__core-js_shared__\"], Nl = (function() {\n  var e = /[^.]+$/.exec(gi && gi.keys && gi.keys.IE_PROTO || \"\");\n  return e ? \"Symbol(src)_1.\" + e : \"\";\n})();\nfunction Nv(e) {\n  return !!Nl && Nl in e;\n}\nvar xv = Function.prototype, zv = xv.toString;\nfunction yn(e) {\n  if (e != null) {\n    try {\n      return zv.call(e);\n    } catch {\n    }\n    try {\n      return e + \"\";\n    } catch {\n    }\n  }\n  return \"\";\n}\nvar Bv = /[\\\\^$.*+?()[\\]{}|]/g, Fv = /^\\[object .+?Constructor\\]$/, Dv = Function.prototype, qv = Object.prototype, Lv = Dv.toString, Hv = qv.hasOwnProperty, $v = RegExp(\n  \"^\" + Lv.call(Hv).replace(Bv, \"\\\\$&\").replace(/hasOwnProperty|(function).*?(?=\\\\\\()| for .+?(?=\\\\\\])/g, \"$1.*?\") + \"$\"\n);\nfunction Uv(e) {\n  if (!Kt(e) || Nv(e))\n    return !1;\n  var t = Hp(e) ? $v : Fv;\n  return t.test(yn(e));\n}\nfunction Kv(e, t) {\n  return e?.[t];\n}\nfunction vn(e, t) {\n  var n = Kv(e, t);\n  return Uv(n) ? n : void 0;\n}\nvar Va = vn(et, \"WeakMap\");\nfunction Gv(e, t, n) {\n  switch (n.length) {\n    case 0:\n      return e.call(t);\n    case 1:\n      return e.call(t, n[0]);\n    case 2:\n      return e.call(t, n[0], n[1]);\n    case 3:\n      return e.call(t, n[0], n[1], n[2]);\n  }\n  return e.apply(t, n);\n}\nvar Vv = 800, Yv = 16, Wv = Date.now;\nfunction Zv(e) {\n  var t = 0, n = 0;\n  return function() {\n    var r = Wv(), o = Yv - (r - n);\n    if (n = r, o > 0) {\n      if (++t >= Vv)\n        return arguments[0];\n    } else\n      t = 0;\n    return e.apply(void 0, arguments);\n  };\n}\nfunction Jv(e) {\n  return function() {\n    return e;\n  };\n}\nvar bo = (function() {\n  try {\n    var e = vn(Object, \"defineProperty\");\n    return e({}, \"\", {}), e;\n  } catch {\n  }\n})(), Qv = bo ? function(e, t) {\n  return bo(e, \"toString\", {\n    configurable: !0,\n    enumerable: !1,\n    value: Jv(t),\n    writable: !0\n  });\n} : Pv, Xv = Zv(Qv);\nfunction e2(e, t) {\n  for (var n = -1, r = e == null ? 0 : e.length; ++n < r && t(e[n], n, e) !== !1; )\n    ;\n  return e;\n}\nvar t2 = 9007199254740991, n2 = /^(?:0|[1-9]\\d*)$/;\nfunction r2(e, t) {\n  var n = typeof e;\n  return t = t ?? t2, !!t && (n == \"number\" || n != \"symbol\" && n2.test(e)) && e > -1 && e % 1 == 0 && e < t;\n}\nfunction $p(e, t, n) {\n  t == \"__proto__\" && bo ? bo(e, t, {\n    configurable: !0,\n    enumerable: !0,\n    value: n,\n    writable: !0\n  }) : e[t] = n;\n}\nfunction jc(e, t) {\n  return e === t || e !== e && t !== t;\n}\nvar o2 = Object.prototype, i2 = o2.hasOwnProperty;\nfunction Up(e, t, n) {\n  var r = e[t];\n  (!(i2.call(e, t) && jc(r, n)) || n === void 0 && !(t in e)) && $p(e, t, n);\n}\nfunction a2(e, t, n, r) {\n  var o = !n;\n  n || (n = {});\n  for (var i = -1, a = t.length; ++i < a; ) {\n    var s = t[i], c = void 0;\n    c === void 0 && (c = e[s]), o ? $p(n, s, c) : Up(n, s, c);\n  }\n  return n;\n}\nvar xl = Math.max;\nfunction s2(e, t, n) {\n  return t = xl(t === void 0 ? e.length - 1 : t, 0), function() {\n    for (var r = arguments, o = -1, i = xl(r.length - t, 0), a = Array(i); ++o < i; )\n      a[o] = r[t + o];\n    o = -1;\n    for (var s = Array(t + 1); ++o < t; )\n      s[o] = r[o];\n    return s[t] = n(a), Gv(e, this, s);\n  };\n}\nvar c2 = 9007199254740991;\nfunction Kp(e) {\n  return typeof e == \"number\" && e > -1 && e % 1 == 0 && e <= c2;\n}\nfunction Gp(e) {\n  return e != null && Kp(e.length) && !Hp(e);\n}\nvar l2 = Object.prototype;\nfunction Vp(e) {\n  var t = e && e.constructor, n = typeof t == \"function\" && t.prototype || l2;\n  return e === n;\n}\nfunction u2(e, t) {\n  for (var n = -1, r = Array(e); ++n < e; )\n    r[n] = t(n);\n  return r;\n}\nvar f2 = \"[object Arguments]\";\nfunction zl(e) {\n  return Tt(e) && gn(e) == f2;\n}\nvar Yp = Object.prototype, d2 = Yp.hasOwnProperty, p2 = Yp.propertyIsEnumerable, Wp = zl(/* @__PURE__ */ (function() {\n  return arguments;\n})()) ? zl : function(e) {\n  return Tt(e) && d2.call(e, \"callee\") && !p2.call(e, \"callee\");\n};\nfunction h2() {\n  return !1;\n}\nvar Zp = typeof exports == \"object\" && exports && !exports.nodeType && exports, Bl = Zp && typeof module == \"object\" && module && !module.nodeType && module, m2 = Bl && Bl.exports === Zp, Fl = m2 ? et.Buffer : void 0, g2 = Fl ? Fl.isBuffer : void 0, _o = g2 || h2, y2 = \"[object Arguments]\", v2 = \"[object Array]\", b2 = \"[object Boolean]\", _2 = \"[object Date]\", w2 = \"[object Error]\", E2 = \"[object Function]\", S2 = \"[object Map]\", T2 = \"[object Number]\", A2 = \"[object Object]\", I2 = \"[object RegExp]\", j2 = \"[object Set]\", O2 = \"[object String]\", P2 = \"[object WeakMap]\", k2 = \"[object ArrayBuffer]\", R2 = \"[object DataView]\", M2 = \"[object Float32Array]\", C2 = \"[object Float64Array]\", N2 = \"[object Int8Array]\", x2 = \"[object Int16Array]\", z2 = \"[object Int32Array]\", B2 = \"[object Uint8Array]\", F2 = \"[object Uint8ClampedArray]\", D2 = \"[object Uint16Array]\", q2 = \"[object Uint32Array]\", re = {};\nre[M2] = re[C2] = re[N2] = re[x2] = re[z2] = re[B2] = re[F2] = re[D2] = re[q2] = !0;\nre[y2] = re[v2] = re[k2] = re[b2] = re[R2] = re[_2] = re[w2] = re[E2] = re[S2] = re[T2] = re[A2] = re[I2] = re[j2] = re[O2] = re[P2] = !1;\nfunction L2(e) {\n  return Tt(e) && Kp(e.length) && !!re[gn(e)];\n}\nfunction Oc(e) {\n  return function(t) {\n    return e(t);\n  };\n}\nvar Jp = typeof exports == \"object\" && exports && !exports.nodeType && exports, cr = Jp && typeof module == \"object\" && module && !module.nodeType && module, H2 = cr && cr.exports === Jp, yi = H2 && Fp.process, Nn = (function() {\n  try {\n    var e = cr && cr.require && cr.require(\"util\").types;\n    return e || yi && yi.binding && yi.binding(\"util\");\n  } catch {\n  }\n})(), Dl = Nn && Nn.isTypedArray, Qp = Dl ? Oc(Dl) : L2, $2 = Object.prototype, U2 = $2.hasOwnProperty;\nfunction Xp(e, t) {\n  var n = At(e), r = !n && Wp(e), o = !n && !r && _o(e), i = !n && !r && !o && Qp(e), a = n || r || o || i, s = a ? u2(e.length, String) : [], c = s.length;\n  for (var l in e)\n    (t || U2.call(e, l)) && !(a && // Safari 9 has enumerable `arguments.length` in strict mode.\n    (l == \"length\" || // Node.js 0.10 has enumerable non-index properties on buffers.\n    o && (l == \"offset\" || l == \"parent\") || // PhantomJS 2 has enumerable non-index properties on typed arrays.\n    i && (l == \"buffer\" || l == \"byteLength\" || l == \"byteOffset\") || // Skip index properties.\n    r2(l, c))) && s.push(l);\n  return s;\n}\nfunction e1(e, t) {\n  return function(n) {\n    return e(t(n));\n  };\n}\nvar K2 = e1(Object.keys, Object), G2 = Object.prototype, V2 = G2.hasOwnProperty;\nfunction Y2(e) {\n  if (!Vp(e))\n    return K2(e);\n  var t = [];\n  for (var n in Object(e))\n    V2.call(e, n) && n != \"constructor\" && t.push(n);\n  return t;\n}\nfunction W2(e) {\n  return Gp(e) ? Xp(e) : Y2(e);\n}\nfunction Z2(e) {\n  var t = [];\n  if (e != null)\n    for (var n in Object(e))\n      t.push(n);\n  return t;\n}\nvar J2 = Object.prototype, Q2 = J2.hasOwnProperty;\nfunction X2(e) {\n  if (!Kt(e))\n    return Z2(e);\n  var t = Vp(e), n = [];\n  for (var r in e)\n    r == \"constructor\" && (t || !Q2.call(e, r)) || n.push(r);\n  return n;\n}\nfunction eb(e) {\n  return Gp(e) ? Xp(e, !0) : X2(e);\n}\nvar tb = /\\.|\\[(?:[^[\\]]*|([\"'])(?:(?!\\1)[^\\\\]|\\\\.)*?\\1)\\]/, nb = /^\\w*$/;\nfunction rb(e, t) {\n  if (At(e))\n    return !1;\n  var n = typeof e;\n  return n == \"number\" || n == \"symbol\" || n == \"boolean\" || e == null || ei(e) ? !0 : nb.test(e) || !tb.test(e) || t != null && e in Object(t);\n}\nvar yr = vn(Object, \"create\");\nfunction ob() {\n  this.__data__ = yr ? yr(null) : {}, this.size = 0;\n}\nfunction ib(e) {\n  var t = this.has(e) && delete this.__data__[e];\n  return this.size -= t ? 1 : 0, t;\n}\nvar ab = \"__lodash_hash_undefined__\", sb = Object.prototype, cb = sb.hasOwnProperty;\nfunction lb(e) {\n  var t = this.__data__;\n  if (yr) {\n    var n = t[e];\n    return n === ab ? void 0 : n;\n  }\n  return cb.call(t, e) ? t[e] : void 0;\n}\nvar ub = Object.prototype, fb = ub.hasOwnProperty;\nfunction db(e) {\n  var t = this.__data__;\n  return yr ? t[e] !== void 0 : fb.call(t, e);\n}\nvar pb = \"__lodash_hash_undefined__\";\nfunction hb(e, t) {\n  var n = this.__data__;\n  return this.size += this.has(e) ? 0 : 1, n[e] = yr && t === void 0 ? pb : t, this;\n}\nfunction ln(e) {\n  var t = -1, n = e == null ? 0 : e.length;\n  for (this.clear(); ++t < n; ) {\n    var r = e[t];\n    this.set(r[0], r[1]);\n  }\n}\nln.prototype.clear = ob;\nln.prototype.delete = ib;\nln.prototype.get = lb;\nln.prototype.has = db;\nln.prototype.set = hb;\nfunction mb() {\n  this.__data__ = [], this.size = 0;\n}\nfunction ti(e, t) {\n  for (var n = e.length; n--; )\n    if (jc(e[n][0], t))\n      return n;\n  return -1;\n}\nvar gb = Array.prototype, yb = gb.splice;\nfunction vb(e) {\n  var t = this.__data__, n = ti(t, e);\n  if (n < 0)\n    return !1;\n  var r = t.length - 1;\n  return n == r ? t.pop() : yb.call(t, n, 1), --this.size, !0;\n}\nfunction bb(e) {\n  var t = this.__data__, n = ti(t, e);\n  return n < 0 ? void 0 : t[n][1];\n}\nfunction _b(e) {\n  return ti(this.__data__, e) > -1;\n}\nfunction wb(e, t) {\n  var n = this.__data__, r = ti(n, e);\n  return r < 0 ? (++this.size, n.push([e, t])) : n[r][1] = t, this;\n}\nfunction Rt(e) {\n  var t = -1, n = e == null ? 0 : e.length;\n  for (this.clear(); ++t < n; ) {\n    var r = e[t];\n    this.set(r[0], r[1]);\n  }\n}\nRt.prototype.clear = mb;\nRt.prototype.delete = vb;\nRt.prototype.get = bb;\nRt.prototype.has = _b;\nRt.prototype.set = wb;\nvar vr = vn(et, \"Map\");\nfunction Eb() {\n  this.size = 0, this.__data__ = {\n    hash: new ln(),\n    map: new (vr || Rt)(),\n    string: new ln()\n  };\n}\nfunction Sb(e) {\n  var t = typeof e;\n  return t == \"string\" || t == \"number\" || t == \"symbol\" || t == \"boolean\" ? e !== \"__proto__\" : e === null;\n}\nfunction ni(e, t) {\n  var n = e.__data__;\n  return Sb(t) ? n[typeof t == \"string\" ? \"string\" : \"hash\"] : n.map;\n}\nfunction Tb(e) {\n  var t = ni(this, e).delete(e);\n  return this.size -= t ? 1 : 0, t;\n}\nfunction Ab(e) {\n  return ni(this, e).get(e);\n}\nfunction Ib(e) {\n  return ni(this, e).has(e);\n}\nfunction jb(e, t) {\n  var n = ni(this, e), r = n.size;\n  return n.set(e, t), this.size += n.size == r ? 0 : 1, this;\n}\nfunction Mt(e) {\n  var t = -1, n = e == null ? 0 : e.length;\n  for (this.clear(); ++t < n; ) {\n    var r = e[t];\n    this.set(r[0], r[1]);\n  }\n}\nMt.prototype.clear = Eb;\nMt.prototype.delete = Tb;\nMt.prototype.get = Ab;\nMt.prototype.has = Ib;\nMt.prototype.set = jb;\nvar Ob = \"Expected a function\";\nfunction Pc(e, t) {\n  if (typeof e != \"function\" || t != null && typeof t != \"function\")\n    throw new TypeError(Ob);\n  var n = function() {\n    var r = arguments, o = t ? t.apply(this, r) : r[0], i = n.cache;\n    if (i.has(o))\n      return i.get(o);\n    var a = e.apply(this, r);\n    return n.cache = i.set(o, a) || i, a;\n  };\n  return n.cache = new (Pc.Cache || Mt)(), n;\n}\nPc.Cache = Mt;\nvar Pb = 500;\nfunction kb(e) {\n  var t = Pc(e, function(r) {\n    return n.size === Pb && n.clear(), r;\n  }), n = t.cache;\n  return t;\n}\nvar Rb = /[^.[\\]]+|\\[(?:(-?\\d+(?:\\.\\d+)?)|([\"'])((?:(?!\\2)[^\\\\]|\\\\.)*?)\\2)\\]|(?=(?:\\.|\\[\\])(?:\\.|\\[\\]|$))/g, Mb = /\\\\(\\\\)?/g, Cb = kb(function(e) {\n  var t = [];\n  return e.charCodeAt(0) === 46 && t.push(\"\"), e.replace(Rb, function(n, r, o, i) {\n    t.push(o ? i.replace(Mb, \"$1\") : r || n);\n  }), t;\n});\nfunction Nb(e) {\n  return e == null ? \"\" : Lp(e);\n}\nfunction kc(e, t) {\n  return At(e) ? e : rb(e, t) ? [e] : Cb(Nb(e));\n}\nfunction t1(e) {\n  if (typeof e == \"string\" || ei(e))\n    return e;\n  var t = e + \"\";\n  return t == \"0\" && 1 / e == -1 / 0 ? \"-0\" : t;\n}\nfunction xb(e, t) {\n  t = kc(t, e);\n  for (var n = 0, r = t.length; e != null && n < r; )\n    e = e[t1(t[n++])];\n  return n && n == r ? e : void 0;\n}\nfunction Rc(e, t) {\n  for (var n = -1, r = t.length, o = e.length; ++n < r; )\n    e[o + n] = t[n];\n  return e;\n}\nvar ql = Ue ? Ue.isConcatSpreadable : void 0;\nfunction zb(e) {\n  return At(e) || Wp(e) || !!(ql && e && e[ql]);\n}\nfunction Bb(e, t, n, r, o) {\n  var i = -1, a = e.length;\n  for (n || (n = zb), o || (o = []); ++i < a; ) {\n    var s = e[i];\n    n(s) ? Rc(o, s) : o[o.length] = s;\n  }\n  return o;\n}\nfunction Fb(e) {\n  var t = e == null ? 0 : e.length;\n  return t ? Bb(e) : [];\n}\nfunction Db(e) {\n  return Xv(s2(e, void 0, Fb), e + \"\");\n}\nvar n1 = e1(Object.getPrototypeOf, Object), qb = \"[object Object]\", Lb = Function.prototype, Hb = Object.prototype, r1 = Lb.toString, $b = Hb.hasOwnProperty, Ub = r1.call(Object);\nfunction Kb(e) {\n  if (!Tt(e) || gn(e) != qb)\n    return !1;\n  var t = n1(e);\n  if (t === null)\n    return !0;\n  var n = $b.call(t, \"constructor\") && t.constructor;\n  return typeof n == \"function\" && n instanceof n && r1.call(n) == Ub;\n}\nfunction Gb(e, t, n) {\n  var r = -1, o = e.length;\n  t < 0 && (t = -t > o ? 0 : o + t), n = n > o ? o : n, n < 0 && (n += o), o = t > n ? 0 : n - t >>> 0, t >>>= 0;\n  for (var i = Array(o); ++r < o; )\n    i[r] = e[r + t];\n  return i;\n}\nfunction Vb() {\n  this.__data__ = new Rt(), this.size = 0;\n}\nfunction Yb(e) {\n  var t = this.__data__, n = t.delete(e);\n  return this.size = t.size, n;\n}\nfunction Wb(e) {\n  return this.__data__.get(e);\n}\nfunction Zb(e) {\n  return this.__data__.has(e);\n}\nvar Jb = 200;\nfunction Qb(e, t) {\n  var n = this.__data__;\n  if (n instanceof Rt) {\n    var r = n.__data__;\n    if (!vr || r.length < Jb - 1)\n      return r.push([e, t]), this.size = ++n.size, this;\n    n = this.__data__ = new Mt(r);\n  }\n  return n.set(e, t), this.size = n.size, this;\n}\nfunction wt(e) {\n  var t = this.__data__ = new Rt(e);\n  this.size = t.size;\n}\nwt.prototype.clear = Vb;\nwt.prototype.delete = Yb;\nwt.prototype.get = Wb;\nwt.prototype.has = Zb;\nwt.prototype.set = Qb;\nvar o1 = typeof exports == \"object\" && exports && !exports.nodeType && exports, Ll = o1 && typeof module == \"object\" && module && !module.nodeType && module, Xb = Ll && Ll.exports === o1, Hl = Xb ? et.Buffer : void 0;\nHl && Hl.allocUnsafe;\nfunction e_(e, t) {\n  return e.slice();\n}\nfunction t_(e, t) {\n  for (var n = -1, r = e == null ? 0 : e.length, o = 0, i = []; ++n < r; ) {\n    var a = e[n];\n    t(a, n, e) && (i[o++] = a);\n  }\n  return i;\n}\nfunction i1() {\n  return [];\n}\nvar n_ = Object.prototype, r_ = n_.propertyIsEnumerable, $l = Object.getOwnPropertySymbols, a1 = $l ? function(e) {\n  return e == null ? [] : (e = Object(e), t_($l(e), function(t) {\n    return r_.call(e, t);\n  }));\n} : i1, o_ = Object.getOwnPropertySymbols, i_ = o_ ? function(e) {\n  for (var t = []; e; )\n    Rc(t, a1(e)), e = n1(e);\n  return t;\n} : i1;\nfunction s1(e, t, n) {\n  var r = t(e);\n  return At(e) ? r : Rc(r, n(e));\n}\nfunction Ul(e) {\n  return s1(e, W2, a1);\n}\nfunction c1(e) {\n  return s1(e, eb, i_);\n}\nvar Ya = vn(et, \"DataView\"), Wa = vn(et, \"Promise\"), Za = vn(et, \"Set\"), Kl = \"[object Map]\", a_ = \"[object Object]\", Gl = \"[object Promise]\", Vl = \"[object Set]\", Yl = \"[object WeakMap]\", Wl = \"[object DataView]\", s_ = yn(Ya), c_ = yn(vr), l_ = yn(Wa), u_ = yn(Za), f_ = yn(Va), Ge = gn;\n(Ya && Ge(new Ya(new ArrayBuffer(1))) != Wl || vr && Ge(new vr()) != Kl || Wa && Ge(Wa.resolve()) != Gl || Za && Ge(new Za()) != Vl || Va && Ge(new Va()) != Yl) && (Ge = function(e) {\n  var t = gn(e), n = t == a_ ? e.constructor : void 0, r = n ? yn(n) : \"\";\n  if (r)\n    switch (r) {\n      case s_:\n        return Wl;\n      case c_:\n        return Kl;\n      case l_:\n        return Gl;\n      case u_:\n        return Vl;\n      case f_:\n        return Yl;\n    }\n  return t;\n});\nvar d_ = Object.prototype, p_ = d_.hasOwnProperty;\nfunction h_(e) {\n  var t = e.length, n = new e.constructor(t);\n  return t && typeof e[0] == \"string\" && p_.call(e, \"index\") && (n.index = e.index, n.input = e.input), n;\n}\nvar wo = et.Uint8Array;\nfunction Mc(e) {\n  var t = new e.constructor(e.byteLength);\n  return new wo(t).set(new wo(e)), t;\n}\nfunction m_(e, t) {\n  var n = Mc(e.buffer);\n  return new e.constructor(n, e.byteOffset, e.byteLength);\n}\nvar g_ = /\\w*$/;\nfunction y_(e) {\n  var t = new e.constructor(e.source, g_.exec(e));\n  return t.lastIndex = e.lastIndex, t;\n}\nvar Zl = Ue ? Ue.prototype : void 0, Jl = Zl ? Zl.valueOf : void 0;\nfunction v_(e) {\n  return Jl ? Object(Jl.call(e)) : {};\n}\nfunction b_(e, t) {\n  var n = Mc(e.buffer);\n  return new e.constructor(n, e.byteOffset, e.length);\n}\nvar __ = \"[object Boolean]\", w_ = \"[object Date]\", E_ = \"[object Map]\", S_ = \"[object Number]\", T_ = \"[object RegExp]\", A_ = \"[object Set]\", I_ = \"[object String]\", j_ = \"[object Symbol]\", O_ = \"[object ArrayBuffer]\", P_ = \"[object DataView]\", k_ = \"[object Float32Array]\", R_ = \"[object Float64Array]\", M_ = \"[object Int8Array]\", C_ = \"[object Int16Array]\", N_ = \"[object Int32Array]\", x_ = \"[object Uint8Array]\", z_ = \"[object Uint8ClampedArray]\", B_ = \"[object Uint16Array]\", F_ = \"[object Uint32Array]\";\nfunction D_(e, t, n) {\n  var r = e.constructor;\n  switch (t) {\n    case O_:\n      return Mc(e);\n    case __:\n    case w_:\n      return new r(+e);\n    case P_:\n      return m_(e);\n    case k_:\n    case R_:\n    case M_:\n    case C_:\n    case N_:\n    case x_:\n    case z_:\n    case B_:\n    case F_:\n      return b_(e);\n    case E_:\n      return new r();\n    case S_:\n    case I_:\n      return new r(e);\n    case T_:\n      return y_(e);\n    case A_:\n      return new r();\n    case j_:\n      return v_(e);\n  }\n}\nvar q_ = \"[object Map]\";\nfunction L_(e) {\n  return Tt(e) && Ge(e) == q_;\n}\nvar Ql = Nn && Nn.isMap, H_ = Ql ? Oc(Ql) : L_, $_ = \"[object Set]\";\nfunction U_(e) {\n  return Tt(e) && Ge(e) == $_;\n}\nvar Xl = Nn && Nn.isSet, K_ = Xl ? Oc(Xl) : U_, l1 = \"[object Arguments]\", G_ = \"[object Array]\", V_ = \"[object Boolean]\", Y_ = \"[object Date]\", W_ = \"[object Error]\", u1 = \"[object Function]\", Z_ = \"[object GeneratorFunction]\", J_ = \"[object Map]\", Q_ = \"[object Number]\", f1 = \"[object Object]\", X_ = \"[object RegExp]\", ew = \"[object Set]\", tw = \"[object String]\", nw = \"[object Symbol]\", rw = \"[object WeakMap]\", ow = \"[object ArrayBuffer]\", iw = \"[object DataView]\", aw = \"[object Float32Array]\", sw = \"[object Float64Array]\", cw = \"[object Int8Array]\", lw = \"[object Int16Array]\", uw = \"[object Int32Array]\", fw = \"[object Uint8Array]\", dw = \"[object Uint8ClampedArray]\", pw = \"[object Uint16Array]\", hw = \"[object Uint32Array]\", ee = {};\nee[l1] = ee[G_] = ee[ow] = ee[iw] = ee[V_] = ee[Y_] = ee[aw] = ee[sw] = ee[cw] = ee[lw] = ee[uw] = ee[J_] = ee[Q_] = ee[f1] = ee[X_] = ee[ew] = ee[tw] = ee[nw] = ee[fw] = ee[dw] = ee[pw] = ee[hw] = !0;\nee[W_] = ee[u1] = ee[rw] = !1;\nfunction io(e, t, n, r, o, i) {\n  var a;\n  if (n && (a = o ? n(e, r, o, i) : n(e)), a !== void 0)\n    return a;\n  if (!Kt(e))\n    return e;\n  var s = At(e);\n  if (s)\n    a = h_(e);\n  else {\n    var c = Ge(e), l = c == u1 || c == Z_;\n    if (_o(e))\n      return e_(e);\n    if (c == f1 || c == l1 || l && !o)\n      a = {};\n    else {\n      if (!ee[c])\n        return o ? e : {};\n      a = D_(e, c);\n    }\n  }\n  i || (i = new wt());\n  var f = i.get(e);\n  if (f)\n    return f;\n  i.set(e, a), K_(e) ? e.forEach(function(b) {\n    a.add(io(b, t, n, b, e, i));\n  }) : H_(e) && e.forEach(function(b, h) {\n    a.set(h, io(b, t, n, h, e, i));\n  });\n  var d = c1, u = s ? void 0 : d(e);\n  return e2(u || e, function(b, h) {\n    u && (h = b, b = e[h]), Up(a, h, io(b, t, n, h, e, i));\n  }), a;\n}\nvar mw = \"__lodash_hash_undefined__\";\nfunction gw(e) {\n  return this.__data__.set(e, mw), this;\n}\nfunction yw(e) {\n  return this.__data__.has(e);\n}\nfunction Eo(e) {\n  var t = -1, n = e == null ? 0 : e.length;\n  for (this.__data__ = new Mt(); ++t < n; )\n    this.add(e[t]);\n}\nEo.prototype.add = Eo.prototype.push = gw;\nEo.prototype.has = yw;\nfunction vw(e, t) {\n  for (var n = -1, r = e == null ? 0 : e.length; ++n < r; )\n    if (t(e[n], n, e))\n      return !0;\n  return !1;\n}\nfunction bw(e, t) {\n  return e.has(t);\n}\nvar _w = 1, ww = 2;\nfunction d1(e, t, n, r, o, i) {\n  var a = n & _w, s = e.length, c = t.length;\n  if (s != c && !(a && c > s))\n    return !1;\n  var l = i.get(e), f = i.get(t);\n  if (l && f)\n    return l == t && f == e;\n  var d = -1, u = !0, b = n & ww ? new Eo() : void 0;\n  for (i.set(e, t), i.set(t, e); ++d < s; ) {\n    var h = e[d], w = t[d];\n    if (r)\n      var E = a ? r(w, h, d, t, e, i) : r(h, w, d, e, t, i);\n    if (E !== void 0) {\n      if (E)\n        continue;\n      u = !1;\n      break;\n    }\n    if (b) {\n      if (!vw(t, function(m, g) {\n        if (!bw(b, g) && (h === m || o(h, m, n, r, i)))\n          return b.push(g);\n      })) {\n        u = !1;\n        break;\n      }\n    } else if (!(h === w || o(h, w, n, r, i))) {\n      u = !1;\n      break;\n    }\n  }\n  return i.delete(e), i.delete(t), u;\n}\nfunction Ew(e) {\n  var t = -1, n = Array(e.size);\n  return e.forEach(function(r, o) {\n    n[++t] = [o, r];\n  }), n;\n}\nfunction Sw(e) {\n  var t = -1, n = Array(e.size);\n  return e.forEach(function(r) {\n    n[++t] = r;\n  }), n;\n}\nvar Tw = 1, Aw = 2, Iw = \"[object Boolean]\", jw = \"[object Date]\", Ow = \"[object Error]\", Pw = \"[object Map]\", kw = \"[object Number]\", Rw = \"[object RegExp]\", Mw = \"[object Set]\", Cw = \"[object String]\", Nw = \"[object Symbol]\", xw = \"[object ArrayBuffer]\", zw = \"[object DataView]\", eu = Ue ? Ue.prototype : void 0, vi = eu ? eu.valueOf : void 0;\nfunction Bw(e, t, n, r, o, i, a) {\n  switch (n) {\n    case zw:\n      if (e.byteLength != t.byteLength || e.byteOffset != t.byteOffset)\n        return !1;\n      e = e.buffer, t = t.buffer;\n    case xw:\n      return !(e.byteLength != t.byteLength || !i(new wo(e), new wo(t)));\n    case Iw:\n    case jw:\n    case kw:\n      return jc(+e, +t);\n    case Ow:\n      return e.name == t.name && e.message == t.message;\n    case Rw:\n    case Cw:\n      return e == t + \"\";\n    case Pw:\n      var s = Ew;\n    case Mw:\n      var c = r & Tw;\n      if (s || (s = Sw), e.size != t.size && !c)\n        return !1;\n      var l = a.get(e);\n      if (l)\n        return l == t;\n      r |= Aw, a.set(e, t);\n      var f = d1(s(e), s(t), r, o, i, a);\n      return a.delete(e), f;\n    case Nw:\n      if (vi)\n        return vi.call(e) == vi.call(t);\n  }\n  return !1;\n}\nvar Fw = 1, Dw = Object.prototype, qw = Dw.hasOwnProperty;\nfunction Lw(e, t, n, r, o, i) {\n  var a = n & Fw, s = Ul(e), c = s.length, l = Ul(t), f = l.length;\n  if (c != f && !a)\n    return !1;\n  for (var d = c; d--; ) {\n    var u = s[d];\n    if (!(a ? u in t : qw.call(t, u)))\n      return !1;\n  }\n  var b = i.get(e), h = i.get(t);\n  if (b && h)\n    return b == t && h == e;\n  var w = !0;\n  i.set(e, t), i.set(t, e);\n  for (var E = a; ++d < c; ) {\n    u = s[d];\n    var m = e[u], g = t[u];\n    if (r)\n      var T = a ? r(g, m, u, t, e, i) : r(m, g, u, e, t, i);\n    if (!(T === void 0 ? m === g || o(m, g, n, r, i) : T)) {\n      w = !1;\n      break;\n    }\n    E || (E = u == \"constructor\");\n  }\n  if (w && !E) {\n    var y = e.constructor, v = t.constructor;\n    y != v && \"constructor\" in e && \"constructor\" in t && !(typeof y == \"function\" && y instanceof y && typeof v == \"function\" && v instanceof v) && (w = !1);\n  }\n  return i.delete(e), i.delete(t), w;\n}\nvar Hw = 1, tu = \"[object Arguments]\", nu = \"[object Array]\", Vr = \"[object Object]\", $w = Object.prototype, ru = $w.hasOwnProperty;\nfunction Uw(e, t, n, r, o, i) {\n  var a = At(e), s = At(t), c = a ? nu : Ge(e), l = s ? nu : Ge(t);\n  c = c == tu ? Vr : c, l = l == tu ? Vr : l;\n  var f = c == Vr, d = l == Vr, u = c == l;\n  if (u && _o(e)) {\n    if (!_o(t))\n      return !1;\n    a = !0, f = !1;\n  }\n  if (u && !f)\n    return i || (i = new wt()), a || Qp(e) ? d1(e, t, n, r, o, i) : Bw(e, t, c, n, r, o, i);\n  if (!(n & Hw)) {\n    var b = f && ru.call(e, \"__wrapped__\"), h = d && ru.call(t, \"__wrapped__\");\n    if (b || h) {\n      var w = b ? e.value() : e, E = h ? t.value() : t;\n      return i || (i = new wt()), o(w, E, n, r, i);\n    }\n  }\n  return u ? (i || (i = new wt()), Lw(e, t, n, r, o, i)) : !1;\n}\nfunction p1(e, t, n, r, o) {\n  return e === t ? !0 : e == null || t == null || !Tt(e) && !Tt(t) ? e !== e && t !== t : Uw(e, t, n, r, p1, o);\n}\nvar bi = function() {\n  return et.Date.now();\n}, Kw = \"Expected a function\", Gw = Math.max, Vw = Math.min;\nfunction Yw(e, t, n) {\n  var r, o, i, a, s, c, l = 0, f = !1, d = !1, u = !0;\n  if (typeof e != \"function\")\n    throw new TypeError(Kw);\n  t = Cl(t) || 0, Kt(n) && (f = !!n.leading, d = \"maxWait\" in n, i = d ? Gw(Cl(n.maxWait) || 0, t) : i, u = \"trailing\" in n ? !!n.trailing : u);\n  function b(S) {\n    var I = r, k = o;\n    return r = o = void 0, l = S, a = e.apply(k, I), a;\n  }\n  function h(S) {\n    return l = S, s = setTimeout(m, t), f ? b(S) : a;\n  }\n  function w(S) {\n    var I = S - c, k = S - l, M = t - I;\n    return d ? Vw(M, i - k) : M;\n  }\n  function E(S) {\n    var I = S - c, k = S - l;\n    return c === void 0 || I >= t || I < 0 || d && k >= i;\n  }\n  function m() {\n    var S = bi();\n    if (E(S))\n      return g(S);\n    s = setTimeout(m, w(S));\n  }\n  function g(S) {\n    return s = void 0, u && r ? b(S) : (r = o = void 0, a);\n  }\n  function T() {\n    s !== void 0 && clearTimeout(s), l = 0, r = c = o = s = void 0;\n  }\n  function y() {\n    return s === void 0 ? a : g(bi());\n  }\n  function v() {\n    var S = bi(), I = E(S);\n    if (r = arguments, o = this, c = S, I) {\n      if (s === void 0)\n        return h(c);\n      if (d)\n        return clearTimeout(s), s = setTimeout(m, t), b(c);\n    }\n    return s === void 0 && (s = setTimeout(m, t)), a;\n  }\n  return v.cancel = T, v.flush = y, v;\n}\nfunction Ww(e) {\n  var t = e == null ? 0 : e.length;\n  return t ? e[t - 1] : void 0;\n}\nfunction Zw(e, t) {\n  return t.length < 2 ? e : xb(e, Gb(t, 0, -1));\n}\nfunction Jw(e, t) {\n  return p1(e, t);\n}\nvar Qw = Object.prototype, Xw = Qw.hasOwnProperty;\nfunction e7(e, t) {\n  t = kc(t, e);\n  var n = -1, r = t.length;\n  if (!r)\n    return !0;\n  for (var o = e == null || typeof e != \"object\" && typeof e != \"function\"; ++n < r; ) {\n    var i = t[n];\n    if (typeof i == \"string\") {\n      if (i === \"__proto__\" && !Xw.call(e, \"__proto__\"))\n        return !1;\n      if (i === \"constructor\" && n + 1 < r && typeof t[n + 1] == \"string\" && t[n + 1] === \"prototype\") {\n        if (o && n === 0)\n          continue;\n        return !1;\n      }\n    }\n  }\n  var a = Zw(e, t);\n  return a == null || delete a[t1(Ww(t))];\n}\nfunction t7(e) {\n  return Kb(e) ? void 0 : e;\n}\nvar n7 = 1, r7 = 2, o7 = 4, i7 = Db(function(e, t) {\n  var n = {};\n  if (e == null)\n    return n;\n  var r = !1;\n  t = qp(t, function(i) {\n    return i = kc(i, e), r || (r = i.length > 1), i;\n  }), a2(e, c1(e), n), r && (n = io(n, n7 | r7 | o7, t7));\n  for (var o = t.length; o--; )\n    e7(n, t[o]);\n  return n;\n}), a7 = \"Expected a function\";\nfunction s7(e, t, n) {\n  var r = !0, o = !0;\n  if (typeof e != \"function\")\n    throw new TypeError(a7);\n  return Kt(n) && (r = \"leading\" in n ? !!n.leading : r, o = \"trailing\" in n ? !!n.trailing : o), Yw(e, t, {\n    leading: r,\n    maxWait: t,\n    trailing: o\n  });\n}\nconst c7 = \"_seekBar_16dv7_14\", l7 = {\n  seekBar: c7\n};\nfunction u7({ value: e = 0, className: t, ...n }) {\n  const { translate: r } = Pe(), [o, i] = Se(e), a = st(() => s7(i, 10), []);\n  return on(() => {\n    a(e);\n  }, [e, a]), /* @__PURE__ */ p.createElement(\n    \"input\",\n    {\n      type: \"range\",\n      className: pe(l7.seekBar, t),\n      onMouseDown: (s) => s.stopPropagation(),\n      min: 0,\n      max: 100,\n      value: o,\n      step: 1,\n      style: { \"--fillTo\": o / 100 },\n      \"aria-label\": r(\"a11y|seek_bar_label\"),\n      ...n\n    }\n  );\n}\nfunction C8({ vm: e }) {\n  const { translate: t } = Pe(), {\n    playbackState: n,\n    mediaName: r = t(\"timeline|m.audio|unnamed_audio\"),\n    sizeBytes: o,\n    durationSeconds: i,\n    playedSeconds: a,\n    percentComplete: s,\n    error: c\n  } = me(e), l = o ? `(${sm(o)})` : null, f = n === \"decoding\";\n  return /* @__PURE__ */ p.createElement(p.Fragment, null, /* @__PURE__ */ p.createElement(\n    Uh,\n    {\n      className: _n.audioPlayer,\n      tabIndex: 0,\n      onKeyDown: e.onKeyDown,\n      \"aria-label\": t(\"timeline|m.audio|audio_player\"),\n      role: \"region\"\n    },\n    /* @__PURE__ */ p.createElement(Q, { gap: \"var(--cpd-space-2x)\", align: \"center\" }, /* @__PURE__ */ p.createElement(\n      am,\n      {\n        tabIndex: -1,\n        disabled: f,\n        playing: n === \"playing\",\n        togglePlay: e.togglePlay\n      }\n    ), /* @__PURE__ */ p.createElement(Q, { direction: \"column\", className: _n.mediaInfo }, /* @__PURE__ */ p.createElement(\"span\", { className: _n.mediaName, \"data-testid\": \"audio-player-name\" }, r), /* @__PURE__ */ p.createElement(Q, { className: _n.byline, gap: \"var(--cpd-space-1-5x)\" }, /* @__PURE__ */ p.createElement(Ol, { seconds: i }), l))),\n    /* @__PURE__ */ p.createElement(Q, { align: \"center\", gap: \"var(--cpd-space-1x)\", \"data-testid\": \"audio-player-seek\" }, /* @__PURE__ */ p.createElement(u7, { tabIndex: -1, disabled: f, value: s, onChange: e.onSeekbarChange }), /* @__PURE__ */ p.createElement(Ol, { className: _n.clock, seconds: a, role: \"timer\" }))\n  ), c && /* @__PURE__ */ p.createElement(\"span\", { className: _n.error }, t(\"timeline|m.audio|error_downloading_audio\")));\n}\nconst f7 = \"_avatarWithDetails_7ga8t_8\", d7 = \"_title_7ga8t_17\", p7 = \"_details_7ga8t_28\", _i = {\n  avatarWithDetails: f7,\n  title: d7,\n  details: p7\n};\nfunction N8({\n  as: e,\n  className: t,\n  details: n,\n  avatar: r,\n  title: o,\n  ...i\n}) {\n  const a = e || \"div\";\n  return /* @__PURE__ */ p.createElement(a, { className: pe(_i.avatarWithDetails, t), ...i }, r, /* @__PURE__ */ p.createElement(Q, { direction: \"column\" }, /* @__PURE__ */ p.createElement(\"span\", { className: _i.title }, o), /* @__PURE__ */ p.createElement(\"span\", { className: _i.details }, n)));\n}\nfunction h1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"m10.6 13.8-2.15-2.15a.95.95 0 0 0-.7-.275.95.95 0 0 0-.7.275.95.95 0 0 0-.275.7q0 .425.275.7L9.9 15.9q.3.3.7.3t.7-.3l5.65-5.65a.95.95 0 0 0 .275-.7.95.95 0 0 0-.275-.7.95.95 0 0 0-.7-.275.95.95 0 0 0-.7.275zM12 22a9.7 9.7 0 0 1-3.9-.788 10.1 10.1 0 0 1-3.175-2.137q-1.35-1.35-2.137-3.175A9.7 9.7 0 0 1 2 12q0-2.075.788-3.9a10.1 10.1 0 0 1 2.137-3.175q1.35-1.35 3.175-2.137A9.7 9.7 0 0 1 12 2q2.075 0 3.9.788a10.1 10.1 0 0 1 3.175 2.137q1.35 1.35 2.137 3.175A9.7 9.7 0 0 1 22 12a9.7 9.7 0 0 1-.788 3.9 10.1 10.1 0 0 1-2.137 3.175q-1.35 1.35-3.175 2.137A9.7 9.7 0 0 1 12 22m0-2q3.35 0 5.675-2.325T20 12t-2.325-5.675T12 4 6.325 6.325 4 12t2.325 5.675T12 20\"\n    })\n  });\n}\nh1.displayName = \"CheckCircleIcon\";\nconst h7 = $(h1);\nfunction m1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M12 17q.424 0 .713-.288A.97.97 0 0 0 13 16a.97.97 0 0 0-.287-.713A.97.97 0 0 0 12 15a.97.97 0 0 0-.713.287A.97.97 0 0 0 11 16q0 .424.287.712.288.288.713.288m0-4q.424 0 .713-.287A.97.97 0 0 0 13 12V8a.97.97 0 0 0-.287-.713A.97.97 0 0 0 12 7a.97.97 0 0 0-.713.287A.97.97 0 0 0 11 8v4q0 .424.287.713.288.287.713.287m0 9a9.7 9.7 0 0 1-3.9-.788 10.1 10.1 0 0 1-3.175-2.137q-1.35-1.35-2.137-3.175A9.7 9.7 0 0 1 2 12q0-2.075.788-3.9a10.1 10.1 0 0 1 2.137-3.175q1.35-1.35 3.175-2.137A9.7 9.7 0 0 1 12 2q2.075 0 3.9.788a10.1 10.1 0 0 1 3.175 2.137q1.35 1.35 2.137 3.175A9.7 9.7 0 0 1 22 12a9.7 9.7 0 0 1-.788 3.9 10.1 10.1 0 0 1-2.137 3.175q-1.35 1.35-3.175 2.137A9.7 9.7 0 0 1 12 22\"\n    })\n  });\n}\nm1.displayName = \"ErrorSolidIcon\";\nconst g1 = $(m1);\nfunction y1(e, t) {\n  return /* @__PURE__ */ R.jsxs(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: [/* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M11.288 7.288A.97.97 0 0 1 12 7q.424 0 .713.287Q13 7.576 13 8t-.287.713A.97.97 0 0 1 12 9a.97.97 0 0 1-.713-.287A.97.97 0 0 1 11 8q0-.424.287-.713m.001 4.001A.97.97 0 0 1 12 11q.424 0 .713.287.287.288.287.713v4q0 .424-.287.712A.97.97 0 0 1 12 17a.97.97 0 0 1-.713-.288A.97.97 0 0 1 11 16v-4q0-.424.287-.713\"\n    }), /* @__PURE__ */ R.jsx(\"path\", {\n      fillRule: \"evenodd\",\n      d: \"M22 12c0 5.523-4.477 10-10 10S2 17.523 2 12 6.477 2 12 2s10 4.477 10 10m-2 0a8 8 0 1 1-16 0 8 8 0 0 1 16 0\",\n      clipRule: \"evenodd\"\n    })]\n  });\n}\ny1.displayName = \"InfoIcon\";\nconst ou = $(y1), m7 = \"_banner_17clp_8\", g7 = \"_content_17clp_39\", y7 = \"_icon_17clp_51\", v7 = \"_actions_17clp_71\", Yr = {\n  banner: m7,\n  content: g7,\n  icon: y7,\n  actions: v7\n};\nfunction b7(e) {\n  return e.toLowerCase().replace(\"_\", \"-\");\n}\nfunction v1(e) {\n  const t = [], n = b7(e), r = n.split(\"-\");\n  return r.length === 2 && r[0] === r[1] ? t.push(r[0]) : (t.push(n), r.length === 2 && t.push(r[0])), t;\n}\nconst _7 = \"|\";\nvar wi, iu;\nfunction w7() {\n  if (iu) return wi;\n  iu = 1;\n  var e = Object.prototype.hasOwnProperty, t = Object.prototype.toString, n = Object.defineProperty, r = Object.getOwnPropertyDescriptor, o = function(l) {\n    return typeof Array.isArray == \"function\" ? Array.isArray(l) : t.call(l) === \"[object Array]\";\n  }, i = function(l) {\n    if (!l || t.call(l) !== \"[object Object]\")\n      return !1;\n    var f = e.call(l, \"constructor\"), d = l.constructor && l.constructor.prototype && e.call(l.constructor.prototype, \"isPrototypeOf\");\n    if (l.constructor && !f && !d)\n      return !1;\n    var u;\n    for (u in l)\n      ;\n    return typeof u > \"u\" || e.call(l, u);\n  }, a = function(l, f) {\n    n && f.name === \"__proto__\" ? n(l, f.name, {\n      enumerable: !0,\n      configurable: !0,\n      value: f.newValue,\n      writable: !0\n    }) : l[f.name] = f.newValue;\n  }, s = function(l, f) {\n    if (f === \"__proto__\")\n      if (e.call(l, f)) {\n        if (r)\n          return r(l, f).value;\n      } else return;\n    return l[f];\n  };\n  return wi = function c() {\n    var l, f, d, u, b, h, w = arguments[0], E = 1, m = arguments.length, g = !1;\n    for (typeof w == \"boolean\" && (g = w, w = arguments[1] || {}, E = 2), (w == null || typeof w != \"object\" && typeof w != \"function\") && (w = {}); E < m; ++E)\n      if (l = arguments[E], l != null)\n        for (f in l)\n          d = s(w, f), u = s(l, f), w !== u && (g && u && (i(u) || (b = o(u))) ? (b ? (b = !1, h = d && o(d) ? d : []) : h = d && i(d) ? d : {}, a(w, { name: f, newValue: c(g, h, u) })) : typeof u < \"u\" && a(w, { name: f, newValue: u }));\n    return w;\n  }, wi;\n}\nvar Ei = {}, Si = {}, Ti, au;\nfunction b1() {\n  return au || (au = 1, Ti = function() {\n    if (typeof Symbol != \"function\" || typeof Object.getOwnPropertySymbols != \"function\")\n      return !1;\n    if (typeof Symbol.iterator == \"symbol\")\n      return !0;\n    var t = {}, n = /* @__PURE__ */ Symbol(\"test\"), r = Object(n);\n    if (typeof n == \"string\" || Object.prototype.toString.call(n) !== \"[object Symbol]\" || Object.prototype.toString.call(r) !== \"[object Symbol]\")\n      return !1;\n    var o = 42;\n    t[n] = o;\n    for (var i in t)\n      return !1;\n    if (typeof Object.keys == \"function\" && Object.keys(t).length !== 0 || typeof Object.getOwnPropertyNames == \"function\" && Object.getOwnPropertyNames(t).length !== 0)\n      return !1;\n    var a = Object.getOwnPropertySymbols(t);\n    if (a.length !== 1 || a[0] !== n || !Object.prototype.propertyIsEnumerable.call(t, n))\n      return !1;\n    if (typeof Object.getOwnPropertyDescriptor == \"function\") {\n      var s = (\n        /** @type {PropertyDescriptor} */\n        Object.getOwnPropertyDescriptor(t, n)\n      );\n      if (s.value !== o || s.enumerable !== !0)\n        return !1;\n    }\n    return !0;\n  }), Ti;\n}\nvar Ai, su;\nfunction ri() {\n  if (su) return Ai;\n  su = 1;\n  var e = b1();\n  return Ai = function() {\n    return e() && !!Symbol.toStringTag;\n  }, Ai;\n}\nvar Ii, cu;\nfunction _1() {\n  return cu || (cu = 1, Ii = Object), Ii;\n}\nvar ji, lu;\nfunction E7() {\n  return lu || (lu = 1, ji = Error), ji;\n}\nvar Oi, uu;\nfunction S7() {\n  return uu || (uu = 1, Oi = EvalError), Oi;\n}\nvar Pi, fu;\nfunction T7() {\n  return fu || (fu = 1, Pi = RangeError), Pi;\n}\nvar ki, du;\nfunction A7() {\n  return du || (du = 1, ki = ReferenceError), ki;\n}\nvar Ri, pu;\nfunction w1() {\n  return pu || (pu = 1, Ri = SyntaxError), Ri;\n}\nvar Mi, hu;\nfunction zr() {\n  return hu || (hu = 1, Mi = TypeError), Mi;\n}\nvar Ci, mu;\nfunction I7() {\n  return mu || (mu = 1, Ci = URIError), Ci;\n}\nvar Ni, gu;\nfunction j7() {\n  return gu || (gu = 1, Ni = Math.abs), Ni;\n}\nvar xi, yu;\nfunction O7() {\n  return yu || (yu = 1, xi = Math.floor), xi;\n}\nvar zi, vu;\nfunction P7() {\n  return vu || (vu = 1, zi = Math.max), zi;\n}\nvar Bi, bu;\nfunction k7() {\n  return bu || (bu = 1, Bi = Math.min), Bi;\n}\nvar Fi, _u;\nfunction R7() {\n  return _u || (_u = 1, Fi = Math.pow), Fi;\n}\nvar Di, wu;\nfunction M7() {\n  return wu || (wu = 1, Di = Math.round), Di;\n}\nvar qi, Eu;\nfunction C7() {\n  return Eu || (Eu = 1, qi = Number.isNaN || function(t) {\n    return t !== t;\n  }), qi;\n}\nvar Li, Su;\nfunction N7() {\n  if (Su) return Li;\n  Su = 1;\n  var e = /* @__PURE__ */ C7();\n  return Li = function(n) {\n    return e(n) || n === 0 ? n : n < 0 ? -1 : 1;\n  }, Li;\n}\nvar Hi, Tu;\nfunction x7() {\n  return Tu || (Tu = 1, Hi = Object.getOwnPropertyDescriptor), Hi;\n}\nvar $i, Au;\nfunction Wn() {\n  if (Au) return $i;\n  Au = 1;\n  var e = /* @__PURE__ */ x7();\n  if (e)\n    try {\n      e([], \"length\");\n    } catch {\n      e = null;\n    }\n  return $i = e, $i;\n}\nvar Ui, Iu;\nfunction oi() {\n  if (Iu) return Ui;\n  Iu = 1;\n  var e = Object.defineProperty || !1;\n  if (e)\n    try {\n      e({}, \"a\", { value: 1 });\n    } catch {\n      e = !1;\n    }\n  return Ui = e, Ui;\n}\nvar Ki, ju;\nfunction z7() {\n  if (ju) return Ki;\n  ju = 1;\n  var e = typeof Symbol < \"u\" && Symbol, t = b1();\n  return Ki = function() {\n    return typeof e != \"function\" || typeof Symbol != \"function\" || typeof e(\"foo\") != \"symbol\" || typeof /* @__PURE__ */ Symbol(\"bar\") != \"symbol\" ? !1 : t();\n  }, Ki;\n}\nvar Gi, Ou;\nfunction E1() {\n  return Ou || (Ou = 1, Gi = typeof Reflect < \"u\" && Reflect.getPrototypeOf || null), Gi;\n}\nvar Vi, Pu;\nfunction S1() {\n  if (Pu) return Vi;\n  Pu = 1;\n  var e = /* @__PURE__ */ _1();\n  return Vi = e.getPrototypeOf || null, Vi;\n}\nvar Yi, ku;\nfunction B7() {\n  if (ku) return Yi;\n  ku = 1;\n  var e = \"Function.prototype.bind called on incompatible \", t = Object.prototype.toString, n = Math.max, r = \"[object Function]\", o = function(c, l) {\n    for (var f = [], d = 0; d < c.length; d += 1)\n      f[d] = c[d];\n    for (var u = 0; u < l.length; u += 1)\n      f[u + c.length] = l[u];\n    return f;\n  }, i = function(c, l) {\n    for (var f = [], d = l, u = 0; d < c.length; d += 1, u += 1)\n      f[u] = c[d];\n    return f;\n  }, a = function(s, c) {\n    for (var l = \"\", f = 0; f < s.length; f += 1)\n      l += s[f], f + 1 < s.length && (l += c);\n    return l;\n  };\n  return Yi = function(c) {\n    var l = this;\n    if (typeof l != \"function\" || t.apply(l) !== r)\n      throw new TypeError(e + l);\n    for (var f = i(arguments, 1), d, u = function() {\n      if (this instanceof d) {\n        var m = l.apply(\n          this,\n          o(f, arguments)\n        );\n        return Object(m) === m ? m : this;\n      }\n      return l.apply(\n        c,\n        o(f, arguments)\n      );\n    }, b = n(0, l.length - f.length), h = [], w = 0; w < b; w++)\n      h[w] = \"$\" + w;\n    if (d = Function(\"binder\", \"return function (\" + a(h, \",\") + \"){ return binder.apply(this,arguments); }\")(u), l.prototype) {\n      var E = function() {\n      };\n      E.prototype = l.prototype, d.prototype = new E(), E.prototype = null;\n    }\n    return d;\n  }, Yi;\n}\nvar Wi, Ru;\nfunction Br() {\n  if (Ru) return Wi;\n  Ru = 1;\n  var e = B7();\n  return Wi = Function.prototype.bind || e, Wi;\n}\nvar Zi, Mu;\nfunction Cc() {\n  return Mu || (Mu = 1, Zi = Function.prototype.call), Zi;\n}\nvar Ji, Cu;\nfunction Nc() {\n  return Cu || (Cu = 1, Ji = Function.prototype.apply), Ji;\n}\nvar Qi, Nu;\nfunction F7() {\n  return Nu || (Nu = 1, Qi = typeof Reflect < \"u\" && Reflect && Reflect.apply), Qi;\n}\nvar Xi, xu;\nfunction T1() {\n  if (xu) return Xi;\n  xu = 1;\n  var e = Br(), t = Nc(), n = Cc(), r = F7();\n  return Xi = r || e.call(n, t), Xi;\n}\nvar ea, zu;\nfunction xc() {\n  if (zu) return ea;\n  zu = 1;\n  var e = Br(), t = /* @__PURE__ */ zr(), n = Cc(), r = T1();\n  return ea = function(i) {\n    if (i.length < 1 || typeof i[0] != \"function\")\n      throw new t(\"a function is required\");\n    return r(e, n, i);\n  }, ea;\n}\nvar ta, Bu;\nfunction D7() {\n  if (Bu) return ta;\n  Bu = 1;\n  var e = xc(), t = /* @__PURE__ */ Wn(), n;\n  try {\n    n = /** @type {{ __proto__?: typeof Array.prototype }} */\n    [].__proto__ === Array.prototype;\n  } catch (a) {\n    if (!a || typeof a != \"object\" || !(\"code\" in a) || a.code !== \"ERR_PROTO_ACCESS\")\n      throw a;\n  }\n  var r = !!n && t && t(\n    Object.prototype,\n    /** @type {keyof typeof Object.prototype} */\n    \"__proto__\"\n  ), o = Object, i = o.getPrototypeOf;\n  return ta = r && typeof r.get == \"function\" ? e([r.get]) : typeof i == \"function\" ? (\n    /** @type {import('./get')} */\n    function(s) {\n      return i(s == null ? s : o(s));\n    }\n  ) : !1, ta;\n}\nvar na, Fu;\nfunction zc() {\n  if (Fu) return na;\n  Fu = 1;\n  var e = E1(), t = S1(), n = /* @__PURE__ */ D7();\n  return na = e ? function(o) {\n    return e(o);\n  } : t ? function(o) {\n    if (!o || typeof o != \"object\" && typeof o != \"function\")\n      throw new TypeError(\"getProto: not an object\");\n    return t(o);\n  } : n ? function(o) {\n    return n(o);\n  } : null, na;\n}\nvar ra, Du;\nfunction A1() {\n  if (Du) return ra;\n  Du = 1;\n  var e = Function.prototype.call, t = Object.prototype.hasOwnProperty, n = Br();\n  return ra = n.call(e, t), ra;\n}\nvar oa, qu;\nfunction I1() {\n  if (qu) return oa;\n  qu = 1;\n  var e, t = /* @__PURE__ */ _1(), n = /* @__PURE__ */ E7(), r = /* @__PURE__ */ S7(), o = /* @__PURE__ */ T7(), i = /* @__PURE__ */ A7(), a = /* @__PURE__ */ w1(), s = /* @__PURE__ */ zr(), c = /* @__PURE__ */ I7(), l = /* @__PURE__ */ j7(), f = /* @__PURE__ */ O7(), d = /* @__PURE__ */ P7(), u = /* @__PURE__ */ k7(), b = /* @__PURE__ */ R7(), h = /* @__PURE__ */ M7(), w = /* @__PURE__ */ N7(), E = Function, m = function(F) {\n    try {\n      return E('\"use strict\"; return (' + F + \").constructor;\")();\n    } catch {\n    }\n  }, g = /* @__PURE__ */ Wn(), T = /* @__PURE__ */ oi(), y = function() {\n    throw new s();\n  }, v = g ? (function() {\n    try {\n      return arguments.callee, y;\n    } catch {\n      try {\n        return g(arguments, \"callee\").get;\n      } catch {\n        return y;\n      }\n    }\n  })() : y, S = z7()(), I = zc(), k = S1(), M = E1(), N = Nc(), L = Cc(), V = {}, ie = typeof Uint8Array > \"u\" || !I ? e : I(Uint8Array), ce = {\n    __proto__: null,\n    \"%AggregateError%\": typeof AggregateError > \"u\" ? e : AggregateError,\n    \"%Array%\": Array,\n    \"%ArrayBuffer%\": typeof ArrayBuffer > \"u\" ? e : ArrayBuffer,\n    \"%ArrayIteratorPrototype%\": S && I ? I([][Symbol.iterator]()) : e,\n    \"%AsyncFromSyncIteratorPrototype%\": e,\n    \"%AsyncFunction%\": V,\n    \"%AsyncGenerator%\": V,\n    \"%AsyncGeneratorFunction%\": V,\n    \"%AsyncIteratorPrototype%\": V,\n    \"%Atomics%\": typeof Atomics > \"u\" ? e : Atomics,\n    \"%BigInt%\": typeof BigInt > \"u\" ? e : BigInt,\n    \"%BigInt64Array%\": typeof BigInt64Array > \"u\" ? e : BigInt64Array,\n    \"%BigUint64Array%\": typeof BigUint64Array > \"u\" ? e : BigUint64Array,\n    \"%Boolean%\": Boolean,\n    \"%DataView%\": typeof DataView > \"u\" ? e : DataView,\n    \"%Date%\": Date,\n    \"%decodeURI%\": decodeURI,\n    \"%decodeURIComponent%\": decodeURIComponent,\n    \"%encodeURI%\": encodeURI,\n    \"%encodeURIComponent%\": encodeURIComponent,\n    \"%Error%\": n,\n    \"%eval%\": eval,\n    // eslint-disable-line no-eval\n    \"%EvalError%\": r,\n    \"%Float16Array%\": typeof Float16Array > \"u\" ? e : Float16Array,\n    \"%Float32Array%\": typeof Float32Array > \"u\" ? e : Float32Array,\n    \"%Float64Array%\": typeof Float64Array > \"u\" ? e : Float64Array,\n    \"%FinalizationRegistry%\": typeof FinalizationRegistry > \"u\" ? e : FinalizationRegistry,\n    \"%Function%\": E,\n    \"%GeneratorFunction%\": V,\n    \"%Int8Array%\": typeof Int8Array > \"u\" ? e : Int8Array,\n    \"%Int16Array%\": typeof Int16Array > \"u\" ? e : Int16Array,\n    \"%Int32Array%\": typeof Int32Array > \"u\" ? e : Int32Array,\n    \"%isFinite%\": isFinite,\n    \"%isNaN%\": isNaN,\n    \"%IteratorPrototype%\": S && I ? I(I([][Symbol.iterator]())) : e,\n    \"%JSON%\": typeof JSON == \"object\" ? JSON : e,\n    \"%Map%\": typeof Map > \"u\" ? e : Map,\n    \"%MapIteratorPrototype%\": typeof Map > \"u\" || !S || !I ? e : I((/* @__PURE__ */ new Map())[Symbol.iterator]()),\n    \"%Math%\": Math,\n    \"%Number%\": Number,\n    \"%Object%\": t,\n    \"%Object.getOwnPropertyDescriptor%\": g,\n    \"%parseFloat%\": parseFloat,\n    \"%parseInt%\": parseInt,\n    \"%Promise%\": typeof Promise > \"u\" ? e : Promise,\n    \"%Proxy%\": typeof Proxy > \"u\" ? e : Proxy,\n    \"%RangeError%\": o,\n    \"%ReferenceError%\": i,\n    \"%Reflect%\": typeof Reflect > \"u\" ? e : Reflect,\n    \"%RegExp%\": RegExp,\n    \"%Set%\": typeof Set > \"u\" ? e : Set,\n    \"%SetIteratorPrototype%\": typeof Set > \"u\" || !S || !I ? e : I((/* @__PURE__ */ new Set())[Symbol.iterator]()),\n    \"%SharedArrayBuffer%\": typeof SharedArrayBuffer > \"u\" ? e : SharedArrayBuffer,\n    \"%String%\": String,\n    \"%StringIteratorPrototype%\": S && I ? I(\"\"[Symbol.iterator]()) : e,\n    \"%Symbol%\": S ? Symbol : e,\n    \"%SyntaxError%\": a,\n    \"%ThrowTypeError%\": v,\n    \"%TypedArray%\": ie,\n    \"%TypeError%\": s,\n    \"%Uint8Array%\": typeof Uint8Array > \"u\" ? e : Uint8Array,\n    \"%Uint8ClampedArray%\": typeof Uint8ClampedArray > \"u\" ? e : Uint8ClampedArray,\n    \"%Uint16Array%\": typeof Uint16Array > \"u\" ? e : Uint16Array,\n    \"%Uint32Array%\": typeof Uint32Array > \"u\" ? e : Uint32Array,\n    \"%URIError%\": c,\n    \"%WeakMap%\": typeof WeakMap > \"u\" ? e : WeakMap,\n    \"%WeakRef%\": typeof WeakRef > \"u\" ? e : WeakRef,\n    \"%WeakSet%\": typeof WeakSet > \"u\" ? e : WeakSet,\n    \"%Function.prototype.call%\": L,\n    \"%Function.prototype.apply%\": N,\n    \"%Object.defineProperty%\": T,\n    \"%Object.getPrototypeOf%\": k,\n    \"%Math.abs%\": l,\n    \"%Math.floor%\": f,\n    \"%Math.max%\": d,\n    \"%Math.min%\": u,\n    \"%Math.pow%\": b,\n    \"%Math.round%\": h,\n    \"%Math.sign%\": w,\n    \"%Reflect.getPrototypeOf%\": M\n  };\n  if (I)\n    try {\n      null.error;\n    } catch (F) {\n      var D = I(I(F));\n      ce[\"%Error.prototype%\"] = D;\n    }\n  var K = function F(x) {\n    var Y;\n    if (x === \"%AsyncFunction%\")\n      Y = m(\"async function () {}\");\n    else if (x === \"%GeneratorFunction%\")\n      Y = m(\"function* () {}\");\n    else if (x === \"%AsyncGeneratorFunction%\")\n      Y = m(\"async function* () {}\");\n    else if (x === \"%AsyncGenerator%\") {\n      var Z = F(\"%AsyncGeneratorFunction%\");\n      Z && (Y = Z.prototype);\n    } else if (x === \"%AsyncIteratorPrototype%\") {\n      var ue = F(\"%AsyncGenerator%\");\n      ue && I && (Y = I(ue.prototype));\n    }\n    return ce[x] = Y, Y;\n  }, W = {\n    __proto__: null,\n    \"%ArrayBufferPrototype%\": [\"ArrayBuffer\", \"prototype\"],\n    \"%ArrayPrototype%\": [\"Array\", \"prototype\"],\n    \"%ArrayProto_entries%\": [\"Array\", \"prototype\", \"entries\"],\n    \"%ArrayProto_forEach%\": [\"Array\", \"prototype\", \"forEach\"],\n    \"%ArrayProto_keys%\": [\"Array\", \"prototype\", \"keys\"],\n    \"%ArrayProto_values%\": [\"Array\", \"prototype\", \"values\"],\n    \"%AsyncFunctionPrototype%\": [\"AsyncFunction\", \"prototype\"],\n    \"%AsyncGenerator%\": [\"AsyncGeneratorFunction\", \"prototype\"],\n    \"%AsyncGeneratorPrototype%\": [\"AsyncGeneratorFunction\", \"prototype\", \"prototype\"],\n    \"%BooleanPrototype%\": [\"Boolean\", \"prototype\"],\n    \"%DataViewPrototype%\": [\"DataView\", \"prototype\"],\n    \"%DatePrototype%\": [\"Date\", \"prototype\"],\n    \"%ErrorPrototype%\": [\"Error\", \"prototype\"],\n    \"%EvalErrorPrototype%\": [\"EvalError\", \"prototype\"],\n    \"%Float32ArrayPrototype%\": [\"Float32Array\", \"prototype\"],\n    \"%Float64ArrayPrototype%\": [\"Float64Array\", \"prototype\"],\n    \"%FunctionPrototype%\": [\"Function\", \"prototype\"],\n    \"%Generator%\": [\"GeneratorFunction\", \"prototype\"],\n    \"%GeneratorPrototype%\": [\"GeneratorFunction\", \"prototype\", \"prototype\"],\n    \"%Int8ArrayPrototype%\": [\"Int8Array\", \"prototype\"],\n    \"%Int16ArrayPrototype%\": [\"Int16Array\", \"prototype\"],\n    \"%Int32ArrayPrototype%\": [\"Int32Array\", \"prototype\"],\n    \"%JSONParse%\": [\"JSON\", \"parse\"],\n    \"%JSONStringify%\": [\"JSON\", \"stringify\"],\n    \"%MapPrototype%\": [\"Map\", \"prototype\"],\n    \"%NumberPrototype%\": [\"Number\", \"prototype\"],\n    \"%ObjectPrototype%\": [\"Object\", \"prototype\"],\n    \"%ObjProto_toString%\": [\"Object\", \"prototype\", \"toString\"],\n    \"%ObjProto_valueOf%\": [\"Object\", \"prototype\", \"valueOf\"],\n    \"%PromisePrototype%\": [\"Promise\", \"prototype\"],\n    \"%PromiseProto_then%\": [\"Promise\", \"prototype\", \"then\"],\n    \"%Promise_all%\": [\"Promise\", \"all\"],\n    \"%Promise_reject%\": [\"Promise\", \"reject\"],\n    \"%Promise_resolve%\": [\"Promise\", \"resolve\"],\n    \"%RangeErrorPrototype%\": [\"RangeError\", \"prototype\"],\n    \"%ReferenceErrorPrototype%\": [\"ReferenceError\", \"prototype\"],\n    \"%RegExpPrototype%\": [\"RegExp\", \"prototype\"],\n    \"%SetPrototype%\": [\"Set\", \"prototype\"],\n    \"%SharedArrayBufferPrototype%\": [\"SharedArrayBuffer\", \"prototype\"],\n    \"%StringPrototype%\": [\"String\", \"prototype\"],\n    \"%SymbolPrototype%\": [\"Symbol\", \"prototype\"],\n    \"%SyntaxErrorPrototype%\": [\"SyntaxError\", \"prototype\"],\n    \"%TypedArrayPrototype%\": [\"TypedArray\", \"prototype\"],\n    \"%TypeErrorPrototype%\": [\"TypeError\", \"prototype\"],\n    \"%Uint8ArrayPrototype%\": [\"Uint8Array\", \"prototype\"],\n    \"%Uint8ClampedArrayPrototype%\": [\"Uint8ClampedArray\", \"prototype\"],\n    \"%Uint16ArrayPrototype%\": [\"Uint16Array\", \"prototype\"],\n    \"%Uint32ArrayPrototype%\": [\"Uint32Array\", \"prototype\"],\n    \"%URIErrorPrototype%\": [\"URIError\", \"prototype\"],\n    \"%WeakMapPrototype%\": [\"WeakMap\", \"prototype\"],\n    \"%WeakSetPrototype%\": [\"WeakSet\", \"prototype\"]\n  }, ne = Br(), le = /* @__PURE__ */ A1(), he = ne.call(L, Array.prototype.concat), O = ne.call(N, Array.prototype.splice), _ = ne.call(L, String.prototype.replace), A = ne.call(L, String.prototype.slice), j = ne.call(L, RegExp.prototype.exec), B = /[^%.[\\]]+|\\[(?:(-?\\d+(?:\\.\\d+)?)|([\"'])((?:(?!\\2)[^\\\\]|\\\\.)*?)\\2)\\]|(?=(?:\\.|\\[\\])(?:\\.|\\[\\]|%$))/g, U = /\\\\(\\\\)?/g, z = function(x) {\n    var Y = A(x, 0, 1), Z = A(x, -1);\n    if (Y === \"%\" && Z !== \"%\")\n      throw new a(\"invalid intrinsic syntax, expected closing `%`\");\n    if (Z === \"%\" && Y !== \"%\")\n      throw new a(\"invalid intrinsic syntax, expected opening `%`\");\n    var ue = [];\n    return _(x, B, function(ge, Ke, ye, bn) {\n      ue[ue.length] = ye ? _(bn, U, \"$1\") : Ke || ge;\n    }), ue;\n  }, q = function(x, Y) {\n    var Z = x, ue;\n    if (le(W, Z) && (ue = W[Z], Z = \"%\" + ue[0] + \"%\"), le(ce, Z)) {\n      var ge = ce[Z];\n      if (ge === V && (ge = K(Z)), typeof ge > \"u\" && !Y)\n        throw new s(\"intrinsic \" + x + \" exists, but is not available. Please file an issue!\");\n      return {\n        alias: ue,\n        name: Z,\n        value: ge\n      };\n    }\n    throw new a(\"intrinsic \" + x + \" does not exist!\");\n  };\n  return oa = function(x, Y) {\n    if (typeof x != \"string\" || x.length === 0)\n      throw new s(\"intrinsic name must be a non-empty string\");\n    if (arguments.length > 1 && typeof Y != \"boolean\")\n      throw new s('\"allowMissing\" argument must be a boolean');\n    if (j(/^%?[^%]*%?$/, x) === null)\n      throw new a(\"`%` may not be present anywhere but at the beginning and end of the intrinsic name\");\n    var Z = z(x), ue = Z.length > 0 ? Z[0] : \"\", ge = q(\"%\" + ue + \"%\", Y), Ke = ge.name, ye = ge.value, bn = !1, Zn = ge.alias;\n    Zn && (ue = Zn[0], O(Z, he([0, 1], Zn)));\n    for (var P = 1, nn = !0; P < Z.length; P += 1) {\n      var tt = Z[P], Dr = A(tt, 0, 1), qr = A(tt, -1);\n      if ((Dr === '\"' || Dr === \"'\" || Dr === \"`\" || qr === '\"' || qr === \"'\" || qr === \"`\") && Dr !== qr)\n        throw new a(\"property names with quotes must have matching quotes\");\n      if ((tt === \"constructor\" || !nn) && (bn = !0), ue += \".\" + tt, Ke = \"%\" + ue + \"%\", le(ce, Ke))\n        ye = ce[Ke];\n      else if (ye != null) {\n        if (!(tt in ye)) {\n          if (!Y)\n            throw new s(\"base intrinsic for \" + x + \" exists, but the property is not available.\");\n          return;\n        }\n        if (g && P + 1 >= Z.length) {\n          var Lr = g(ye, tt);\n          nn = !!Lr, nn && \"get\" in Lr && !(\"originalValue\" in Lr.get) ? ye = Lr.get : ye = ye[tt];\n        } else\n          nn = le(ye, tt), ye = ye[tt];\n        nn && !bn && (ce[Ke] = ye);\n      }\n    }\n    return ye;\n  }, oa;\n}\nvar ia, Lu;\nfunction Fr() {\n  if (Lu) return ia;\n  Lu = 1;\n  var e = /* @__PURE__ */ I1(), t = xc(), n = t([e(\"%String.prototype.indexOf%\")]);\n  return ia = function(o, i) {\n    var a = (\n      /** @type {(this: unknown, ...args: unknown[]) => unknown} */\n      e(o, !!i)\n    );\n    return typeof a == \"function\" && n(o, \".prototype.\") > -1 ? t(\n      /** @type {const} */\n      [a]\n    ) : a;\n  }, ia;\n}\nvar aa, Hu;\nfunction q7() {\n  if (Hu) return aa;\n  Hu = 1;\n  var e = ri()(), t = /* @__PURE__ */ Fr(), n = t(\"Object.prototype.toString\"), r = function(s) {\n    return e && s && typeof s == \"object\" && Symbol.toStringTag in s ? !1 : n(s) === \"[object Arguments]\";\n  }, o = function(s) {\n    return r(s) ? !0 : s !== null && typeof s == \"object\" && \"length\" in s && typeof s.length == \"number\" && s.length >= 0 && n(s) !== \"[object Array]\" && \"callee\" in s && n(s.callee) === \"[object Function]\";\n  }, i = (function() {\n    return r(arguments);\n  })();\n  return r.isLegacyArguments = o, aa = i ? r : o, aa;\n}\nvar sa, $u;\nfunction L7() {\n  if ($u) return sa;\n  $u = 1;\n  var e = /* @__PURE__ */ Fr(), t = ri()(), n = /* @__PURE__ */ A1(), r = /* @__PURE__ */ Wn(), o;\n  if (t) {\n    var i = e(\"RegExp.prototype.exec\"), a = {}, s = function() {\n      throw a;\n    }, c = {\n      toString: s,\n      valueOf: s\n    };\n    typeof Symbol.toPrimitive == \"symbol\" && (c[Symbol.toPrimitive] = s), o = function(u) {\n      if (!u || typeof u != \"object\")\n        return !1;\n      var b = (\n        /** @type {NonNullable<typeof gOPD>} */\n        r(\n          /** @type {{ lastIndex?: unknown }} */\n          u,\n          \"lastIndex\"\n        )\n      ), h = b && n(b, \"value\");\n      if (!h)\n        return !1;\n      try {\n        i(\n          u,\n          /** @type {string} */\n          /** @type {unknown} */\n          c\n        );\n      } catch (w) {\n        return w === a;\n      }\n    };\n  } else {\n    var l = e(\"Object.prototype.toString\"), f = \"[object RegExp]\";\n    o = function(u) {\n      return !u || typeof u != \"object\" && typeof u != \"function\" ? !1 : l(u) === f;\n    };\n  }\n  return sa = o, sa;\n}\nvar ca, Uu;\nfunction H7() {\n  if (Uu) return ca;\n  Uu = 1;\n  var e = /* @__PURE__ */ Fr(), t = L7(), n = e(\"RegExp.prototype.exec\"), r = /* @__PURE__ */ zr();\n  return ca = function(i) {\n    if (!t(i))\n      throw new r(\"`regex` must be a RegExp\");\n    return function(s) {\n      return n(i, s) !== null;\n    };\n  }, ca;\n}\nvar la, Ku;\nfunction $7() {\n  if (Ku) return la;\n  Ku = 1;\n  const e = (\n    /** @type {GeneratorFunctionConstructor} */\n    (function* () {\n    }).constructor\n  );\n  return la = () => e, la;\n}\nvar ua, Gu;\nfunction U7() {\n  if (Gu) return ua;\n  Gu = 1;\n  var e = /* @__PURE__ */ Fr(), t = /* @__PURE__ */ H7(), n = t(/^\\s*(?:function)?\\*/), r = ri()(), o = zc(), i = e(\"Object.prototype.toString\"), a = e(\"Function.prototype.toString\"), s = /* @__PURE__ */ $7();\n  return ua = function(l) {\n    if (typeof l != \"function\")\n      return !1;\n    if (n(a(l)))\n      return !0;\n    if (!r) {\n      var f = i(l);\n      return f === \"[object GeneratorFunction]\";\n    }\n    if (!o)\n      return !1;\n    var d = s();\n    return d && o(l) === d.prototype;\n  }, ua;\n}\nvar fa, Vu;\nfunction K7() {\n  if (Vu) return fa;\n  Vu = 1;\n  var e = Function.prototype.toString, t = typeof Reflect == \"object\" && Reflect !== null && Reflect.apply, n, r;\n  if (typeof t == \"function\" && typeof Object.defineProperty == \"function\")\n    try {\n      n = Object.defineProperty({}, \"length\", {\n        get: function() {\n          throw r;\n        }\n      }), r = {}, t(function() {\n        throw 42;\n      }, null, n);\n    } catch (g) {\n      g !== r && (t = null);\n    }\n  else\n    t = null;\n  var o = /^\\s*class\\b/, i = function(T) {\n    try {\n      var y = e.call(T);\n      return o.test(y);\n    } catch {\n      return !1;\n    }\n  }, a = function(T) {\n    try {\n      return i(T) ? !1 : (e.call(T), !0);\n    } catch {\n      return !1;\n    }\n  }, s = Object.prototype.toString, c = \"[object Object]\", l = \"[object Function]\", f = \"[object GeneratorFunction]\", d = \"[object HTMLAllCollection]\", u = \"[object HTML document.all class]\", b = \"[object HTMLCollection]\", h = typeof Symbol == \"function\" && !!Symbol.toStringTag, w = !(0 in [,]), E = function() {\n    return !1;\n  };\n  if (typeof document == \"object\") {\n    var m = document.all;\n    s.call(m) === s.call(document.all) && (E = function(T) {\n      if ((w || !T) && (typeof T > \"u\" || typeof T == \"object\"))\n        try {\n          var y = s.call(T);\n          return (y === d || y === u || y === b || y === c) && T(\"\") == null;\n        } catch {\n        }\n      return !1;\n    });\n  }\n  return fa = t ? function(T) {\n    if (E(T))\n      return !0;\n    if (!T || typeof T != \"function\" && typeof T != \"object\")\n      return !1;\n    try {\n      t(T, null, n);\n    } catch (y) {\n      if (y !== r)\n        return !1;\n    }\n    return !i(T) && a(T);\n  } : function(T) {\n    if (E(T))\n      return !0;\n    if (!T || typeof T != \"function\" && typeof T != \"object\")\n      return !1;\n    if (h)\n      return a(T);\n    if (i(T))\n      return !1;\n    var y = s.call(T);\n    return y !== l && y !== f && !/^\\[object HTML/.test(y) ? !1 : a(T);\n  }, fa;\n}\nvar da, Yu;\nfunction G7() {\n  if (Yu) return da;\n  Yu = 1;\n  var e = K7(), t = Object.prototype.toString, n = Object.prototype.hasOwnProperty, r = function(c, l, f) {\n    for (var d = 0, u = c.length; d < u; d++)\n      n.call(c, d) && (f == null ? l(c[d], d, c) : l.call(f, c[d], d, c));\n  }, o = function(c, l, f) {\n    for (var d = 0, u = c.length; d < u; d++)\n      f == null ? l(c.charAt(d), d, c) : l.call(f, c.charAt(d), d, c);\n  }, i = function(c, l, f) {\n    for (var d in c)\n      n.call(c, d) && (f == null ? l(c[d], d, c) : l.call(f, c[d], d, c));\n  };\n  function a(s) {\n    return t.call(s) === \"[object Array]\";\n  }\n  return da = function(c, l, f) {\n    if (!e(l))\n      throw new TypeError(\"iterator must be a function\");\n    var d;\n    arguments.length >= 3 && (d = f), a(c) ? r(c, l, d) : typeof c == \"string\" ? o(c, l, d) : i(c, l, d);\n  }, da;\n}\nvar pa, Wu;\nfunction V7() {\n  return Wu || (Wu = 1, pa = [\n    \"Float16Array\",\n    \"Float32Array\",\n    \"Float64Array\",\n    \"Int8Array\",\n    \"Int16Array\",\n    \"Int32Array\",\n    \"Uint8Array\",\n    \"Uint8ClampedArray\",\n    \"Uint16Array\",\n    \"Uint32Array\",\n    \"BigInt64Array\",\n    \"BigUint64Array\"\n  ]), pa;\n}\nvar ha, Zu;\nfunction Y7() {\n  if (Zu) return ha;\n  Zu = 1;\n  var e = /* @__PURE__ */ V7(), t = typeof globalThis > \"u\" ? Cf : globalThis;\n  return ha = function() {\n    for (var r = [], o = 0; o < e.length; o++)\n      typeof t[e[o]] == \"function\" && (r[r.length] = e[o]);\n    return r;\n  }, ha;\n}\nvar ma = { exports: {} }, ga, Ju;\nfunction W7() {\n  if (Ju) return ga;\n  Ju = 1;\n  var e = /* @__PURE__ */ oi(), t = /* @__PURE__ */ w1(), n = /* @__PURE__ */ zr(), r = /* @__PURE__ */ Wn();\n  return ga = function(i, a, s) {\n    if (!i || typeof i != \"object\" && typeof i != \"function\")\n      throw new n(\"`obj` must be an object or a function`\");\n    if (typeof a != \"string\" && typeof a != \"symbol\")\n      throw new n(\"`property` must be a string or a symbol`\");\n    if (arguments.length > 3 && typeof arguments[3] != \"boolean\" && arguments[3] !== null)\n      throw new n(\"`nonEnumerable`, if provided, must be a boolean or null\");\n    if (arguments.length > 4 && typeof arguments[4] != \"boolean\" && arguments[4] !== null)\n      throw new n(\"`nonWritable`, if provided, must be a boolean or null\");\n    if (arguments.length > 5 && typeof arguments[5] != \"boolean\" && arguments[5] !== null)\n      throw new n(\"`nonConfigurable`, if provided, must be a boolean or null\");\n    if (arguments.length > 6 && typeof arguments[6] != \"boolean\")\n      throw new n(\"`loose`, if provided, must be a boolean\");\n    var c = arguments.length > 3 ? arguments[3] : null, l = arguments.length > 4 ? arguments[4] : null, f = arguments.length > 5 ? arguments[5] : null, d = arguments.length > 6 ? arguments[6] : !1, u = !!r && r(i, a);\n    if (e)\n      e(i, a, {\n        configurable: f === null && u ? u.configurable : !f,\n        enumerable: c === null && u ? u.enumerable : !c,\n        value: s,\n        writable: l === null && u ? u.writable : !l\n      });\n    else if (d || !c && !l && !f)\n      i[a] = s;\n    else\n      throw new t(\"This environment does not support defining a property as non-configurable, non-writable, or non-enumerable.\");\n  }, ga;\n}\nvar ya, Qu;\nfunction Z7() {\n  if (Qu) return ya;\n  Qu = 1;\n  var e = /* @__PURE__ */ oi(), t = function() {\n    return !!e;\n  };\n  return t.hasArrayLengthDefineBug = function() {\n    if (!e)\n      return null;\n    try {\n      return e([], \"length\", { value: 1 }).length !== 1;\n    } catch {\n      return !0;\n    }\n  }, ya = t, ya;\n}\nvar va, Xu;\nfunction J7() {\n  if (Xu) return va;\n  Xu = 1;\n  var e = /* @__PURE__ */ I1(), t = /* @__PURE__ */ W7(), n = /* @__PURE__ */ Z7()(), r = /* @__PURE__ */ Wn(), o = /* @__PURE__ */ zr(), i = e(\"%Math.floor%\");\n  return va = function(s, c) {\n    if (typeof s != \"function\")\n      throw new o(\"`fn` is not a function\");\n    if (typeof c != \"number\" || c < 0 || c > 4294967295 || i(c) !== c)\n      throw new o(\"`length` must be a positive 32-bit integer\");\n    var l = arguments.length > 2 && !!arguments[2], f = !0, d = !0;\n    if (\"length\" in s && r) {\n      var u = r(s, \"length\");\n      u && !u.configurable && (f = !1), u && !u.writable && (d = !1);\n    }\n    return (f || d || !l) && (n ? t(\n      /** @type {Parameters<define>[0]} */\n      s,\n      \"length\",\n      c,\n      !0,\n      !0\n    ) : t(\n      /** @type {Parameters<define>[0]} */\n      s,\n      \"length\",\n      c\n    )), s;\n  }, va;\n}\nvar ba, ef;\nfunction Q7() {\n  if (ef) return ba;\n  ef = 1;\n  var e = Br(), t = Nc(), n = T1();\n  return ba = function() {\n    return n(e, t, arguments);\n  }, ba;\n}\nvar tf;\nfunction X7() {\n  return tf || (tf = 1, (function(e) {\n    var t = /* @__PURE__ */ J7(), n = /* @__PURE__ */ oi(), r = xc(), o = Q7();\n    e.exports = function(a) {\n      var s = r(arguments), c = a.length - (arguments.length - 1);\n      return t(\n        s,\n        1 + (c > 0 ? c : 0),\n        !0\n      );\n    }, n ? n(e.exports, \"apply\", { value: o }) : e.exports.apply = o;\n  })(ma)), ma.exports;\n}\nvar _a, nf;\nfunction j1() {\n  if (nf) return _a;\n  nf = 1;\n  var e = G7(), t = /* @__PURE__ */ Y7(), n = X7(), r = /* @__PURE__ */ Fr(), o = /* @__PURE__ */ Wn(), i = zc(), a = r(\"Object.prototype.toString\"), s = ri()(), c = typeof globalThis > \"u\" ? Cf : globalThis, l = t(), f = r(\"String.prototype.slice\"), d = r(\"Array.prototype.indexOf\", !0) || function(E, m) {\n    for (var g = 0; g < E.length; g += 1)\n      if (E[g] === m)\n        return g;\n    return -1;\n  }, u = { __proto__: null };\n  s && o && i ? e(l, function(w) {\n    var E = new c[w]();\n    if (Symbol.toStringTag in E && i) {\n      var m = i(E), g = o(m, Symbol.toStringTag);\n      if (!g && m) {\n        var T = i(m);\n        g = o(T, Symbol.toStringTag);\n      }\n      if (g && g.get) {\n        var y = n(g.get);\n        u[\n          /** @type {`$${import('.').TypedArrayName}`} */\n          \"$\" + w\n        ] = y;\n      }\n    }\n  }) : e(l, function(w) {\n    var E = new c[w](), m = E.slice || E.set;\n    if (m) {\n      var g = (\n        /** @type {import('./types').BoundSlice | import('./types').BoundSet} */\n        // @ts-expect-error TODO FIXME\n        n(m)\n      );\n      u[\n        /** @type {`$${import('.').TypedArrayName}`} */\n        \"$\" + w\n      ] = g;\n    }\n  });\n  var b = function(E) {\n    var m = !1;\n    return e(\n      /** @type {Record<`\\$${import('.').TypedArrayName}`, Getter>} */\n      u,\n      /** @type {(getter: Getter, name: `\\$${import('.').TypedArrayName}`) => void} */\n      function(g, T) {\n        if (!m)\n          try {\n            \"$\" + g(E) === T && (m = /** @type {import('.').TypedArrayName} */\n            f(T, 1));\n          } catch {\n          }\n      }\n    ), m;\n  }, h = function(E) {\n    var m = !1;\n    return e(\n      /** @type {Record<`\\$${import('.').TypedArrayName}`, Getter>} */\n      u,\n      /** @type {(getter: Getter, name: `\\$${import('.').TypedArrayName}`) => void} */\n      function(g, T) {\n        if (!m)\n          try {\n            g(E), m = /** @type {import('.').TypedArrayName} */\n            f(T, 1);\n          } catch {\n          }\n      }\n    ), m;\n  };\n  return _a = function(E) {\n    if (!E || typeof E != \"object\")\n      return !1;\n    if (!s) {\n      var m = f(a(E), 8, -1);\n      return d(l, m) > -1 ? m : m !== \"Object\" ? !1 : h(E);\n    }\n    return o ? b(E) : null;\n  }, _a;\n}\nvar wa, rf;\nfunction e3() {\n  if (rf) return wa;\n  rf = 1;\n  var e = /* @__PURE__ */ j1();\n  return wa = function(n) {\n    return !!e(n);\n  }, wa;\n}\nvar of;\nfunction t3() {\n  return of || (of = 1, (function(e) {\n    var t = /* @__PURE__ */ q7(), n = U7(), r = /* @__PURE__ */ j1(), o = /* @__PURE__ */ e3();\n    function i(P) {\n      return P.call.bind(P);\n    }\n    var a = typeof BigInt < \"u\", s = typeof Symbol < \"u\", c = i(Object.prototype.toString), l = i(Number.prototype.valueOf), f = i(String.prototype.valueOf), d = i(Boolean.prototype.valueOf);\n    if (a)\n      var u = i(BigInt.prototype.valueOf);\n    if (s)\n      var b = i(Symbol.prototype.valueOf);\n    function h(P, nn) {\n      if (typeof P != \"object\")\n        return !1;\n      try {\n        return nn(P), !0;\n      } catch {\n        return !1;\n      }\n    }\n    e.isArgumentsObject = t, e.isGeneratorFunction = n, e.isTypedArray = o;\n    function w(P) {\n      return typeof Promise < \"u\" && P instanceof Promise || P !== null && typeof P == \"object\" && typeof P.then == \"function\" && typeof P.catch == \"function\";\n    }\n    e.isPromise = w;\n    function E(P) {\n      return typeof ArrayBuffer < \"u\" && ArrayBuffer.isView ? ArrayBuffer.isView(P) : o(P) || A(P);\n    }\n    e.isArrayBufferView = E;\n    function m(P) {\n      return r(P) === \"Uint8Array\";\n    }\n    e.isUint8Array = m;\n    function g(P) {\n      return r(P) === \"Uint8ClampedArray\";\n    }\n    e.isUint8ClampedArray = g;\n    function T(P) {\n      return r(P) === \"Uint16Array\";\n    }\n    e.isUint16Array = T;\n    function y(P) {\n      return r(P) === \"Uint32Array\";\n    }\n    e.isUint32Array = y;\n    function v(P) {\n      return r(P) === \"Int8Array\";\n    }\n    e.isInt8Array = v;\n    function S(P) {\n      return r(P) === \"Int16Array\";\n    }\n    e.isInt16Array = S;\n    function I(P) {\n      return r(P) === \"Int32Array\";\n    }\n    e.isInt32Array = I;\n    function k(P) {\n      return r(P) === \"Float32Array\";\n    }\n    e.isFloat32Array = k;\n    function M(P) {\n      return r(P) === \"Float64Array\";\n    }\n    e.isFloat64Array = M;\n    function N(P) {\n      return r(P) === \"BigInt64Array\";\n    }\n    e.isBigInt64Array = N;\n    function L(P) {\n      return r(P) === \"BigUint64Array\";\n    }\n    e.isBigUint64Array = L;\n    function V(P) {\n      return c(P) === \"[object Map]\";\n    }\n    V.working = typeof Map < \"u\" && V(/* @__PURE__ */ new Map());\n    function ie(P) {\n      return typeof Map > \"u\" ? !1 : V.working ? V(P) : P instanceof Map;\n    }\n    e.isMap = ie;\n    function ce(P) {\n      return c(P) === \"[object Set]\";\n    }\n    ce.working = typeof Set < \"u\" && ce(/* @__PURE__ */ new Set());\n    function D(P) {\n      return typeof Set > \"u\" ? !1 : ce.working ? ce(P) : P instanceof Set;\n    }\n    e.isSet = D;\n    function K(P) {\n      return c(P) === \"[object WeakMap]\";\n    }\n    K.working = typeof WeakMap < \"u\" && K(/* @__PURE__ */ new WeakMap());\n    function W(P) {\n      return typeof WeakMap > \"u\" ? !1 : K.working ? K(P) : P instanceof WeakMap;\n    }\n    e.isWeakMap = W;\n    function ne(P) {\n      return c(P) === \"[object WeakSet]\";\n    }\n    ne.working = typeof WeakSet < \"u\" && ne(/* @__PURE__ */ new WeakSet());\n    function le(P) {\n      return ne(P);\n    }\n    e.isWeakSet = le;\n    function he(P) {\n      return c(P) === \"[object ArrayBuffer]\";\n    }\n    he.working = typeof ArrayBuffer < \"u\" && he(new ArrayBuffer());\n    function O(P) {\n      return typeof ArrayBuffer > \"u\" ? !1 : he.working ? he(P) : P instanceof ArrayBuffer;\n    }\n    e.isArrayBuffer = O;\n    function _(P) {\n      return c(P) === \"[object DataView]\";\n    }\n    _.working = typeof ArrayBuffer < \"u\" && typeof DataView < \"u\" && _(new DataView(new ArrayBuffer(1), 0, 1));\n    function A(P) {\n      return typeof DataView > \"u\" ? !1 : _.working ? _(P) : P instanceof DataView;\n    }\n    e.isDataView = A;\n    var j = typeof SharedArrayBuffer < \"u\" ? SharedArrayBuffer : void 0;\n    function B(P) {\n      return c(P) === \"[object SharedArrayBuffer]\";\n    }\n    function U(P) {\n      return typeof j > \"u\" ? !1 : (typeof B.working > \"u\" && (B.working = B(new j())), B.working ? B(P) : P instanceof j);\n    }\n    e.isSharedArrayBuffer = U;\n    function z(P) {\n      return c(P) === \"[object AsyncFunction]\";\n    }\n    e.isAsyncFunction = z;\n    function q(P) {\n      return c(P) === \"[object Map Iterator]\";\n    }\n    e.isMapIterator = q;\n    function F(P) {\n      return c(P) === \"[object Set Iterator]\";\n    }\n    e.isSetIterator = F;\n    function x(P) {\n      return c(P) === \"[object Generator]\";\n    }\n    e.isGeneratorObject = x;\n    function Y(P) {\n      return c(P) === \"[object WebAssembly.Module]\";\n    }\n    e.isWebAssemblyCompiledModule = Y;\n    function Z(P) {\n      return h(P, l);\n    }\n    e.isNumberObject = Z;\n    function ue(P) {\n      return h(P, f);\n    }\n    e.isStringObject = ue;\n    function ge(P) {\n      return h(P, d);\n    }\n    e.isBooleanObject = ge;\n    function Ke(P) {\n      return a && h(P, u);\n    }\n    e.isBigIntObject = Ke;\n    function ye(P) {\n      return s && h(P, b);\n    }\n    e.isSymbolObject = ye;\n    function bn(P) {\n      return Z(P) || ue(P) || ge(P) || Ke(P) || ye(P);\n    }\n    e.isBoxedPrimitive = bn;\n    function Zn(P) {\n      return typeof Uint8Array < \"u\" && (O(P) || U(P));\n    }\n    e.isAnyArrayBuffer = Zn, [\"isProxy\", \"isExternal\", \"isModuleNamespaceObject\"].forEach(function(P) {\n      Object.defineProperty(e, P, {\n        enumerable: !1,\n        value: function() {\n          throw new Error(P + \" is not supported in userland\");\n        }\n      });\n    });\n  })(Si)), Si;\n}\nvar Ea, af;\nfunction n3() {\n  return af || (af = 1, Ea = function(t) {\n    return t && typeof t == \"object\" && typeof t.copy == \"function\" && typeof t.fill == \"function\" && typeof t.readUInt8 == \"function\";\n  }), Ea;\n}\nvar Wr = { exports: {} }, sf;\nfunction r3() {\n  return sf || (sf = 1, typeof Object.create == \"function\" ? Wr.exports = function(t, n) {\n    n && (t.super_ = n, t.prototype = Object.create(n.prototype, {\n      constructor: {\n        value: t,\n        enumerable: !1,\n        writable: !0,\n        configurable: !0\n      }\n    }));\n  } : Wr.exports = function(t, n) {\n    if (n) {\n      t.super_ = n;\n      var r = function() {\n      };\n      r.prototype = n.prototype, t.prototype = new r(), t.prototype.constructor = t;\n    }\n  }), Wr.exports;\n}\nvar cf;\nfunction lf() {\n  return cf || (cf = 1, (function(e) {\n    var t = Object.getOwnPropertyDescriptors || function(A) {\n      for (var j = Object.keys(A), B = {}, U = 0; U < j.length; U++)\n        B[j[U]] = Object.getOwnPropertyDescriptor(A, j[U]);\n      return B;\n    }, n = /%[sdj%]/g;\n    e.format = function(_) {\n      if (!v(_)) {\n        for (var A = [], j = 0; j < arguments.length; j++)\n          A.push(a(arguments[j]));\n        return A.join(\" \");\n      }\n      for (var j = 1, B = arguments, U = B.length, z = String(_).replace(n, function(F) {\n        if (F === \"%%\") return \"%\";\n        if (j >= U) return F;\n        switch (F) {\n          case \"%s\":\n            return String(B[j++]);\n          case \"%d\":\n            return Number(B[j++]);\n          case \"%j\":\n            try {\n              return JSON.stringify(B[j++]);\n            } catch {\n              return \"[Circular]\";\n            }\n          default:\n            return F;\n        }\n      }), q = B[j]; j < U; q = B[++j])\n        g(q) || !M(q) ? z += \" \" + q : z += \" \" + a(q);\n      return z;\n    }, e.deprecate = function(_, A) {\n      if (typeof process < \"u\" && process.noDeprecation === !0)\n        return _;\n      if (typeof process > \"u\")\n        return function() {\n          return e.deprecate(_, A).apply(this, arguments);\n        };\n      var j = !1;\n      function B() {\n        if (!j) {\n          if (process.throwDeprecation)\n            throw new Error(A);\n          process.traceDeprecation ? console.trace(A) : console.error(A), j = !0;\n        }\n        return _.apply(this, arguments);\n      }\n      return B;\n    };\n    var r = {}, o = /^$/;\n    if (process.env.NODE_DEBUG) {\n      var i = process.env.NODE_DEBUG;\n      i = i.replace(/[|\\\\{}()[\\]^$+?.]/g, \"\\\\$&\").replace(/\\*/g, \".*\").replace(/,/g, \"$|^\").toUpperCase(), o = new RegExp(\"^\" + i + \"$\", \"i\");\n    }\n    e.debuglog = function(_) {\n      if (_ = _.toUpperCase(), !r[_])\n        if (o.test(_)) {\n          var A = process.pid;\n          r[_] = function() {\n            var j = e.format.apply(e, arguments);\n            console.error(\"%s %d: %s\", _, A, j);\n          };\n        } else\n          r[_] = function() {\n          };\n      return r[_];\n    };\n    function a(_, A) {\n      var j = {\n        seen: [],\n        stylize: c\n      };\n      return arguments.length >= 3 && (j.depth = arguments[2]), arguments.length >= 4 && (j.colors = arguments[3]), m(A) ? j.showHidden = A : A && e._extend(j, A), I(j.showHidden) && (j.showHidden = !1), I(j.depth) && (j.depth = 2), I(j.colors) && (j.colors = !1), I(j.customInspect) && (j.customInspect = !0), j.colors && (j.stylize = s), f(j, _, j.depth);\n    }\n    e.inspect = a, a.colors = {\n      bold: [1, 22],\n      italic: [3, 23],\n      underline: [4, 24],\n      inverse: [7, 27],\n      white: [37, 39],\n      grey: [90, 39],\n      black: [30, 39],\n      blue: [34, 39],\n      cyan: [36, 39],\n      green: [32, 39],\n      magenta: [35, 39],\n      red: [31, 39],\n      yellow: [33, 39]\n    }, a.styles = {\n      special: \"cyan\",\n      number: \"yellow\",\n      boolean: \"yellow\",\n      undefined: \"grey\",\n      null: \"bold\",\n      string: \"green\",\n      date: \"magenta\",\n      // \"name\": intentionally not styling\n      regexp: \"red\"\n    };\n    function s(_, A) {\n      var j = a.styles[A];\n      return j ? \"\\x1B[\" + a.colors[j][0] + \"m\" + _ + \"\\x1B[\" + a.colors[j][1] + \"m\" : _;\n    }\n    function c(_, A) {\n      return _;\n    }\n    function l(_) {\n      var A = {};\n      return _.forEach(function(j, B) {\n        A[j] = !0;\n      }), A;\n    }\n    function f(_, A, j) {\n      if (_.customInspect && A && V(A.inspect) && // Filter out the util module, it's inspect function is special\n      A.inspect !== e.inspect && // Also filter out any prototype objects using the circular check.\n      !(A.constructor && A.constructor.prototype === A)) {\n        var B = A.inspect(j, _);\n        return v(B) || (B = f(_, B, j)), B;\n      }\n      var U = d(_, A);\n      if (U)\n        return U;\n      var z = Object.keys(A), q = l(z);\n      if (_.showHidden && (z = Object.getOwnPropertyNames(A)), L(A) && (z.indexOf(\"message\") >= 0 || z.indexOf(\"description\") >= 0))\n        return u(A);\n      if (z.length === 0) {\n        if (V(A)) {\n          var F = A.name ? \": \" + A.name : \"\";\n          return _.stylize(\"[Function\" + F + \"]\", \"special\");\n        }\n        if (k(A))\n          return _.stylize(RegExp.prototype.toString.call(A), \"regexp\");\n        if (N(A))\n          return _.stylize(Date.prototype.toString.call(A), \"date\");\n        if (L(A))\n          return u(A);\n      }\n      var x = \"\", Y = !1, Z = [\"{\", \"}\"];\n      if (E(A) && (Y = !0, Z = [\"[\", \"]\"]), V(A)) {\n        var ue = A.name ? \": \" + A.name : \"\";\n        x = \" [Function\" + ue + \"]\";\n      }\n      if (k(A) && (x = \" \" + RegExp.prototype.toString.call(A)), N(A) && (x = \" \" + Date.prototype.toUTCString.call(A)), L(A) && (x = \" \" + u(A)), z.length === 0 && (!Y || A.length == 0))\n        return Z[0] + x + Z[1];\n      if (j < 0)\n        return k(A) ? _.stylize(RegExp.prototype.toString.call(A), \"regexp\") : _.stylize(\"[Object]\", \"special\");\n      _.seen.push(A);\n      var ge;\n      return Y ? ge = b(_, A, j, q, z) : ge = z.map(function(Ke) {\n        return h(_, A, j, q, Ke, Y);\n      }), _.seen.pop(), w(ge, x, Z);\n    }\n    function d(_, A) {\n      if (I(A))\n        return _.stylize(\"undefined\", \"undefined\");\n      if (v(A)) {\n        var j = \"'\" + JSON.stringify(A).replace(/^\"|\"$/g, \"\").replace(/'/g, \"\\\\'\").replace(/\\\\\"/g, '\"') + \"'\";\n        return _.stylize(j, \"string\");\n      }\n      if (y(A))\n        return _.stylize(\"\" + A, \"number\");\n      if (m(A))\n        return _.stylize(\"\" + A, \"boolean\");\n      if (g(A))\n        return _.stylize(\"null\", \"null\");\n    }\n    function u(_) {\n      return \"[\" + Error.prototype.toString.call(_) + \"]\";\n    }\n    function b(_, A, j, B, U) {\n      for (var z = [], q = 0, F = A.length; q < F; ++q)\n        ne(A, String(q)) ? z.push(h(\n          _,\n          A,\n          j,\n          B,\n          String(q),\n          !0\n        )) : z.push(\"\");\n      return U.forEach(function(x) {\n        x.match(/^\\d+$/) || z.push(h(\n          _,\n          A,\n          j,\n          B,\n          x,\n          !0\n        ));\n      }), z;\n    }\n    function h(_, A, j, B, U, z) {\n      var q, F, x;\n      if (x = Object.getOwnPropertyDescriptor(A, U) || { value: A[U] }, x.get ? x.set ? F = _.stylize(\"[Getter/Setter]\", \"special\") : F = _.stylize(\"[Getter]\", \"special\") : x.set && (F = _.stylize(\"[Setter]\", \"special\")), ne(B, U) || (q = \"[\" + U + \"]\"), F || (_.seen.indexOf(x.value) < 0 ? (g(j) ? F = f(_, x.value, null) : F = f(_, x.value, j - 1), F.indexOf(`\n`) > -1 && (z ? F = F.split(`\n`).map(function(Y) {\n        return \"  \" + Y;\n      }).join(`\n`).slice(2) : F = `\n` + F.split(`\n`).map(function(Y) {\n        return \"   \" + Y;\n      }).join(`\n`))) : F = _.stylize(\"[Circular]\", \"special\")), I(q)) {\n        if (z && U.match(/^\\d+$/))\n          return F;\n        q = JSON.stringify(\"\" + U), q.match(/^\"([a-zA-Z_][a-zA-Z_0-9]*)\"$/) ? (q = q.slice(1, -1), q = _.stylize(q, \"name\")) : (q = q.replace(/'/g, \"\\\\'\").replace(/\\\\\"/g, '\"').replace(/(^\"|\"$)/g, \"'\"), q = _.stylize(q, \"string\"));\n      }\n      return q + \": \" + F;\n    }\n    function w(_, A, j) {\n      var B = _.reduce(function(U, z) {\n        return z.indexOf(`\n`) >= 0, U + z.replace(/\\u001b\\[\\d\\d?m/g, \"\").length + 1;\n      }, 0);\n      return B > 60 ? j[0] + (A === \"\" ? \"\" : A + `\n `) + \" \" + _.join(`,\n  `) + \" \" + j[1] : j[0] + A + \" \" + _.join(\", \") + \" \" + j[1];\n    }\n    e.types = t3();\n    function E(_) {\n      return Array.isArray(_);\n    }\n    e.isArray = E;\n    function m(_) {\n      return typeof _ == \"boolean\";\n    }\n    e.isBoolean = m;\n    function g(_) {\n      return _ === null;\n    }\n    e.isNull = g;\n    function T(_) {\n      return _ == null;\n    }\n    e.isNullOrUndefined = T;\n    function y(_) {\n      return typeof _ == \"number\";\n    }\n    e.isNumber = y;\n    function v(_) {\n      return typeof _ == \"string\";\n    }\n    e.isString = v;\n    function S(_) {\n      return typeof _ == \"symbol\";\n    }\n    e.isSymbol = S;\n    function I(_) {\n      return _ === void 0;\n    }\n    e.isUndefined = I;\n    function k(_) {\n      return M(_) && ce(_) === \"[object RegExp]\";\n    }\n    e.isRegExp = k, e.types.isRegExp = k;\n    function M(_) {\n      return typeof _ == \"object\" && _ !== null;\n    }\n    e.isObject = M;\n    function N(_) {\n      return M(_) && ce(_) === \"[object Date]\";\n    }\n    e.isDate = N, e.types.isDate = N;\n    function L(_) {\n      return M(_) && (ce(_) === \"[object Error]\" || _ instanceof Error);\n    }\n    e.isError = L, e.types.isNativeError = L;\n    function V(_) {\n      return typeof _ == \"function\";\n    }\n    e.isFunction = V;\n    function ie(_) {\n      return _ === null || typeof _ == \"boolean\" || typeof _ == \"number\" || typeof _ == \"string\" || typeof _ == \"symbol\" || // ES6 symbol\n      typeof _ > \"u\";\n    }\n    e.isPrimitive = ie, e.isBuffer = n3();\n    function ce(_) {\n      return Object.prototype.toString.call(_);\n    }\n    function D(_) {\n      return _ < 10 ? \"0\" + _.toString(10) : _.toString(10);\n    }\n    var K = [\n      \"Jan\",\n      \"Feb\",\n      \"Mar\",\n      \"Apr\",\n      \"May\",\n      \"Jun\",\n      \"Jul\",\n      \"Aug\",\n      \"Sep\",\n      \"Oct\",\n      \"Nov\",\n      \"Dec\"\n    ];\n    function W() {\n      var _ = /* @__PURE__ */ new Date(), A = [\n        D(_.getHours()),\n        D(_.getMinutes()),\n        D(_.getSeconds())\n      ].join(\":\");\n      return [_.getDate(), K[_.getMonth()], A].join(\" \");\n    }\n    e.log = function() {\n      console.log(\"%s - %s\", W(), e.format.apply(e, arguments));\n    }, e.inherits = r3(), e._extend = function(_, A) {\n      if (!A || !M(A)) return _;\n      for (var j = Object.keys(A), B = j.length; B--; )\n        _[j[B]] = A[j[B]];\n      return _;\n    };\n    function ne(_, A) {\n      return Object.prototype.hasOwnProperty.call(_, A);\n    }\n    var le = typeof Symbol < \"u\" ? /* @__PURE__ */ Symbol(\"util.promisify.custom\") : void 0;\n    e.promisify = function(A) {\n      if (typeof A != \"function\")\n        throw new TypeError('The \"original\" argument must be of type Function');\n      if (le && A[le]) {\n        var j = A[le];\n        if (typeof j != \"function\")\n          throw new TypeError('The \"util.promisify.custom\" argument must be of type Function');\n        return Object.defineProperty(j, le, {\n          value: j,\n          enumerable: !1,\n          writable: !1,\n          configurable: !0\n        }), j;\n      }\n      function j() {\n        for (var B, U, z = new Promise(function(x, Y) {\n          B = x, U = Y;\n        }), q = [], F = 0; F < arguments.length; F++)\n          q.push(arguments[F]);\n        q.push(function(x, Y) {\n          x ? U(x) : B(Y);\n        });\n        try {\n          A.apply(this, q);\n        } catch (x) {\n          U(x);\n        }\n        return z;\n      }\n      return Object.setPrototypeOf(j, Object.getPrototypeOf(A)), le && Object.defineProperty(j, le, {\n        value: j,\n        enumerable: !1,\n        writable: !1,\n        configurable: !0\n      }), Object.defineProperties(\n        j,\n        t(A)\n      );\n    }, e.promisify.custom = le;\n    function he(_, A) {\n      if (!_) {\n        var j = new Error(\"Promise was rejected with a falsy value\");\n        j.reason = _, _ = j;\n      }\n      return A(_);\n    }\n    function O(_) {\n      if (typeof _ != \"function\")\n        throw new TypeError('The \"original\" argument must be of type Function');\n      function A() {\n        for (var j = [], B = 0; B < arguments.length; B++)\n          j.push(arguments[B]);\n        var U = j.pop();\n        if (typeof U != \"function\")\n          throw new TypeError(\"The last argument must be of type Function\");\n        var z = this, q = function() {\n          return U.apply(z, arguments);\n        };\n        _.apply(this, j).then(\n          function(F) {\n            process.nextTick(q.bind(null, null, F));\n          },\n          function(F) {\n            process.nextTick(he.bind(null, F, q));\n          }\n        );\n      }\n      return Object.setPrototypeOf(A, Object.getPrototypeOf(_)), Object.defineProperties(\n        A,\n        t(_)\n      ), A;\n    }\n    e.callbackify = O;\n  })(Ei)), Ei;\n}\nvar Sa = {}, uf;\nfunction o3() {\n  return uf || (uf = 1, (function(e) {\n    (function(t) {\n      var n = {\n        not_string: /[^s]/,\n        number: /[diefg]/,\n        json: /[j]/,\n        not_json: /[^j]/,\n        text: /^[^\\x25]+/,\n        modulo: /^\\x25{2}/,\n        placeholder: /^\\x25(?:([1-9]\\d*)\\$|\\(([^\\)]+)\\))?(\\+)?(0|'[^$])?(-)?(\\d+)?(?:\\.(\\d+))?([b-gijosuxX])/,\n        key: /^([a-z_][a-z_\\d]*)/i,\n        key_access: /^\\.([a-z_][a-z_\\d]*)/i,\n        index_access: /^\\[(\\d+)\\]/,\n        sign: /^[\\+\\-]/\n      };\n      function r() {\n        var s = arguments[0], c = r.cache;\n        return c[s] && c.hasOwnProperty(s) || (c[s] = r.parse(s)), r.format.call(null, c[s], arguments);\n      }\n      r.format = function(s, c) {\n        var l = 1, f = s.length, d = \"\", u, b = [], h, w, E, m, g, T, y = !0, v = \"\";\n        for (h = 0; h < f; h++)\n          if (d = i(s[h]), d === \"string\")\n            b[b.length] = s[h];\n          else if (d === \"array\") {\n            if (E = s[h], E[2])\n              for (u = c[l], w = 0; w < E[2].length; w++) {\n                if (!u.hasOwnProperty(E[2][w]))\n                  throw new Error(r(\"[sprintf] property '%s' does not exist\", E[2][w]));\n                u = u[E[2][w]];\n              }\n            else E[1] ? u = c[E[1]] : u = c[l++];\n            if (i(u) == \"function\" && (u = u()), n.not_string.test(E[8]) && n.not_json.test(E[8]) && i(u) != \"number\" && isNaN(u))\n              throw new TypeError(r(\"[sprintf] expecting number but found %s\", i(u)));\n            switch (n.number.test(E[8]) && (y = u >= 0), E[8]) {\n              case \"b\":\n                u = u.toString(2);\n                break;\n              case \"c\":\n                u = String.fromCharCode(u);\n                break;\n              case \"d\":\n              case \"i\":\n                u = parseInt(u, 10);\n                break;\n              case \"j\":\n                u = JSON.stringify(u, null, E[6] ? parseInt(E[6]) : 0);\n                break;\n              case \"e\":\n                u = E[7] ? u.toExponential(E[7]) : u.toExponential();\n                break;\n              case \"f\":\n                u = E[7] ? parseFloat(u).toFixed(E[7]) : parseFloat(u);\n                break;\n              case \"g\":\n                u = E[7] ? parseFloat(u).toPrecision(E[7]) : parseFloat(u);\n                break;\n              case \"o\":\n                u = u.toString(8);\n                break;\n              case \"s\":\n                u = (u = String(u)) && E[7] ? u.substring(0, E[7]) : u;\n                break;\n              case \"u\":\n                u = u >>> 0;\n                break;\n              case \"x\":\n                u = u.toString(16);\n                break;\n              case \"X\":\n                u = u.toString(16).toUpperCase();\n                break;\n            }\n            n.json.test(E[8]) ? b[b.length] = u : (n.number.test(E[8]) && (!y || E[3]) ? (v = y ? \"+\" : \"-\", u = u.toString().replace(n.sign, \"\")) : v = \"\", g = E[4] ? E[4] === \"0\" ? \"0\" : E[4].charAt(1) : \" \", T = E[6] - (v + u).length, m = E[6] && T > 0 ? a(g, T) : \"\", b[b.length] = E[5] ? v + u + m : g === \"0\" ? v + m + u : m + v + u);\n          }\n        return b.join(\"\");\n      }, r.cache = {}, r.parse = function(s) {\n        for (var c = s, l = [], f = [], d = 0; c; ) {\n          if ((l = n.text.exec(c)) !== null)\n            f[f.length] = l[0];\n          else if ((l = n.modulo.exec(c)) !== null)\n            f[f.length] = \"%\";\n          else if ((l = n.placeholder.exec(c)) !== null) {\n            if (l[2]) {\n              d |= 1;\n              var u = [], b = l[2], h = [];\n              if ((h = n.key.exec(b)) !== null)\n                for (u[u.length] = h[1]; (b = b.substring(h[0].length)) !== \"\"; )\n                  if ((h = n.key_access.exec(b)) !== null)\n                    u[u.length] = h[1];\n                  else if ((h = n.index_access.exec(b)) !== null)\n                    u[u.length] = h[1];\n                  else\n                    throw new SyntaxError(\"[sprintf] failed to parse named argument key\");\n              else\n                throw new SyntaxError(\"[sprintf] failed to parse named argument key\");\n              l[2] = u;\n            } else\n              d |= 2;\n            if (d === 3)\n              throw new Error(\"[sprintf] mixing positional and named placeholders is not (yet) supported\");\n            f[f.length] = l;\n          } else\n            throw new SyntaxError(\"[sprintf] unexpected placeholder\");\n          c = c.substring(l[0].length);\n        }\n        return f;\n      };\n      var o = function(s, c, l) {\n        return l = (c || []).slice(0), l.splice(0, 0, s), r.apply(null, l);\n      };\n      function i(s) {\n        return Object.prototype.toString.call(s).slice(8, -1).toLowerCase();\n      }\n      function a(s, c) {\n        return Array(c + 1).join(s);\n      }\n      e.sprintf = r, e.vsprintf = o;\n    })();\n  })(Sa)), Sa;\n}\nvar Zr = { exports: {} }, ff;\nfunction i3() {\n  if (ff) return Zr.exports;\n  ff = 1;\n  var e = typeof Reflect == \"object\" ? Reflect : null, t = e && typeof e.apply == \"function\" ? e.apply : function(v, S, I) {\n    return Function.prototype.apply.call(v, S, I);\n  }, n;\n  e && typeof e.ownKeys == \"function\" ? n = e.ownKeys : Object.getOwnPropertySymbols ? n = function(v) {\n    return Object.getOwnPropertyNames(v).concat(Object.getOwnPropertySymbols(v));\n  } : n = function(v) {\n    return Object.getOwnPropertyNames(v);\n  };\n  function r(y) {\n    console && console.warn && console.warn(y);\n  }\n  var o = Number.isNaN || function(v) {\n    return v !== v;\n  };\n  function i() {\n    i.init.call(this);\n  }\n  Zr.exports = i, Zr.exports.once = m, i.EventEmitter = i, i.prototype._events = void 0, i.prototype._eventsCount = 0, i.prototype._maxListeners = void 0;\n  var a = 10;\n  function s(y) {\n    if (typeof y != \"function\")\n      throw new TypeError('The \"listener\" argument must be of type Function. Received type ' + typeof y);\n  }\n  Object.defineProperty(i, \"defaultMaxListeners\", {\n    enumerable: !0,\n    get: function() {\n      return a;\n    },\n    set: function(y) {\n      if (typeof y != \"number\" || y < 0 || o(y))\n        throw new RangeError('The value of \"defaultMaxListeners\" is out of range. It must be a non-negative number. Received ' + y + \".\");\n      a = y;\n    }\n  }), i.init = function() {\n    (this._events === void 0 || this._events === Object.getPrototypeOf(this)._events) && (this._events = /* @__PURE__ */ Object.create(null), this._eventsCount = 0), this._maxListeners = this._maxListeners || void 0;\n  }, i.prototype.setMaxListeners = function(v) {\n    if (typeof v != \"number\" || v < 0 || o(v))\n      throw new RangeError('The value of \"n\" is out of range. It must be a non-negative number. Received ' + v + \".\");\n    return this._maxListeners = v, this;\n  };\n  function c(y) {\n    return y._maxListeners === void 0 ? i.defaultMaxListeners : y._maxListeners;\n  }\n  i.prototype.getMaxListeners = function() {\n    return c(this);\n  }, i.prototype.emit = function(v) {\n    for (var S = [], I = 1; I < arguments.length; I++) S.push(arguments[I]);\n    var k = v === \"error\", M = this._events;\n    if (M !== void 0)\n      k = k && M.error === void 0;\n    else if (!k)\n      return !1;\n    if (k) {\n      var N;\n      if (S.length > 0 && (N = S[0]), N instanceof Error)\n        throw N;\n      var L = new Error(\"Unhandled error.\" + (N ? \" (\" + N.message + \")\" : \"\"));\n      throw L.context = N, L;\n    }\n    var V = M[v];\n    if (V === void 0)\n      return !1;\n    if (typeof V == \"function\")\n      t(V, this, S);\n    else\n      for (var ie = V.length, ce = h(V, ie), I = 0; I < ie; ++I)\n        t(ce[I], this, S);\n    return !0;\n  };\n  function l(y, v, S, I) {\n    var k, M, N;\n    if (s(S), M = y._events, M === void 0 ? (M = y._events = /* @__PURE__ */ Object.create(null), y._eventsCount = 0) : (M.newListener !== void 0 && (y.emit(\n      \"newListener\",\n      v,\n      S.listener ? S.listener : S\n    ), M = y._events), N = M[v]), N === void 0)\n      N = M[v] = S, ++y._eventsCount;\n    else if (typeof N == \"function\" ? N = M[v] = I ? [S, N] : [N, S] : I ? N.unshift(S) : N.push(S), k = c(y), k > 0 && N.length > k && !N.warned) {\n      N.warned = !0;\n      var L = new Error(\"Possible EventEmitter memory leak detected. \" + N.length + \" \" + String(v) + \" listeners added. Use emitter.setMaxListeners() to increase limit\");\n      L.name = \"MaxListenersExceededWarning\", L.emitter = y, L.type = v, L.count = N.length, r(L);\n    }\n    return y;\n  }\n  i.prototype.addListener = function(v, S) {\n    return l(this, v, S, !1);\n  }, i.prototype.on = i.prototype.addListener, i.prototype.prependListener = function(v, S) {\n    return l(this, v, S, !0);\n  };\n  function f() {\n    if (!this.fired)\n      return this.target.removeListener(this.type, this.wrapFn), this.fired = !0, arguments.length === 0 ? this.listener.call(this.target) : this.listener.apply(this.target, arguments);\n  }\n  function d(y, v, S) {\n    var I = { fired: !1, wrapFn: void 0, target: y, type: v, listener: S }, k = f.bind(I);\n    return k.listener = S, I.wrapFn = k, k;\n  }\n  i.prototype.once = function(v, S) {\n    return s(S), this.on(v, d(this, v, S)), this;\n  }, i.prototype.prependOnceListener = function(v, S) {\n    return s(S), this.prependListener(v, d(this, v, S)), this;\n  }, i.prototype.removeListener = function(v, S) {\n    var I, k, M, N, L;\n    if (s(S), k = this._events, k === void 0)\n      return this;\n    if (I = k[v], I === void 0)\n      return this;\n    if (I === S || I.listener === S)\n      --this._eventsCount === 0 ? this._events = /* @__PURE__ */ Object.create(null) : (delete k[v], k.removeListener && this.emit(\"removeListener\", v, I.listener || S));\n    else if (typeof I != \"function\") {\n      for (M = -1, N = I.length - 1; N >= 0; N--)\n        if (I[N] === S || I[N].listener === S) {\n          L = I[N].listener, M = N;\n          break;\n        }\n      if (M < 0)\n        return this;\n      M === 0 ? I.shift() : w(I, M), I.length === 1 && (k[v] = I[0]), k.removeListener !== void 0 && this.emit(\"removeListener\", v, L || S);\n    }\n    return this;\n  }, i.prototype.off = i.prototype.removeListener, i.prototype.removeAllListeners = function(v) {\n    var S, I, k;\n    if (I = this._events, I === void 0)\n      return this;\n    if (I.removeListener === void 0)\n      return arguments.length === 0 ? (this._events = /* @__PURE__ */ Object.create(null), this._eventsCount = 0) : I[v] !== void 0 && (--this._eventsCount === 0 ? this._events = /* @__PURE__ */ Object.create(null) : delete I[v]), this;\n    if (arguments.length === 0) {\n      var M = Object.keys(I), N;\n      for (k = 0; k < M.length; ++k)\n        N = M[k], N !== \"removeListener\" && this.removeAllListeners(N);\n      return this.removeAllListeners(\"removeListener\"), this._events = /* @__PURE__ */ Object.create(null), this._eventsCount = 0, this;\n    }\n    if (S = I[v], typeof S == \"function\")\n      this.removeListener(v, S);\n    else if (S !== void 0)\n      for (k = S.length - 1; k >= 0; k--)\n        this.removeListener(v, S[k]);\n    return this;\n  };\n  function u(y, v, S) {\n    var I = y._events;\n    if (I === void 0)\n      return [];\n    var k = I[v];\n    return k === void 0 ? [] : typeof k == \"function\" ? S ? [k.listener || k] : [k] : S ? E(k) : h(k, k.length);\n  }\n  i.prototype.listeners = function(v) {\n    return u(this, v, !0);\n  }, i.prototype.rawListeners = function(v) {\n    return u(this, v, !1);\n  }, i.listenerCount = function(y, v) {\n    return typeof y.listenerCount == \"function\" ? y.listenerCount(v) : b.call(y, v);\n  }, i.prototype.listenerCount = b;\n  function b(y) {\n    var v = this._events;\n    if (v !== void 0) {\n      var S = v[y];\n      if (typeof S == \"function\")\n        return 1;\n      if (S !== void 0)\n        return S.length;\n    }\n    return 0;\n  }\n  i.prototype.eventNames = function() {\n    return this._eventsCount > 0 ? n(this._events) : [];\n  };\n  function h(y, v) {\n    for (var S = new Array(v), I = 0; I < v; ++I)\n      S[I] = y[I];\n    return S;\n  }\n  function w(y, v) {\n    for (; v + 1 < y.length; v++)\n      y[v] = y[v + 1];\n    y.pop();\n  }\n  function E(y) {\n    for (var v = new Array(y.length), S = 0; S < v.length; ++S)\n      v[S] = y[S].listener || y[S];\n    return v;\n  }\n  function m(y, v) {\n    return new Promise(function(S, I) {\n      function k(N) {\n        y.removeListener(v, M), I(N);\n      }\n      function M() {\n        typeof y.removeListener == \"function\" && y.removeListener(\"error\", k), S([].slice.call(arguments));\n      }\n      T(y, v, M, { once: !0 }), v !== \"error\" && g(y, k, { once: !0 });\n    });\n  }\n  function g(y, v, S) {\n    typeof y.on == \"function\" && T(y, \"error\", v, S);\n  }\n  function T(y, v, S, I) {\n    if (typeof y.on == \"function\")\n      I.once ? y.once(v, S) : y.on(v, S);\n    else if (typeof y.addEventListener == \"function\")\n      y.addEventListener(v, function k(M) {\n        I.once && y.removeEventListener(v, k), S(M);\n      });\n    else\n      throw new TypeError('The \"emitter\" argument must be of type EventEmitter. Received type ' + typeof y);\n  }\n  return Zr.exports;\n}\nvar Ta, df;\nfunction a3() {\n  if (df) return Ta;\n  df = 1;\n  var e = [].indexOf;\n  return Ta = function(t, n) {\n    if (e) return t.indexOf(n);\n    for (var r = 0; r < t.length; ++r)\n      if (t[r] === n) return r;\n    return -1;\n  }, Ta;\n}\nvar Aa, pf;\nfunction s3() {\n  if (pf) return Aa;\n  pf = 1;\n  var e = Array.prototype, t = e.concat, n = e.slice, r = a3();\n  function o(i) {\n    var a = {}, s = t.apply(e, n.call(arguments, 1));\n    for (var c in i)\n      r(s, c) === -1 && (a[c] = i[c]);\n    return a;\n  }\n  return Aa = o, Aa;\n}\nvar Ia, hf;\nfunction O1() {\n  return hf || (hf = 1, Ia = {\n    __locale: \"en\",\n    days: [\"Sunday\", \"Monday\", \"Tuesday\", \"Wednesday\", \"Thursday\", \"Friday\", \"Saturday\"],\n    abbreviated_days: [\"Sun\", \"Mon\", \"Tue\", \"Wed\", \"Thu\", \"Fri\", \"Sat\"],\n    months: [\"January\", \"February\", \"March\", \"April\", \"May\", \"June\", \"July\", \"August\", \"September\", \"October\", \"November\", \"December\"],\n    abbreviated_months: [\"Jan\", \"Feb\", \"Mar\", \"Apr\", \"May\", \"Jun\", \"Jul\", \"Aug\", \"Sep\", \"Oct\", \"Nov\", \"Dec\"],\n    am: \"AM\",\n    pm: \"PM\"\n  }), Ia;\n}\nvar ja, mf;\nfunction c3() {\n  return mf || (mf = 1, ja = O1()), ja;\n}\nvar Oa, gf;\nfunction l3() {\n  if (gf) return Oa;\n  gf = 1;\n  var e = c3();\n  function t(a, s, c) {\n    var l = a.getTime();\n    return c = c || e, s.replace(/%([-_0]?.)/g, function(f, d) {\n      var u = null;\n      if (d.length == 2) {\n        switch (d[0]) {\n          case \"-\":\n            u = \"\";\n            break;\n          case \"_\":\n            u = \" \";\n            break;\n          case \"0\":\n            u = \"0\";\n            break;\n          default:\n            return f;\n        }\n        d = d[1];\n      }\n      switch (d) {\n        case \"A\":\n          return c.days[a.getDay()];\n        case \"a\":\n          return c.abbreviated_days[a.getDay()];\n        case \"B\":\n          return c.months[a.getMonth()];\n        case \"b\":\n          return c.abbreviated_months[a.getMonth()];\n        case \"C\":\n          return n(Math.floor(a.getFullYear() / 100), u);\n        case \"D\":\n          return t(a, \"%m/%d/%y\");\n        case \"d\":\n          return n(a.getDate(), u);\n        case \"e\":\n          return a.getDate();\n        case \"F\":\n          return t(a, \"%Y-%m-%d\");\n        case \"H\":\n          return n(a.getHours(), u);\n        case \"h\":\n          return c.abbreviated_months[a.getMonth()];\n        case \"I\":\n          return n(r(a), u);\n        case \"j\":\n          return n(Math.ceil((a.getTime() - new Date(a.getFullYear(), 0, 1).getTime()) / (1e3 * 60 * 60 * 24)), 3);\n        case \"k\":\n          return n(a.getHours(), u === null ? \" \" : u);\n        case \"L\":\n          return n(Math.floor(l % 1e3), 3);\n        case \"l\":\n          return n(r(a), u === null ? \" \" : u);\n        case \"M\":\n          return n(a.getMinutes(), u);\n        case \"m\":\n          return n(a.getMonth() + 1, u);\n        case \"n\":\n          return `\n`;\n        case \"o\":\n          return String(a.getDate()) + o(a.getDate());\n        case \"P\":\n          return a.getHours() < 12 ? c.am.toLowerCase() : c.pm.toLowerCase();\n        case \"p\":\n          return a.getHours() < 12 ? c.am.toUpperCase() : c.pm.toUpperCase();\n        case \"R\":\n          return t(a, \"%H:%M\");\n        case \"r\":\n          return t(a, \"%I:%M:%S %p\");\n        case \"S\":\n          return n(a.getSeconds(), u);\n        case \"s\":\n          return Math.floor(l / 1e3);\n        case \"T\":\n          return t(a, \"%H:%M:%S\");\n        case \"t\":\n          return \"\t\";\n        case \"U\":\n          return n(i(a, \"sunday\"), u);\n        case \"u\":\n          return a.getDay() === 0 ? 7 : a.getDay();\n        case \"v\":\n          return t(a, \"%e-%b-%Y\");\n        case \"W\":\n          return n(i(a, \"monday\"), u);\n        case \"w\":\n          return a.getDay();\n        case \"Y\":\n          return a.getFullYear();\n        case \"y\":\n          var b = String(a.getFullYear());\n          return b.slice(b.length - 2);\n        case \"Z\":\n          var h = a.toString().match(/\\((\\w+)\\)/);\n          return h && h[1] || \"\";\n        case \"z\":\n          var w = a.getTimezoneOffset();\n          return (w > 0 ? \"-\" : \"+\") + n(Math.round(Math.abs(w / 60)), 2) + \":\" + n(w % 60, 2);\n        default:\n          return d;\n      }\n    });\n  }\n  function n(a, s, c) {\n    typeof s == \"number\" && (c = s, s = \"0\"), s === null && (s = \"0\"), c = c || 2;\n    var l = String(a);\n    if (s)\n      for (; l.length < c; )\n        l = s + l;\n    return l;\n  }\n  function r(a) {\n    var s = a.getHours();\n    return s === 0 ? s = 12 : s > 12 && (s -= 12), s;\n  }\n  function o(a) {\n    var s = a % 10, c = a % 100;\n    if (c >= 11 && c <= 13 || s === 0 || s >= 4)\n      return \"th\";\n    switch (s) {\n      case 1:\n        return \"st\";\n      case 2:\n        return \"nd\";\n      case 3:\n        return \"rd\";\n    }\n  }\n  function i(a, s) {\n    s = s || \"sunday\";\n    var c = a.getDay();\n    s == \"monday\" && (c === 0 ? c = 6 : c--);\n    var l = new Date(a.getFullYear(), 0, 1), f = (a - l) / 864e5, d = (f + 7 - c) / 7;\n    return Math.floor(d);\n  }\n  return Oa = t, Oa;\n}\nvar Pa, yf;\nfunction u3() {\n  return yf || (yf = 1, Pa = function(e, t) {\n    var n;\n    return t === 0 && \"zero\" in e && (n = \"zero\"), n = n || (t === 1 ? \"one\" : \"other\"), e[n];\n  }), Pa;\n}\nvar ka, vf;\nfunction f3() {\n  return vf || (vf = 1, ka = {\n    counterpart: {\n      names: O1(),\n      pluralize: u3(),\n      formats: {\n        date: {\n          default: \"%a, %e %b %Y\",\n          long: \"%A, %B %o, %Y\",\n          short: \"%b %e\"\n        },\n        time: {\n          default: \"%H:%M\",\n          long: \"%H:%M:%S %z\",\n          short: \"%H:%M\"\n        },\n        datetime: {\n          default: \"%a, %e %b %Y %H:%M\",\n          long: \"%A, %B %o, %Y %H:%M:%S %z\",\n          short: \"%e %b %H:%M\"\n        }\n      }\n    }\n  }), ka;\n}\nvar Ra, bf;\nfunction d3() {\n  if (bf) return Ra;\n  bf = 1;\n  var e = w7(), t = lf().isArray, n = lf().isDate, r = o3().sprintf, o = i3(), i = s3(), a = l3(), s = \"counterpart\";\n  function c(m) {\n    return typeof m == \"string\" || Object.prototype.toString.call(m) === \"[object String]\";\n  }\n  function l(m) {\n    return typeof m == \"function\" || Object.prototype.toString.call(m) === \"[object Function]\";\n  }\n  function f(m) {\n    return m === null ? !1 : Object.prototype.toString.call(m) === \"[object Object]\";\n  }\n  function d(m) {\n    return c(m) && m[0] === \":\";\n  }\n  function u(m, g) {\n    return Object.prototype.hasOwnProperty.call(m, g);\n  }\n  function b(m, g) {\n    return g.reduce(function(T, y) {\n      return f(T) && u(T, y) ? T[y] : null;\n    }, m);\n  }\n  function h() {\n    o.EventEmitter.apply(this), this._registry = {\n      locale: \"en\",\n      interpolate: !0,\n      fallbackLocales: [],\n      scope: null,\n      translations: {},\n      interpolations: {},\n      normalizedKeys: {},\n      separator: \".\",\n      keepTrailingDot: !1,\n      keyTransformer: function(m) {\n        return m;\n      },\n      generateMissingEntry: function(m) {\n        return \"missing translation: \" + m;\n      }\n    }, this.registerTranslations(\"en\", f3()), this.setMaxListeners(0);\n  }\n  h.prototype = o.EventEmitter.prototype, h.prototype.constructor = o.EventEmitter, h.prototype.getLocale = function() {\n    return this._registry.locale;\n  }, h.prototype.setLocale = function(m) {\n    var g = this._registry.locale;\n    return g != m && (this._registry.locale = m, this.emit(\"localechange\", m, g)), g;\n  }, h.prototype.getFallbackLocale = function() {\n    return this._registry.fallbackLocales;\n  }, h.prototype.setFallbackLocale = function(m) {\n    var g = this._registry.fallbackLocales;\n    return this._registry.fallbackLocales = [].concat(m || []), g;\n  }, h.prototype.getAvailableLocales = function() {\n    return this._registry.availableLocales || Object.keys(this._registry.translations);\n  }, h.prototype.setAvailableLocales = function(m) {\n    var g = this.getAvailableLocales();\n    return this._registry.availableLocales = m, g;\n  }, h.prototype.getSeparator = function() {\n    return this._registry.separator;\n  }, h.prototype.setSeparator = function(m) {\n    var g = this._registry.separator;\n    return this._registry.separator = m, g;\n  }, h.prototype.setInterpolate = function(m) {\n    var g = this._registry.interpolate;\n    return this._registry.interpolate = m, g;\n  }, h.prototype.getInterpolate = function() {\n    return this._registry.interpolate;\n  }, h.prototype.setKeyTransformer = function(m) {\n    var g = this._registry.keyTransformer;\n    return this._registry.keyTransformer = m, g;\n  }, h.prototype.getKeyTransformer = function() {\n    return this._registry.keyTransformer;\n  }, h.prototype.setMissingEntryGenerator = function(m) {\n    var g = this._registry.generateMissingEntry;\n    return this._registry.generateMissingEntry = m, g;\n  }, h.prototype.getMissingEntryGenerator = function() {\n    return this._registry.generateMissingEntry;\n  }, h.prototype.registerTranslations = function(m, g) {\n    var T = {};\n    return T[m] = g, e(!0, this._registry.translations, T), T;\n  }, h.prototype.registerInterpolations = function(m) {\n    return e(!0, this._registry.interpolations, m);\n  }, h.prototype.onLocaleChange = h.prototype.addLocaleChangeListener = function(m) {\n    this.addListener(\"localechange\", m);\n  }, h.prototype.offLocaleChange = h.prototype.removeLocaleChangeListener = function(m) {\n    this.removeListener(\"localechange\", m);\n  }, h.prototype.onTranslationNotFound = h.prototype.addTranslationNotFoundListener = function(m) {\n    this.addListener(\"translationnotfound\", m);\n  }, h.prototype.offTranslationNotFound = h.prototype.removeTranslationNotFoundListener = function(m) {\n    this.removeListener(\"translationnotfound\", m);\n  }, h.prototype.onError = h.prototype.addErrorListener = function(m) {\n    this.addListener(\"error\", m);\n  }, h.prototype.offError = h.prototype.removeErrorListener = function(m) {\n    this.removeListener(\"error\", m);\n  }, h.prototype.translate = function(m, g) {\n    if (!t(m) && !c(m) || !m.length)\n      throw new Error(\"invalid argument: key\");\n    d(m) && (m = m.substr(1)), m = this._registry.keyTransformer(m, g), g = e(!0, {}, g);\n    var T = g.locale || this._registry.locale;\n    delete g.locale;\n    var y = g.scope || this._registry.scope;\n    delete g.scope;\n    var v = g.separator || this._registry.separator;\n    delete g.separator;\n    var S = [].concat(g.fallbackLocale || this._registry.fallbackLocales);\n    delete g.fallbackLocale;\n    var I = this._normalizeKeys(T, y, m, v), k = b(this._registry.translations, I);\n    if (k === null && (this.emit(\"translationnotfound\", T, m, g.fallback, y), g.fallback && (k = this._fallback(T, y, m, g.fallback, g))), k === null && S.length > 0 && S.indexOf(T) === -1)\n      for (var M = 0, N = S.length; M < N; M++) {\n        var L = S[M], V = this._normalizeKeys(L, y, m, v);\n        if (k = b(this._registry.translations, V), k) {\n          T = L;\n          break;\n        }\n      }\n    return k === null && (k = this._registry.generateMissingEntry(I.join(v))), k = this._pluralize(T, k, g.count), this._registry.interpolate !== !1 && g.interpolate !== !1 && (k = this._interpolate(k, g)), k;\n  }, h.prototype.localize = function(m, g) {\n    if (!n(m))\n      throw new Error(\"invalid argument: object must be a date\");\n    g = e(!0, {}, g);\n    var T = g.locale || this._registry.locale, y = g.scope || s, v = g.type || \"datetime\", S = g.format || \"default\";\n    return g = { locale: T, scope: y, interpolate: !1 }, S = this.translate([\"formats\", v, S], e(!0, {}, g)), a(m, S, this.translate(\"names\", g));\n  }, h.prototype._pluralize = function(m, g, T) {\n    if (typeof g != \"object\" || g === null || typeof T != \"number\")\n      return g;\n    var y = this.translate(\"pluralize\", { locale: m, scope: s });\n    return Object.prototype.toString.call(y) !== \"[object Function]\" ? y : y(g, T);\n  }, h.prototype.withLocale = function(m, g, T) {\n    var y = this._registry.locale;\n    this._registry.locale = m;\n    var v = g.call(T);\n    return this._registry.locale = y, v;\n  }, h.prototype.withScope = function(m, g, T) {\n    var y = this._registry.scope;\n    this._registry.scope = m;\n    var v = g.call(T);\n    return this._registry.scope = y, v;\n  }, h.prototype.withSeparator = function(m, g, T) {\n    var y = this.setSeparator(m), v = g.call(T);\n    return this.setSeparator(y), v;\n  }, h.prototype._normalizeKeys = function(m, g, T, y) {\n    var v = [];\n    return v = v.concat(this._normalizeKey(m, y)), v = v.concat(this._normalizeKey(g, y)), v = v.concat(this._normalizeKey(T, y)), v;\n  }, h.prototype._normalizeKey = function(m, g) {\n    return this._registry.normalizedKeys[g] = this._registry.normalizedKeys[g] || {}, this._registry.normalizedKeys[g][m] = this._registry.normalizedKeys[g][m] || (function(T) {\n      if (t(T)) {\n        var y = T.map((function(I) {\n          return this._normalizeKey(I, g);\n        }).bind(this));\n        return [].concat.apply([], y);\n      } else {\n        if (typeof T > \"u\" || T === null)\n          return [];\n        for (var v = T.split(g), S = v.length - 1; S >= 0; S--)\n          v[S] === \"\" && (v.splice(S, 1), this._registry.keepTrailingDot === !0 && S == v.length && (v[v.length - 1] += \"\" + g));\n        return v;\n      }\n    }).bind(this)(m), this._registry.normalizedKeys[g][m];\n  }, h.prototype._interpolate = function(m, g) {\n    if (typeof m != \"string\")\n      return m;\n    try {\n      return r(m, e({}, this._registry.interpolations, g));\n    } catch (T) {\n      if (this.listenerCount(\"error\") > 0)\n        this.emit(\"error\", T, m, g);\n      else\n        throw T;\n      return null;\n    }\n  }, h.prototype._resolve = function(m, g, T, y, v) {\n    if (v = v || {}, v.resolve === !1)\n      return y;\n    var S;\n    if (d(y))\n      S = this.translate(y, e({}, v, { locale: m, scope: g }));\n    else if (l(y)) {\n      var I;\n      v.object ? (I = v.object, delete v.object) : I = T, S = this._resolve(m, g, T, y(I, v));\n    } else\n      S = y;\n    return /^missing translation:/.test(S) ? null : S;\n  }, h.prototype._fallback = function(m, g, T, y, v) {\n    if (v = i(v, \"fallback\"), t(y)) {\n      for (var S = 0, I = y.length; S < I; S++) {\n        var k = this._resolve(m, g, T, y[S], v);\n        if (k)\n          return k;\n      }\n      return null;\n    } else\n      return this._resolve(m, g, T, y, v);\n  };\n  var w = new h();\n  function E() {\n    return w.translate.apply(w, arguments);\n  }\n  return e(E, w, {\n    Instance: h,\n    Translator: h\n  }), Ra = E, Ra;\n}\nvar p3 = d3();\nconst We = /* @__PURE__ */ Nf(p3), P1 = \"i18n/\";\nWe.setSeparator(_7);\nconst k1 = \"en\";\nWe.setFallbackLocale(k1);\nfunction h3(e, t) {\n  We.registerTranslations(e, t);\n}\nfunction x8(e) {\n  We.setMissingEntryGenerator(e);\n}\nfunction m3() {\n  return We.getLocale();\n}\nfunction z8(e) {\n  return We.setLocale(e);\n}\nfunction B8(e) {\n  return e;\n}\nfunction _f(e) {\n  return typeof e == \"string\" && !e.startsWith(\"missing translation:\");\n}\nconst g3 = (e, t) => {\n  const n = We.translate(e, { ...t, fallbackLocale: We.getLocale() });\n  if (_f(n))\n    return { translated: n };\n  const r = We.translate(e, { ...t, locale: k1 });\n  return _f(r) ? { translated: r, isFallback: !0 } : { translated: e, isFallback: !0 };\n};\nfunction Bc(e, t) {\n  const n = { ...t, interpolate: !1 };\n  return n && typeof n == \"object\" && Object.keys(n).forEach((r) => {\n    n[r] === void 0 && (console.warn(\"safeCounterpartTranslate called with undefined interpolation name: \" + r), n[r] = \"undefined\"), n[r] === null && (console.warn(\"safeCounterpartTranslate called with null interpolation name: \" + r), n[r] = \"null\");\n  }), g3(e, n);\n}\nconst R1 = (e, t) => e;\nfunction C(e, t, n) {\n  const { translated: r } = Bc(e, t), o = M1(r, t, n);\n  return R1(o);\n}\nfunction F8(e) {\n  return Bc(e, {}).translated;\n}\nfunction D8(e, t, n) {\n  const { translated: r, isFallback: o } = Bc(e, t), i = M1(r, t, n);\n  return R1(o ? /* @__PURE__ */ p.createElement(\"span\", { lang: \"en\" }, i) : i);\n}\nfunction q8(e) {\n  return e.replace(/%\\(([^)]*)\\)/g, \"% ($1)\");\n}\nfunction M1(e, t, n) {\n  let r = e;\n  if (t !== void 0) {\n    const o = {};\n    for (const i in t)\n      o[`%\\\\(${i}\\\\)s`] = t[i];\n    r = wf(r, o);\n  }\n  if (n !== void 0) {\n    const o = {};\n    for (const i in n)\n      o[`(<${i}>(.*?)<\\\\/${i}>|<${i}>|<${i}\\\\s*\\\\/>)`] = n[i];\n    r = wf(r, o);\n  }\n  return r;\n}\nfunction wf(e, t) {\n  const n = [e];\n  let r = !1;\n  for (const o in t) {\n    const i = new RegExp(o, \"g\");\n    let a = !1;\n    for (let s = 0; s < n.length; s++) {\n      const c = n[s];\n      if (typeof c != \"string\")\n        continue;\n      let l = i.exec(c);\n      if (!l) continue;\n      a = !0;\n      const f = c.slice(0, l.index), d = [];\n      let u;\n      for (; l; ) {\n        u = l;\n        const b = l.slice(2);\n        let h;\n        t[o] instanceof Function ? h = t[o](...b) : h = t[o], typeof h == \"object\" && (r = !0), (typeof h != \"string\" || h !== \"\") && d.push(h), l = i.exec(c);\n        let w;\n        if (l) {\n          const E = u.index + u[0].length;\n          w = c.slice(E, l.index);\n        } else\n          w = c.slice(u.index + u[0].length);\n        w && d.push(w);\n      }\n      n.splice(s, 1, ...d), f !== \"\" && n.splice(s, 0, f);\n    }\n    a || // The current regexp did not match anything in the input. Missing\n    // matches is entirely possible because you might choose to show some\n    // variables only in the case of e.g. plurals. It's still a bit\n    // suspicious, and could be due to an error, so log it. However, not\n    // showing count is so common that it's not worth logging. And other\n    // commonly unused variables here, if there are any.\n    o !== \"%\\\\(count\\\\)s\" && // Ignore the `locale` option which can be used to override the locale\n    // in counterpart\n    o !== \"%\\\\(locale\\\\)s\" && console.log(`Could not find ${i} in ${e}`);\n  }\n  return r ? p.createElement(\"span\", null, ...n) : n.join(\"\");\n}\nasync function L8(e) {\n  const t = await v3(), n = e in t ? e : \"en\", r = await y3(P1 + t[n]);\n  We.registerTranslations(n, r), We.setLocale(n);\n}\nasync function y3(e) {\n  console.log(\"Loading language from\", e);\n  const t = await fetch(e, { method: \"GET\" });\n  if (!t.ok)\n    throw new Error(`Failed to load ${e}, got ${t.status}`);\n  return t.json();\n}\nasync function v3() {\n  const e = P1 + \"languages.json\", t = await fetch(e, { method: \"GET\" });\n  if (!t.ok)\n    throw new Error(`Failed to load ${e}, got ${t.status}`);\n  return t.json();\n}\nfunction rr({\n  type: e,\n  children: t,\n  avatar: n,\n  className: r,\n  actions: o,\n  onClose: i,\n  ...a\n}) {\n  const s = pe(Yr.banner, r), c = st(() => {\n    switch (e) {\n      case \"critical\":\n        return /* @__PURE__ */ p.createElement(g1, { fontSize: 24 });\n      case \"info\":\n        return /* @__PURE__ */ p.createElement(ou, { fontSize: 24 });\n      case \"success\":\n        return /* @__PURE__ */ p.createElement(h7, { fontSize: 24 });\n      default:\n        return /* @__PURE__ */ p.createElement(ou, { fontSize: 24 });\n    }\n  }, [e]);\n  return /* @__PURE__ */ p.createElement(\"div\", { ...a, className: s, \"data-type\": e }, /* @__PURE__ */ p.createElement(\"div\", { className: Yr.icon }, n ?? c), /* @__PURE__ */ p.createElement(\"div\", { className: Yr.content }, t), /* @__PURE__ */ p.createElement(\"div\", { className: Yr.actions }, o, i && /* @__PURE__ */ p.createElement(Fe, { kind: \"secondary\", size: \"sm\", onClick: i }, C(\"action|dismiss\"))));\n}\nconst b3 = /* @__PURE__ */ JSON.parse(`[{\"number\":0,\"emoji\":\"🐶\",\"description\":\"Dog\",\"unicode\":\"U+1F436\",\"translated_descriptions\":{\"ar\":\"كلب\",\"bg\":\"Куче\",\"ca\":\"Gos\",\"cs\":\"Pes\",\"de\":\"Hund\",\"eo\":\"Hundo\",\"es\":\"Perro\",\"et\":\"Koer\",\"fa\":\"سگ\",\"fi\":\"Koira\",\"fr\":\"Chien\",\"hr\":\"pas\",\"hu\":\"Kutya\",\"id\":\"Anjing\",\"it\":\"Cane\",\"ja\":\"犬\",\"nb_NO\":\"Hund\",\"nl\":\"Hond\",\"pt\":\"Cão\",\"pt_BR\":\"Cachorro\",\"ru\":\"Собака\",\"si\":\"බල්ලා\",\"sk\":\"Pes\",\"sq\":\"Qen\",\"sr\":\"пас\",\"sv\":\"Hund\",\"szl\":null,\"tzm\":\"Aydi\",\"uk\":\"Пес\",\"vi\":\"Chó\",\"zh_Hans\":\"狗\",\"zh_Hant\":\"狗\"}},{\"number\":1,\"emoji\":\"🐱\",\"description\":\"Cat\",\"unicode\":\"U+1F431\",\"translated_descriptions\":{\"ar\":\"هِرَّة\",\"bg\":\"Котка\",\"ca\":\"Gat\",\"cs\":\"Kočka\",\"de\":\"Katze\",\"eo\":\"Kato\",\"es\":\"Gato\",\"et\":\"Kass\",\"fa\":\"گربه\",\"fi\":\"Kissa\",\"fr\":\"Chat\",\"hr\":\"mačka\",\"hu\":\"Macska\",\"id\":\"Kucing\",\"it\":\"Gatto\",\"ja\":\"猫\",\"nb_NO\":\"Katt\",\"nl\":\"Kat\",\"pt\":\"Gato\",\"pt_BR\":\"Gato\",\"ru\":\"Кошка\",\"si\":\"පූසා\",\"sk\":\"Mačka\",\"sq\":\"Mace\",\"sr\":\"мачка\",\"sv\":\"Katt\",\"szl\":null,\"tzm\":\"Amuc\",\"uk\":\"Кіт\",\"vi\":\"Mèo\",\"zh_Hans\":\"猫\",\"zh_Hant\":\"貓\"}},{\"number\":2,\"emoji\":\"🦁\",\"description\":\"Lion\",\"unicode\":\"U+1F981\",\"translated_descriptions\":{\"ar\":\"أَسَد\",\"bg\":\"Лъв\",\"ca\":\"Lleó\",\"cs\":\"Lev\",\"de\":\"Löwe\",\"eo\":\"Leono\",\"es\":\"León\",\"et\":\"Lõvi\",\"fa\":\"شیر\",\"fi\":\"Leijona\",\"fr\":\"Lion\",\"hr\":\"lav\",\"hu\":\"Oroszlán\",\"id\":\"Singa\",\"it\":\"Leone\",\"ja\":\"ライオン\",\"nb_NO\":\"Løve\",\"nl\":\"Leeuw\",\"pt\":\"Leão\",\"pt_BR\":\"Leão\",\"ru\":\"Лев\",\"si\":\"සිංහයා\",\"sk\":\"Lev\",\"sq\":\"Luan\",\"sr\":\"лав\",\"sv\":\"Lejon\",\"szl\":null,\"tzm\":\"Izem\",\"uk\":\"Лев\",\"vi\":\"Sư tử\",\"zh_Hans\":\"狮子\",\"zh_Hant\":\"獅子\"}},{\"number\":3,\"emoji\":\"🐎\",\"description\":\"Horse\",\"unicode\":\"U+1F40E\",\"translated_descriptions\":{\"ar\":\"حِصَان\",\"bg\":\"Кон\",\"ca\":\"Cavall\",\"cs\":\"Kůň\",\"de\":\"Pferd\",\"eo\":\"Ĉevalo\",\"es\":\"Caballo\",\"et\":\"Hobune\",\"fa\":\"اسب\",\"fi\":\"Hevonen\",\"fr\":\"Cheval\",\"hr\":\"konj\",\"hu\":\"Ló\",\"id\":\"Kuda\",\"it\":\"Cavallo\",\"ja\":\"馬\",\"nb_NO\":\"Hest\",\"nl\":\"Paard\",\"pt\":\"Cavalo\",\"pt_BR\":\"Cavalo\",\"ru\":\"Лошадь\",\"si\":\"අශ්වයා\",\"sk\":\"Kôň\",\"sq\":\"Kalë\",\"sr\":\"коњ\",\"sv\":\"Häst\",\"szl\":null,\"tzm\":\"Ayyis\",\"uk\":\"Кінь\",\"vi\":\"Ngựa\",\"zh_Hans\":\"马\",\"zh_Hant\":\"馬\"}},{\"number\":4,\"emoji\":\"🦄\",\"description\":\"Unicorn\",\"unicode\":\"U+1F984\",\"translated_descriptions\":{\"ar\":\"حصان وحيد القرن\",\"bg\":\"Еднорог\",\"ca\":\"Unicorn\",\"cs\":\"Jednorožec\",\"de\":\"Einhorn\",\"eo\":\"Unukorno\",\"es\":\"Unicornio\",\"et\":\"Ükssarvik\",\"fa\":\"تک شاخ\",\"fi\":\"Yksisarvinen\",\"fr\":\"Licorne\",\"hr\":\"jednorog\",\"hu\":\"Egyszarvú\",\"id\":\"Unicorn\",\"it\":\"Unicorno\",\"ja\":\"ユニコーン\",\"nb_NO\":\"Enhjørning\",\"nl\":\"Eenhoorn\",\"pt\":\"Unicórnio\",\"pt_BR\":\"Unicórnio\",\"ru\":\"Единорог\",\"si\":null,\"sk\":\"Jednorožec\",\"sq\":\"Njëbrirësh\",\"sr\":\"једнорог\",\"sv\":\"Enhörning\",\"szl\":null,\"tzm\":null,\"uk\":\"Єдиноріг\",\"vi\":\"Kỳ lân\",\"zh_Hans\":\"独角兽\",\"zh_Hant\":\"獨角獸\"}},{\"number\":5,\"emoji\":\"🐷\",\"description\":\"Pig\",\"unicode\":\"U+1F437\",\"translated_descriptions\":{\"ar\":\"خِنزِير\",\"bg\":\"Прасе\",\"ca\":\"Porc\",\"cs\":\"Prase\",\"de\":\"Schwein\",\"eo\":\"Porko\",\"es\":\"Cerdo\",\"et\":\"Siga\",\"fa\":\"خوک\",\"fi\":\"Sika\",\"fr\":\"Cochon\",\"hr\":\"svinja\",\"hu\":\"Malac\",\"id\":\"Babi\",\"it\":\"Maiale\",\"ja\":\"ブタ\",\"nb_NO\":\"Gris\",\"nl\":\"Varken\",\"pt\":\"Porco\",\"pt_BR\":\"Porco\",\"ru\":\"Свинья\",\"si\":null,\"sk\":\"Prasa\",\"sq\":\"Derr\",\"sr\":\"прасе\",\"sv\":\"Gris\",\"szl\":null,\"tzm\":\"Ilef\",\"uk\":\"Свиня\",\"vi\":\"Heo\",\"zh_Hans\":\"猪\",\"zh_Hant\":\"豬\"}},{\"number\":6,\"emoji\":\"🐘\",\"description\":\"Elephant\",\"unicode\":\"U+1F418\",\"translated_descriptions\":{\"ar\":\"فِيل\",\"bg\":\"Слон\",\"ca\":\"Elefant\",\"cs\":\"Slon\",\"de\":\"Elefant\",\"eo\":\"Elefanto\",\"es\":\"Elefante\",\"et\":\"Elevant\",\"fa\":\"فیل\",\"fi\":\"Norsu\",\"fr\":\"Éléphant\",\"hr\":\"slon\",\"hu\":\"Elefánt\",\"id\":\"Gajah\",\"it\":\"Elefante\",\"ja\":\"ゾウ\",\"nb_NO\":\"Elefant\",\"nl\":\"Olifant\",\"pt\":\"Elefante\",\"pt_BR\":\"Elefante\",\"ru\":\"Слон\",\"si\":null,\"sk\":\"Slon\",\"sq\":\"Elefant\",\"sr\":\"слон\",\"sv\":\"Elefant\",\"szl\":null,\"tzm\":\"Ilu\",\"uk\":\"Слон\",\"vi\":\"Voi\",\"zh_Hans\":\"大象\",\"zh_Hant\":\"大象\"}},{\"number\":7,\"emoji\":\"🐰\",\"description\":\"Rabbit\",\"unicode\":\"U+1F430\",\"translated_descriptions\":{\"ar\":\"أَرنَب\",\"bg\":\"Заек\",\"ca\":\"Conill\",\"cs\":\"Králík\",\"de\":\"Hase\",\"eo\":\"Kuniklo\",\"es\":\"Conejo\",\"et\":\"Jänes\",\"fa\":\"خرگوش\",\"fi\":\"Kani\",\"fr\":\"Lapin\",\"hr\":\"zec\",\"hu\":\"Nyúl\",\"id\":\"Kelinci\",\"it\":\"Coniglio\",\"ja\":\"うさぎ\",\"nb_NO\":\"Kanin\",\"nl\":\"Konijn\",\"pt\":\"Coelho\",\"pt_BR\":\"Coelho\",\"ru\":\"Кролик\",\"si\":null,\"sk\":\"Zajac\",\"sq\":\"Lepur\",\"sr\":\"зец\",\"sv\":\"Kanin\",\"szl\":null,\"tzm\":\"Agnin\",\"uk\":\"Кріль\",\"vi\":\"Thỏ\",\"zh_Hans\":\"兔子\",\"zh_Hant\":\"兔子\"}},{\"number\":8,\"emoji\":\"🐼\",\"description\":\"Panda\",\"unicode\":\"U+1F43C\",\"translated_descriptions\":{\"ar\":\"باندَا\",\"bg\":\"Панда\",\"ca\":\"Panda\",\"cs\":\"Panda\",\"de\":\"Panda\",\"eo\":\"Pando\",\"es\":\"Panda\",\"et\":\"Panda\",\"fa\":\"پاندا\",\"fi\":\"Panda\",\"fr\":\"Panda\",\"hr\":\"panda\",\"hu\":\"Panda\",\"id\":\"Panda\",\"it\":\"Panda\",\"ja\":\"パンダ\",\"nb_NO\":\"Panda\",\"nl\":\"Panda\",\"pt\":\"Panda\",\"pt_BR\":\"Panda\",\"ru\":\"Панда\",\"si\":null,\"sk\":\"Panda\",\"sq\":\"Panda\",\"sr\":\"панда\",\"sv\":\"Panda\",\"szl\":null,\"tzm\":null,\"uk\":\"Панда\",\"vi\":\"Gấu trúc\",\"zh_Hans\":\"熊猫\",\"zh_Hant\":\"熊貓\"}},{\"number\":9,\"emoji\":\"🐓\",\"description\":\"Rooster\",\"unicode\":\"U+1F413\",\"translated_descriptions\":{\"ar\":\"دِيك\",\"bg\":\"Петел\",\"ca\":\"Gall\",\"cs\":\"Kohout\",\"de\":\"Hahn\",\"eo\":\"Virkoko\",\"es\":\"Gallo\",\"et\":\"Kukk\",\"fa\":\"خروس\",\"fi\":\"Kukko\",\"fr\":\"Coq\",\"hr\":\"kokot\",\"hu\":\"Kakas\",\"id\":\"Ayam\",\"it\":\"Gallo\",\"ja\":\"ニワトリ\",\"nb_NO\":\"Hane\",\"nl\":\"Haan\",\"pt\":\"Galo\",\"pt_BR\":\"Galo\",\"ru\":\"Петух\",\"si\":null,\"sk\":\"Kohút\",\"sq\":\"Këndes\",\"sr\":\"петао\",\"sv\":\"Tupp\",\"szl\":null,\"tzm\":\"Ayaẓiḍ\",\"uk\":\"Когут\",\"vi\":\"Gà trống\",\"zh_Hans\":\"公鸡\",\"zh_Hant\":\"公雞\"}},{\"number\":10,\"emoji\":\"🐧\",\"description\":\"Penguin\",\"unicode\":\"U+1F427\",\"translated_descriptions\":{\"ar\":\"بطريق\",\"bg\":\"Пингвин\",\"ca\":\"Pingüí\",\"cs\":\"Tučňák\",\"de\":\"Pinguin\",\"eo\":\"Pingveno\",\"es\":\"Pingüino\",\"et\":\"Pingviin\",\"fa\":\"پنگوئن\",\"fi\":\"Pingviini\",\"fr\":\"Manchot\",\"hr\":\"pingvin\",\"hu\":\"Pingvin\",\"id\":\"Penguin\",\"it\":\"Pinguino\",\"ja\":\"ペンギン\",\"nb_NO\":\"Pingvin\",\"nl\":\"Pinguïn\",\"pt\":\"Pinguim\",\"pt_BR\":\"Pinguim\",\"ru\":\"Пингвин\",\"si\":null,\"sk\":\"Tučniak\",\"sq\":\"Pinguin\",\"sr\":\"пингвин\",\"sv\":\"Pingvin\",\"szl\":null,\"tzm\":null,\"uk\":\"Пінгвін\",\"vi\":\"Chim cánh cụt\",\"zh_Hans\":\"企鹅\",\"zh_Hant\":\"企鵝\"}},{\"number\":11,\"emoji\":\"🐢\",\"description\":\"Turtle\",\"unicode\":\"U+1F422\",\"translated_descriptions\":{\"ar\":\"سُلحفاة\",\"bg\":\"Костенурка\",\"ca\":\"Tortuga\",\"cs\":\"Želva\",\"de\":\"Schildkröte\",\"eo\":\"Testudo\",\"es\":\"Tortuga\",\"et\":\"Kilpkonn\",\"fa\":\"لاک‌پشت\",\"fi\":\"Kilpikonna\",\"fr\":\"Tortue\",\"hr\":\"kornjača\",\"hu\":\"Teknős\",\"id\":\"Kura-Kura\",\"it\":\"Tartaruga\",\"ja\":\"亀\",\"nb_NO\":\"Skilpadde\",\"nl\":\"Schildpad\",\"pt\":\"Tartaruga\",\"pt_BR\":\"Tartaruga\",\"ru\":\"Черепаха\",\"si\":null,\"sk\":\"Korytnačka\",\"sq\":\"Breshkë\",\"sr\":\"корњача\",\"sv\":\"Sköldpadda\",\"szl\":null,\"tzm\":\"Ifker\",\"uk\":\"Черепаха\",\"vi\":\"Rùa\",\"zh_Hans\":\"乌龟\",\"zh_Hant\":\"烏龜\"}},{\"number\":12,\"emoji\":\"🐟\",\"description\":\"Fish\",\"unicode\":\"U+1F41F\",\"translated_descriptions\":{\"ar\":\"سَمَكة\",\"bg\":\"Риба\",\"ca\":\"Peix\",\"cs\":\"Ryba\",\"de\":\"Fisch\",\"eo\":\"Fiŝo\",\"es\":\"Pez\",\"et\":\"Kala\",\"fa\":\"ماهی\",\"fi\":\"Kala\",\"fr\":\"Poisson\",\"hr\":\"riba\",\"hu\":\"Hal\",\"id\":\"Ikan\",\"it\":\"Pesce\",\"ja\":\"魚\",\"nb_NO\":\"Fisk\",\"nl\":\"Vis\",\"pt\":\"Peixe\",\"pt_BR\":\"Peixe\",\"ru\":\"Рыба\",\"si\":null,\"sk\":\"Ryba\",\"sq\":\"Peshk\",\"sr\":\"риба\",\"sv\":\"Fisk\",\"szl\":null,\"tzm\":\"Aselm\",\"uk\":\"Риба\",\"vi\":\"Cá\",\"zh_Hans\":\"鱼\",\"zh_Hant\":\"魚\"}},{\"number\":13,\"emoji\":\"🐙\",\"description\":\"Octopus\",\"unicode\":\"U+1F419\",\"translated_descriptions\":{\"ar\":\"أُخطُبُوط\",\"bg\":\"Октопод\",\"ca\":\"Pop\",\"cs\":\"Chobotnice\",\"de\":\"Oktopus\",\"eo\":\"Polpo\",\"es\":\"Pulpo\",\"et\":\"Kaheksajalg\",\"fa\":\"اختاپوس\",\"fi\":\"Tursas\",\"fr\":\"Poulpe\",\"hr\":\"hobotnica\",\"hu\":\"Polip\",\"id\":\"Gurita\",\"it\":\"Polpo\",\"ja\":\"たこ\",\"nb_NO\":\"Blekksprut\",\"nl\":\"Octopus\",\"pt\":\"Polvo\",\"pt_BR\":\"Polvo\",\"ru\":\"Осьминог\",\"si\":null,\"sk\":\"Chobotnica\",\"sq\":\"Oktapod\",\"sr\":\"октопод\",\"sv\":\"Bläckfisk\",\"szl\":null,\"tzm\":null,\"uk\":\"Восьминіг\",\"vi\":\"Bạch tuộc\",\"zh_Hans\":\"章鱼\",\"zh_Hant\":\"章魚\"}},{\"number\":14,\"emoji\":\"🦋\",\"description\":\"Butterfly\",\"unicode\":\"U+1F98B\",\"translated_descriptions\":{\"ar\":\"فَرَاشَة\",\"bg\":\"Пеперуда\",\"ca\":\"Papallona\",\"cs\":\"Motýl\",\"de\":\"Schmetterling\",\"eo\":\"Papilio\",\"es\":\"Mariposa\",\"et\":\"Liblikas\",\"fa\":\"پروانه\",\"fi\":\"Perhonen\",\"fr\":\"Papillon\",\"hr\":\"leptir\",\"hu\":\"Pillangó\",\"id\":\"Kupu-Kupu\",\"it\":\"Farfalla\",\"ja\":\"ちょうちょ\",\"nb_NO\":\"Sommerfugl\",\"nl\":\"Vlinder\",\"pt\":\"Borboleta\",\"pt_BR\":\"Borboleta\",\"ru\":\"Бабочка\",\"si\":null,\"sk\":\"Motýľ\",\"sq\":\"Flutur\",\"sr\":\"лептир\",\"sv\":\"Fjäril\",\"szl\":null,\"tzm\":null,\"uk\":\"Метелик\",\"vi\":\"Bướm\",\"zh_Hans\":\"蝴蝶\",\"zh_Hant\":\"蝴蝶\"}},{\"number\":15,\"emoji\":\"🌷\",\"description\":\"Flower\",\"unicode\":\"U+1F337\",\"translated_descriptions\":{\"ar\":\"زَهرَة\",\"bg\":\"Цвете\",\"ca\":\"Flor\",\"cs\":\"Květina\",\"de\":\"Blume\",\"eo\":\"Floro\",\"es\":\"Flor\",\"et\":\"Lill\",\"fa\":\"گل\",\"fi\":\"Kukka\",\"fr\":\"Fleur\",\"hr\":\"svijet\",\"hu\":\"Virág\",\"id\":\"Bunga\",\"it\":\"Fiore\",\"ja\":\"花\",\"nb_NO\":\"Blomst\",\"nl\":\"Bloem\",\"pt\":\"Flor\",\"pt_BR\":\"Flor\",\"ru\":\"Цветок\",\"si\":null,\"sk\":\"Kvet\",\"sq\":\"Lule\",\"sr\":\"цвет\",\"sv\":\"Blomma\",\"szl\":null,\"tzm\":null,\"uk\":\"Квітка\",\"vi\":\"Hoa\",\"zh_Hans\":\"花\",\"zh_Hant\":\"花\"}},{\"number\":16,\"emoji\":\"🌳\",\"description\":\"Tree\",\"unicode\":\"U+1F333\",\"translated_descriptions\":{\"ar\":\"شَجَرَة\",\"bg\":\"Дърво\",\"ca\":\"Arbre\",\"cs\":\"Strom\",\"de\":\"Baum\",\"eo\":\"Arbo\",\"es\":\"Árbol\",\"et\":\"Puu\",\"fa\":\"درخت\",\"fi\":\"Puu\",\"fr\":\"Arbre\",\"hr\":\"drvo\",\"hu\":\"Fa\",\"id\":\"Pohon\",\"it\":\"Albero\",\"ja\":\"木\",\"nb_NO\":\"Tre\",\"nl\":\"Boom\",\"pt\":\"Árvore\",\"pt_BR\":\"Árvore\",\"ru\":\"Дерево\",\"si\":null,\"sk\":\"Strom\",\"sq\":\"Pemë\",\"sr\":\"дрво\",\"sv\":\"Träd\",\"szl\":null,\"tzm\":\"Aseklu\",\"uk\":\"Дерево\",\"vi\":\"Cây\",\"zh_Hans\":\"树\",\"zh_Hant\":\"樹\"}},{\"number\":17,\"emoji\":\"🌵\",\"description\":\"Cactus\",\"unicode\":\"U+1F335\",\"translated_descriptions\":{\"ar\":\"صبار\",\"bg\":\"Кактус\",\"ca\":\"Cactus\",\"cs\":\"Kaktus\",\"de\":\"Kaktus\",\"eo\":\"Kakto\",\"es\":\"Cactus\",\"et\":\"Kaktus\",\"fa\":\"کاکتوس\",\"fi\":\"Kaktus\",\"fr\":\"Cactus\",\"hr\":\"kaktus\",\"hu\":\"Kaktusz\",\"id\":\"Kaktus\",\"it\":\"Cactus\",\"ja\":\"サボテン\",\"nb_NO\":\"Kaktus\",\"nl\":\"Cactus\",\"pt\":\"Cato\",\"pt_BR\":\"Cacto\",\"ru\":\"Кактус\",\"si\":null,\"sk\":\"Kaktus\",\"sq\":\"Kaktus\",\"sr\":\"кактус\",\"sv\":\"Kaktus\",\"szl\":null,\"tzm\":null,\"uk\":\"Кактус\",\"vi\":\"Xương rồng\",\"zh_Hans\":\"仙人掌\",\"zh_Hant\":\"仙人掌\"}},{\"number\":18,\"emoji\":\"🍄\",\"description\":\"Mushroom\",\"unicode\":\"U+1F344\",\"translated_descriptions\":{\"ar\":\"فُطر\",\"bg\":\"Гъба\",\"ca\":\"Bolet\",\"cs\":\"Houba\",\"de\":\"Pilz\",\"eo\":\"Fungo\",\"es\":\"Seta\",\"et\":\"Seen\",\"fa\":\"قارچ\",\"fi\":\"Sieni\",\"fr\":\"Champignon\",\"hr\":\"gljiva\",\"hu\":\"Gomba\",\"id\":\"Jamur\",\"it\":\"Fungo\",\"ja\":\"きのこ\",\"nb_NO\":\"Sopp\",\"nl\":\"Paddenstoel\",\"pt\":\"Cogumelo\",\"pt_BR\":\"Cogumelo\",\"ru\":\"Гриб\",\"si\":null,\"sk\":\"Huba\",\"sq\":\"Kërpudhë\",\"sr\":\"печурка\",\"sv\":\"Svamp\",\"szl\":null,\"tzm\":\"Agursel\",\"uk\":\"Гриб\",\"vi\":\"Nấm\",\"zh_Hans\":\"蘑菇\",\"zh_Hant\":\"蘑菇\"}},{\"number\":19,\"emoji\":\"🌏\",\"description\":\"Globe\",\"unicode\":\"U+1F30F\",\"translated_descriptions\":{\"ar\":\"كُرَةٌ أرضِيَّة\",\"bg\":\"Глобус\",\"ca\":\"Globus terraqüi\",\"cs\":\"Zeměkoule\",\"de\":\"Globus\",\"eo\":\"Globo\",\"es\":\"Globo\",\"et\":\"Maakera\",\"fa\":\"زمین\",\"fi\":\"Maapallo\",\"fr\":\"Globe\",\"hr\":\"Globus\",\"hu\":\"Földgömb\",\"id\":\"Bola Dunia\",\"it\":\"Globo\",\"ja\":\"地球\",\"nb_NO\":\"Globus\",\"nl\":\"Wereldbol\",\"pt\":\"Globo\",\"pt_BR\":\"Globo\",\"ru\":\"Глобус\",\"si\":null,\"sk\":\"Zemeguľa\",\"sq\":\"Rruzull\",\"sr\":\"глобус\",\"sv\":\"Jordklot\",\"szl\":null,\"tzm\":null,\"uk\":\"Глобус\",\"vi\":\"Địa cầu\",\"zh_Hans\":\"地球\",\"zh_Hant\":\"地球\"}},{\"number\":20,\"emoji\":\"🌙\",\"description\":\"Moon\",\"unicode\":\"U+1F319\",\"translated_descriptions\":{\"ar\":\"قَمَر\",\"bg\":\"Луна\",\"ca\":\"Lluna\",\"cs\":\"Měsíc\",\"de\":\"Mond\",\"eo\":\"Luno\",\"es\":\"Luna\",\"et\":\"Kuu\",\"fa\":\"ماه\",\"fi\":\"Kuu\",\"fr\":\"Lune\",\"hr\":\"mjesec\",\"hu\":\"Hold\",\"id\":\"Bulan\",\"it\":\"Luna\",\"ja\":\"月\",\"nb_NO\":\"Måne\",\"nl\":\"Maan\",\"pt\":\"Lua\",\"pt_BR\":\"Lua\",\"ru\":\"Луна\",\"si\":null,\"sk\":\"Mesiac\",\"sq\":\"Hënë\",\"sr\":\"месец\",\"sv\":\"Måne\",\"szl\":null,\"tzm\":\"Ayyur\",\"uk\":\"Місяць\",\"vi\":\"Mặt trăng\",\"zh_Hans\":\"月亮\",\"zh_Hant\":\"月亮\"}},{\"number\":21,\"emoji\":\"☁️\",\"description\":\"Cloud\",\"unicode\":\"U+2601U+FE0F\",\"translated_descriptions\":{\"ar\":\"سَحابَة\",\"bg\":\"Облак\",\"ca\":\"Núvol\",\"cs\":\"Mrak\",\"de\":\"Wolke\",\"eo\":\"Nubo\",\"es\":\"Nube\",\"et\":\"Pilv\",\"fa\":\"ابر\",\"fi\":\"Pilvi\",\"fr\":\"Nuage\",\"hr\":\"oblak\",\"hu\":\"Felhő\",\"id\":\"Awan\",\"it\":\"Nuvola\",\"ja\":\"雲\",\"nb_NO\":\"Sky\",\"nl\":\"Wolk\",\"pt\":\"Nuvem\",\"pt_BR\":\"Nuvem\",\"ru\":\"Облако\",\"si\":null,\"sk\":\"Oblak\",\"sq\":\"Re\",\"sr\":\"облак\",\"sv\":\"Moln\",\"szl\":null,\"tzm\":null,\"uk\":\"Хмара\",\"vi\":\"Mây\",\"zh_Hans\":\"云\",\"zh_Hant\":\"雲朵\"}},{\"number\":22,\"emoji\":\"🔥\",\"description\":\"Fire\",\"unicode\":\"U+1F525\",\"translated_descriptions\":{\"ar\":\"نار\",\"bg\":\"Огън\",\"ca\":\"Foc\",\"cs\":\"Oheň\",\"de\":\"Feuer\",\"eo\":\"Fajro\",\"es\":\"Fuego\",\"et\":\"Tuli\",\"fa\":\"آتش\",\"fi\":\"Tuli\",\"fr\":\"Feu\",\"hr\":\"vatra\",\"hu\":\"Tűz\",\"id\":\"Api\",\"it\":\"Fuoco\",\"ja\":\"炎\",\"nb_NO\":\"Flamme\",\"nl\":\"Vuur\",\"pt\":\"Fogo\",\"pt_BR\":\"Fogo\",\"ru\":\"Огонь\",\"si\":null,\"sk\":\"Oheň\",\"sq\":\"Zjarr\",\"sr\":\"ватра\",\"sv\":\"Eld\",\"szl\":null,\"tzm\":\"Timessi\",\"uk\":\"Вогонь\",\"vi\":\"Lửa\",\"zh_Hans\":\"火\",\"zh_Hant\":\"火\"}},{\"number\":23,\"emoji\":\"🍌\",\"description\":\"Banana\",\"unicode\":\"U+1F34C\",\"translated_descriptions\":{\"ar\":\"مَوزَة\",\"bg\":\"Банан\",\"ca\":\"Plàtan\",\"cs\":\"Banán\",\"de\":\"Banane\",\"eo\":\"Banano\",\"es\":\"Plátano\",\"et\":\"Banaan\",\"fa\":\"موز\",\"fi\":\"Banaani\",\"fr\":\"Banane\",\"hr\":\"banana\",\"hu\":\"Banán\",\"id\":\"Pisang\",\"it\":\"Banana\",\"ja\":\"バナナ\",\"nb_NO\":\"Banan\",\"nl\":\"Banaan\",\"pt\":\"Banana\",\"pt_BR\":\"Banana\",\"ru\":\"Банан\",\"si\":null,\"sk\":\"Banán\",\"sq\":\"Banane\",\"sr\":\"банана\",\"sv\":\"Banan\",\"szl\":null,\"tzm\":\"Tabanant\",\"uk\":\"Банан\",\"vi\":\"Chuối\",\"zh_Hans\":\"香蕉\",\"zh_Hant\":\"香蕉\"}},{\"number\":24,\"emoji\":\"🍎\",\"description\":\"Apple\",\"unicode\":\"U+1F34E\",\"translated_descriptions\":{\"ar\":\"تُفَّاحَة\",\"bg\":\"Ябълка\",\"ca\":\"Poma\",\"cs\":\"Jablko\",\"de\":\"Apfel\",\"eo\":\"Pomo\",\"es\":\"Manzana\",\"et\":\"Õun\",\"fa\":\"سیب\",\"fi\":\"Omena\",\"fr\":\"Pomme\",\"hr\":\"jabuka\",\"hu\":\"Alma\",\"id\":\"Apel\",\"it\":\"Mela\",\"ja\":\"リンゴ\",\"nb_NO\":\"Eple\",\"nl\":\"Appel\",\"pt\":\"Maçã\",\"pt_BR\":\"Maçã\",\"ru\":\"Яблоко\",\"si\":null,\"sk\":\"Jablko\",\"sq\":\"Mollë\",\"sr\":\"јабука\",\"sv\":\"Äpple\",\"szl\":null,\"tzm\":\"Tadeffuyt\",\"uk\":\"Яблуко\",\"vi\":\"Táo\",\"zh_Hans\":\"苹果\",\"zh_Hant\":\"蘋果\"}},{\"number\":25,\"emoji\":\"🍓\",\"description\":\"Strawberry\",\"unicode\":\"U+1F353\",\"translated_descriptions\":{\"ar\":\"فَراوِلَة\",\"bg\":\"Ягода\",\"ca\":\"Maduixa\",\"cs\":\"Jahoda\",\"de\":\"Erdbeere\",\"eo\":\"Frago\",\"es\":\"Fresa\",\"et\":\"Maasikas\",\"fa\":\"توت فرنگی\",\"fi\":\"Mansikka\",\"fr\":\"Fraise\",\"hr\":\"jagoda\",\"hu\":\"Eper\",\"id\":\"Stroberi\",\"it\":\"Fragola\",\"ja\":\"いちご\",\"nb_NO\":\"Jordbær\",\"nl\":\"Aardbei\",\"pt\":\"Morango\",\"pt_BR\":\"Morango\",\"ru\":\"Клубника\",\"si\":null,\"sk\":\"Jahoda\",\"sq\":\"Luleshtrydhe\",\"sr\":\"јагода\",\"sv\":\"Jordgubbe\",\"szl\":null,\"tzm\":null,\"uk\":\"Полуниця\",\"vi\":\"Dâu tây\",\"zh_Hans\":\"草莓\",\"zh_Hant\":\"草莓\"}},{\"number\":26,\"emoji\":\"🌽\",\"description\":\"Corn\",\"unicode\":\"U+1F33D\",\"translated_descriptions\":{\"ar\":\"ذُرَة\",\"bg\":\"Царевица\",\"ca\":\"Blat de moro\",\"cs\":\"Kukuřice\",\"de\":\"Mais\",\"eo\":\"Maizo\",\"es\":\"Maíz\",\"et\":\"Mais\",\"fa\":\"ذرت\",\"fi\":\"Maissi\",\"fr\":\"Maïs\",\"hr\":\"kukuruza\",\"hu\":\"Kukorica\",\"id\":\"Jagung\",\"it\":\"Mais\",\"ja\":\"とうもろこし\",\"nb_NO\":\"Mais\",\"nl\":\"Maïs\",\"pt\":\"Milho\",\"pt_BR\":\"Milho\",\"ru\":\"Кукуруза\",\"si\":null,\"sk\":\"Kukurica\",\"sq\":\"Misër\",\"sr\":\"кукуруз\",\"sv\":\"Majs\",\"szl\":null,\"tzm\":null,\"uk\":\"Кукурудза\",\"vi\":\"Bắp\",\"zh_Hans\":\"玉米\",\"zh_Hant\":\"玉米\"}},{\"number\":27,\"emoji\":\"🍕\",\"description\":\"Pizza\",\"unicode\":\"U+1F355\",\"translated_descriptions\":{\"ar\":\"بِيتزا\",\"bg\":\"Пица\",\"ca\":\"Pizza\",\"cs\":\"Pizza\",\"de\":\"Pizza\",\"eo\":\"Pico\",\"es\":\"Pizza\",\"et\":\"Pitsa\",\"fa\":\"پیتزا\",\"fi\":\"Pizza\",\"fr\":\"Pizza\",\"hr\":\"pizza\",\"hu\":\"Pizza\",\"id\":\"Pizza\",\"it\":\"Pizza\",\"ja\":\"ピザ\",\"nb_NO\":\"Pizza\",\"nl\":\"Pizza\",\"pt\":\"Piza\",\"pt_BR\":\"Pizza\",\"ru\":\"Пицца\",\"si\":null,\"sk\":\"Pizza\",\"sq\":\"Picë\",\"sr\":\"пица\",\"sv\":\"Pizza\",\"szl\":null,\"tzm\":null,\"uk\":\"Піца\",\"vi\":\"Pizza\",\"zh_Hans\":\"披萨\",\"zh_Hant\":\"披薩\"}},{\"number\":28,\"emoji\":\"🎂\",\"description\":\"Cake\",\"unicode\":\"U+1F382\",\"translated_descriptions\":{\"ar\":\"كَعكَة\",\"bg\":\"Торта\",\"ca\":\"Pastís\",\"cs\":\"Dort\",\"de\":\"Kuchen\",\"eo\":\"Torto\",\"es\":\"Tarta\",\"et\":\"Kook\",\"fa\":\"کیک\",\"fi\":\"Kakku\",\"fr\":\"Gâteau\",\"hr\":\"torta\",\"hu\":\"Süti\",\"id\":\"Kue\",\"it\":\"Torta\",\"ja\":\"ケーキ\",\"nb_NO\":\"Kake\",\"nl\":\"Taart\",\"pt\":\"Bolo\",\"pt_BR\":\"Bolo\",\"ru\":\"Торт\",\"si\":null,\"sk\":\"Torta\",\"sq\":\"Tortë\",\"sr\":\"торта\",\"sv\":\"Tårta\",\"szl\":null,\"tzm\":null,\"uk\":\"Пиріг\",\"vi\":\"Bánh\",\"zh_Hans\":\"蛋糕\",\"zh_Hant\":\"蛋糕\"}},{\"number\":29,\"emoji\":\"❤️\",\"description\":\"Heart\",\"unicode\":\"U+2764U+FE0F\",\"translated_descriptions\":{\"ar\":\"قَلب\",\"bg\":\"Сърце\",\"ca\":\"Cor\",\"cs\":\"Srdce\",\"de\":\"Herz\",\"eo\":\"Koro\",\"es\":\"Corazón\",\"et\":\"Süda\",\"fa\":\"قلب\",\"fi\":\"Sydän\",\"fr\":\"Cœur\",\"hr\":\"srca\",\"hu\":\"Szív\",\"id\":\"Hati\",\"it\":\"Cuore\",\"ja\":\"ハート\",\"nb_NO\":\"Hjerte\",\"nl\":\"Hart\",\"pt\":\"Coração\",\"pt_BR\":\"Coração\",\"ru\":\"Сердце\",\"si\":null,\"sk\":\"Srdce\",\"sq\":\"Zemër\",\"sr\":\"срце\",\"sv\":\"Hjärta\",\"szl\":null,\"tzm\":\"Ul\",\"uk\":\"Серце\",\"vi\":\"Tim\",\"zh_Hans\":\"心\",\"zh_Hant\":\"愛心\"}},{\"number\":30,\"emoji\":\"😀\",\"description\":\"Smiley\",\"unicode\":\"U+1F600\",\"translated_descriptions\":{\"ar\":\"اِبتِسَامَة\",\"bg\":\"Усмивка\",\"ca\":\"Somrient\",\"cs\":\"Smajlík\",\"de\":\"Lächeln\",\"eo\":\"Rideto\",\"es\":\"Emoticono\",\"et\":\"Smaili\",\"fa\":\"خنده\",\"fi\":\"Hymynaama\",\"fr\":\"Sourire\",\"hr\":\"smajlića\",\"hu\":\"Mosoly\",\"id\":\"Senyuman\",\"it\":\"Faccina sorridente\",\"ja\":\"スマイル\",\"nb_NO\":\"Smilefjes\",\"nl\":\"Smiley\",\"pt\":\"Sorriso\",\"pt_BR\":\"Sorriso\",\"ru\":\"Улыбка\",\"si\":null,\"sk\":\"Smajlík\",\"sq\":\"Emotikon\",\"sr\":\"смајли\",\"sv\":\"Smiley\",\"szl\":null,\"tzm\":null,\"uk\":\"Посмішка\",\"vi\":\"Mặt cười\",\"zh_Hans\":\"笑脸\",\"zh_Hant\":\"笑臉\"}},{\"number\":31,\"emoji\":\"🤖\",\"description\":\"Robot\",\"unicode\":\"U+1F916\",\"translated_descriptions\":{\"ar\":\"رُوبُوت\",\"bg\":\"Робот\",\"ca\":\"Robot\",\"cs\":\"Robot\",\"de\":\"Roboter\",\"eo\":\"Roboto\",\"es\":\"Robot\",\"et\":\"Robot\",\"fa\":\"ربات\",\"fi\":\"Robotti\",\"fr\":\"Robot\",\"hr\":\"robot\",\"hu\":\"Robot\",\"id\":\"Robot\",\"it\":\"Robot\",\"ja\":\"ロボット\",\"nb_NO\":\"Robot\",\"nl\":\"Robot\",\"pt\":\"Robô\",\"pt_BR\":\"Robô\",\"ru\":\"Робот\",\"si\":null,\"sk\":\"Robot\",\"sq\":\"Robot\",\"sr\":\"робот\",\"sv\":\"Robot\",\"szl\":null,\"tzm\":\"Aṛubu\",\"uk\":\"Робот\",\"vi\":\"Rô-bô\",\"zh_Hans\":\"机器人\",\"zh_Hant\":\"機器人\"}},{\"number\":32,\"emoji\":\"🎩\",\"description\":\"Hat\",\"unicode\":\"U+1F3A9\",\"translated_descriptions\":{\"ar\":\"قُبَّعَة\",\"bg\":\"Шапка\",\"ca\":\"Barret\",\"cs\":\"Klobouk\",\"de\":\"Hut\",\"eo\":\"Ĉapelo\",\"es\":\"Sombrero\",\"et\":\"Kübar\",\"fa\":\"کلاه\",\"fi\":\"Hattu\",\"fr\":\"Chapeau\",\"hr\":\"kapa\",\"hu\":\"Kalap\",\"id\":\"Topi\",\"it\":\"Cappello\",\"ja\":\"帽子\",\"nb_NO\":\"Hatt\",\"nl\":\"Hoed\",\"pt\":\"Chapéu\",\"pt_BR\":\"Chapéu\",\"ru\":\"Шляпа\",\"si\":null,\"sk\":\"Klobúk\",\"sq\":\"Kapë\",\"sr\":\"шешир\",\"sv\":\"Hatt\",\"szl\":null,\"tzm\":\"Taraza\",\"uk\":\"Капелюх\",\"vi\":\"Mũ\",\"zh_Hans\":\"帽子\",\"zh_Hant\":\"帽子\"}},{\"number\":33,\"emoji\":\"👓\",\"description\":\"Glasses\",\"unicode\":\"U+1F453\",\"translated_descriptions\":{\"ar\":\"نَظَّارَة\",\"bg\":\"Очила\",\"ca\":\"Ulleres\",\"cs\":\"Brýle\",\"de\":\"Brille\",\"eo\":\"Okulvitroj\",\"es\":\"Gafas\",\"et\":\"Prillid\",\"fa\":\"عینک\",\"fi\":\"Silmälasit\",\"fr\":\"Lunettes\",\"hr\":\"naočale\",\"hu\":\"Szemüveg\",\"id\":\"Kacamata\",\"it\":\"Occhiali\",\"ja\":\"めがね\",\"nb_NO\":\"Briller\",\"nl\":\"Bril\",\"pt\":\"Óculos\",\"pt_BR\":\"Óculos\",\"ru\":\"Очки\",\"si\":null,\"sk\":\"Okuliare\",\"sq\":\"Syze\",\"sr\":\"наочаре\",\"sv\":\"Glasögon\",\"szl\":null,\"tzm\":null,\"uk\":\"Окуляри\",\"vi\":\"Kính mắt\",\"zh_Hans\":\"眼镜\",\"zh_Hant\":\"眼鏡\"}},{\"number\":34,\"emoji\":\"🔧\",\"description\":\"Spanner\",\"unicode\":\"U+1F527\",\"translated_descriptions\":{\"ar\":\"مِفتَاحُ رَبط\",\"bg\":\"Гаечен ключ\",\"ca\":\"Clau anglesa\",\"cs\":\"Klíč\",\"de\":\"Schraubenschlüssel\",\"eo\":\"Ŝraŭbŝlosilo\",\"es\":\"Llave inglesa\",\"et\":\"Mutrivõti\",\"fa\":\"آچار\",\"fi\":\"Kiintoavain\",\"fr\":\"Clé à molette\",\"hr\":\"ključ\",\"hu\":\"Csavarkulcs\",\"id\":\"Kunci Bengkel\",\"it\":\"Chiave inglese\",\"ja\":\"スパナ\",\"nb_NO\":\"Fastnøkkel\",\"nl\":\"Moersleutel\",\"pt\":\"Chave inglesa\",\"pt_BR\":\"Chave inglesa\",\"ru\":\"Ключ\",\"si\":null,\"sk\":\"Vidlicový kľúč\",\"sq\":\"Çelës\",\"sr\":\"кључ\",\"sv\":\"Skruvnyckel\",\"szl\":null,\"tzm\":null,\"uk\":\"Гайковий ключ\",\"vi\":\"Cờ-lê\",\"zh_Hans\":\"扳手\",\"zh_Hant\":\"扳手\"}},{\"number\":35,\"emoji\":\"🎅\",\"description\":\"Santa\",\"unicode\":\"U+1F385\",\"translated_descriptions\":{\"ar\":\"سانتا\",\"bg\":\"Дядо Коледа\",\"ca\":\"Pare Noél\",\"cs\":\"Mikuláš\",\"de\":\"Weihnachtsmann\",\"eo\":\"Kristnaska viro\",\"es\":\"Papá Noel\",\"et\":\"Jõuluvana\",\"fa\":\"بابا نوئل\",\"fi\":\"Joulupukki\",\"fr\":\"Père Noël\",\"hr\":\"deda Mraz\",\"hu\":\"Télapó\",\"id\":\"Santa\",\"it\":\"Babbo Natale\",\"ja\":\"サンタ\",\"nb_NO\":\"Julenisse\",\"nl\":\"Kerstman\",\"pt\":\"Pai Natal\",\"pt_BR\":\"Papai-noel\",\"ru\":\"Санта\",\"si\":null,\"sk\":\"Mikuláš\",\"sq\":\"Babagjyshi i Vitit të Ri\",\"sr\":\"деда Мраз\",\"sv\":\"Tomte\",\"szl\":null,\"tzm\":null,\"uk\":\"Санта Клаус\",\"vi\":\"ông già Nô-en\",\"zh_Hans\":\"圣诞老人\",\"zh_Hant\":\"聖誕老人\"}},{\"number\":36,\"emoji\":\"👍\",\"description\":\"Thumbs Up\",\"unicode\":\"U+1F44D\",\"translated_descriptions\":{\"ar\":\"رَفعُ إِبهَام\",\"bg\":\"Палец нагоре\",\"ca\":\"Polzes amunt\",\"cs\":\"Palec nahoru\",\"de\":\"Daumen Hoch\",\"eo\":\"Dikfingro supren\",\"es\":\"Pulgar arriba\",\"et\":\"Pöidlad püsti\",\"fa\":\"لایک\",\"fi\":\"Peukalo ylös\",\"fr\":\"Pouce en l’air\",\"hr\":\"palac gore\",\"hu\":\"Hüvelykujj fel\",\"id\":\"Jempol\",\"it\":\"Pollice alzato\",\"ja\":\"いいね\",\"nb_NO\":\"Tommel Opp\",\"nl\":\"Duim omhoog\",\"pt\":\"Polegar para cima\",\"pt_BR\":\"Joinha\",\"ru\":\"Большой палец вверх\",\"si\":null,\"sk\":\"Palec nahor\",\"sq\":null,\"sr\":\"палчић горе\",\"sv\":\"Tummen upp\",\"szl\":null,\"tzm\":null,\"uk\":\"Великий палець вгору\",\"vi\":\"Thích\",\"zh_Hans\":\"赞\",\"zh_Hant\":\"讚\"}},{\"number\":37,\"emoji\":\"☂️\",\"description\":\"Umbrella\",\"unicode\":\"U+2602U+FE0F\",\"translated_descriptions\":{\"ar\":\"مِظَلَّة\",\"bg\":\"Чадър\",\"ca\":\"Paraigües\",\"cs\":\"Deštník\",\"de\":\"Regenschirm\",\"eo\":\"Ombrelo\",\"es\":\"Paraguas\",\"et\":\"Vihmavari\",\"fa\":\"چتر\",\"fi\":\"Sateenvarjo\",\"fr\":\"Parapluie\",\"hr\":\"kišobran\",\"hu\":\"Esernyő\",\"id\":\"Payung\",\"it\":\"Ombrello\",\"ja\":\"傘\",\"nb_NO\":\"Paraply\",\"nl\":\"Paraplu\",\"pt\":\"Guarda-chuva\",\"pt_BR\":\"Guarda-chuva\",\"ru\":\"Зонт\",\"si\":null,\"sk\":\"Dáždnik\",\"sq\":\"Ombrellë\",\"sr\":\"кишобран\",\"sv\":\"Paraply\",\"szl\":null,\"tzm\":null,\"uk\":\"Парасолька\",\"vi\":\"Cái ô\",\"zh_Hans\":\"伞\",\"zh_Hant\":\"雨傘\"}},{\"number\":38,\"emoji\":\"⌛\",\"description\":\"Hourglass\",\"unicode\":\"U+231B\",\"translated_descriptions\":{\"ar\":\"سَاعَةٌ رَملِيَّة\",\"bg\":\"Пясъчен часовник\",\"ca\":\"Rellotge de sorra\",\"cs\":\"Přesýpací hodiny\",\"de\":\"Sanduhr\",\"eo\":\"Sablohorloĝo\",\"es\":\"Reloj de arena\",\"et\":\"Liivakell\",\"fa\":\"ساعت شنی\",\"fi\":\"Tiimalasi\",\"fr\":\"Sablier\",\"hr\":\"pješčani sat\",\"hu\":\"Homokóra\",\"id\":\"Jam Pasir\",\"it\":\"Clessidra\",\"ja\":\"砂時計\",\"nb_NO\":\"Timeglass\",\"nl\":\"Zandloper\",\"pt\":\"Ampulheta\",\"pt_BR\":\"Ampulheta\",\"ru\":\"Песочные часы\",\"si\":null,\"sk\":\"Presýpacie hodiny\",\"sq\":\"Klepsidër\",\"sr\":\"пешчаник\",\"sv\":\"Timglas\",\"szl\":null,\"tzm\":null,\"uk\":\"Пісковий годинник\",\"vi\":\"Đồng hồ cát\",\"zh_Hans\":\"沙漏\",\"zh_Hant\":\"沙漏\"}},{\"number\":39,\"emoji\":\"⏰\",\"description\":\"Clock\",\"unicode\":\"U+23F0\",\"translated_descriptions\":{\"ar\":\"سَاعَة\",\"bg\":\"Часовник\",\"ca\":\"Rellotge\",\"cs\":\"Hodiny\",\"de\":\"Uhr\",\"eo\":\"Horloĝo\",\"es\":\"Reloj\",\"et\":\"Kell\",\"fa\":\"ساعت\",\"fi\":\"Pöytäkello\",\"fr\":\"Réveil\",\"hr\":\"sat\",\"hu\":\"Óra\",\"id\":\"Jam\",\"it\":\"Orologio\",\"ja\":\"時計\",\"nb_NO\":\"Klokke\",\"nl\":\"Wekker\",\"pt\":\"Relógio\",\"pt_BR\":\"Relógio\",\"ru\":\"Часы\",\"si\":null,\"sk\":\"Budík\",\"sq\":\"Sahat\",\"sr\":\"сат\",\"sv\":\"Klocka\",\"szl\":null,\"tzm\":null,\"uk\":\"Годинник\",\"vi\":\"Đồng hồ\",\"zh_Hans\":\"时钟\",\"zh_Hant\":\"時鐘\"}},{\"number\":40,\"emoji\":\"🎁\",\"description\":\"Gift\",\"unicode\":\"U+1F381\",\"translated_descriptions\":{\"ar\":\"هَدِيَّة\",\"bg\":\"Подарък\",\"ca\":\"Regal\",\"cs\":\"Dárek\",\"de\":\"Geschenk\",\"eo\":\"Donaco\",\"es\":\"Regalo\",\"et\":\"Kingitus\",\"fa\":\"هدیه\",\"fi\":\"Lahja\",\"fr\":\"Cadeau\",\"hr\":\"poklon\",\"hu\":\"Ajándék\",\"id\":\"Kado\",\"it\":\"Regalo\",\"ja\":\"ギフト\",\"nb_NO\":\"Gave\",\"nl\":\"Geschenk\",\"pt\":\"Presente\",\"pt_BR\":\"Presente\",\"ru\":\"Подарок\",\"si\":null,\"sk\":\"Darček\",\"sq\":\"Dhuratë\",\"sr\":\"поклон\",\"sv\":\"Present\",\"szl\":null,\"tzm\":null,\"uk\":\"Подарунок\",\"vi\":\"Quà tặng\",\"zh_Hans\":\"礼物\",\"zh_Hant\":\"禮物\"}},{\"number\":41,\"emoji\":\"💡\",\"description\":\"Light Bulb\",\"unicode\":\"U+1F4A1\",\"translated_descriptions\":{\"ar\":\"مِصبَاح\",\"bg\":\"Лампа\",\"ca\":\"Bombeta\",\"cs\":\"Žárovka\",\"de\":\"Glühbirne\",\"eo\":\"Lampo\",\"es\":\"Bombilla\",\"et\":\"Lambipirn\",\"fa\":\"لامپ\",\"fi\":\"Hehkulamppu\",\"fr\":\"Ampoule\",\"hr\":\"žarulja\",\"hu\":\"Égő\",\"id\":\"Bohlam Lampu\",\"it\":\"Lampadina\",\"ja\":\"電球\",\"nb_NO\":\"Lyspære\",\"nl\":\"Gloeilamp\",\"pt\":\"Lâmpada\",\"pt_BR\":\"Lâmpada\",\"ru\":\"Лампочка\",\"si\":null,\"sk\":\"Žiarovka\",\"sq\":\"Llambë\",\"sr\":\"сијалица\",\"sv\":\"Lampa\",\"szl\":null,\"tzm\":null,\"uk\":\"Лампочка\",\"vi\":\"Bóng đèn tròn\",\"zh_Hans\":\"灯泡\",\"zh_Hant\":\"燈泡\"}},{\"number\":42,\"emoji\":\"📕\",\"description\":\"Book\",\"unicode\":\"U+1F4D5\",\"translated_descriptions\":{\"ar\":\"كِتَاب\",\"bg\":\"Книга\",\"ca\":\"Llibre\",\"cs\":\"Kniha\",\"de\":\"Buch\",\"eo\":\"Libro\",\"es\":\"Libro\",\"et\":\"Raamat\",\"fa\":\"کتاب\",\"fi\":\"Kirja\",\"fr\":\"Livre\",\"hr\":\"knjiga\",\"hu\":\"Könyv\",\"id\":\"Buku\",\"it\":\"Libro\",\"ja\":\"本\",\"nb_NO\":\"Bok\",\"nl\":\"Boek\",\"pt\":\"Livro\",\"pt_BR\":\"Livro\",\"ru\":\"Книга\",\"si\":null,\"sk\":\"Kniha\",\"sq\":\"Libër\",\"sr\":\"књига\",\"sv\":\"Bok\",\"szl\":null,\"tzm\":\"Adlis\",\"uk\":\"Книга\",\"vi\":\"Sách\",\"zh_Hans\":\"书\",\"zh_Hant\":\"書\"}},{\"number\":43,\"emoji\":\"✏️\",\"description\":\"Pencil\",\"unicode\":\"U+270FU+FE0F\",\"translated_descriptions\":{\"ar\":\"قَلَمُ رَصاص\",\"bg\":\"Молив\",\"ca\":\"Llapis\",\"cs\":\"Tužka\",\"de\":\"Bleistift\",\"eo\":\"Krajono\",\"es\":\"Lápiz\",\"et\":\"Pliiats\",\"fa\":\"مداد\",\"fi\":\"Lyijykynä\",\"fr\":\"Crayon\",\"hr\":\"olovka\",\"hu\":\"Ceruza\",\"id\":\"Pensil\",\"it\":\"Matita\",\"ja\":\"鉛筆\",\"nb_NO\":\"Blyant\",\"nl\":\"Potlood\",\"pt\":\"Lápis\",\"pt_BR\":\"Lápis\",\"ru\":\"Карандаш\",\"si\":null,\"sk\":\"Ceruzka\",\"sq\":\"Laps\",\"sr\":\"оловка\",\"sv\":\"Penna\",\"szl\":null,\"tzm\":null,\"uk\":\"Олівець\",\"vi\":\"Viết chì\",\"zh_Hans\":\"铅笔\",\"zh_Hant\":\"鉛筆\"}},{\"number\":44,\"emoji\":\"📎\",\"description\":\"Paperclip\",\"unicode\":\"U+1F4CE\",\"translated_descriptions\":{\"ar\":\"مِشبَكُ وَرَق\",\"bg\":\"Кламер\",\"ca\":\"Clip\",\"cs\":\"Sponka\",\"de\":\"Büroklammer\",\"eo\":\"Paperkuntenilo\",\"es\":\"Clip\",\"et\":\"Kirjaklamber\",\"fa\":\"گیره کاغذ\",\"fi\":\"Paperiliitin\",\"fr\":\"Trombone\",\"hr\":\"spajalica\",\"hu\":\"Gémkapocs\",\"id\":\"Klip Kertas\",\"it\":\"Graffetta\",\"ja\":\"クリップ\",\"nb_NO\":\"BInders\",\"nl\":\"Papierklemmetje\",\"pt\":\"Clipe\",\"pt_BR\":\"Clipe de papel\",\"ru\":\"Скрепка\",\"si\":null,\"sk\":\"Kancelárska sponka\",\"sq\":\"Kapëse\",\"sr\":\"спајалица\",\"sv\":\"Gem\",\"szl\":null,\"tzm\":null,\"uk\":\"Спиначка\",\"vi\":\"Kẹp giấy\",\"zh_Hans\":\"回形针\",\"zh_Hant\":\"迴紋針\"}},{\"number\":45,\"emoji\":\"✂️\",\"description\":\"Scissors\",\"unicode\":\"U+2702U+FE0F\",\"translated_descriptions\":{\"ar\":\"مِقَصّ\",\"bg\":\"Ножици\",\"ca\":\"Tisores\",\"cs\":\"Nůžky\",\"de\":\"Schere\",\"eo\":\"Tondilo\",\"es\":\"Tijeras\",\"et\":\"Käärid\",\"fa\":\"قیچی\",\"fi\":\"Sakset\",\"fr\":\"Ciseaux\",\"hr\":\"škare\",\"hu\":\"Olló\",\"id\":\"Gunting\",\"it\":\"Forbici\",\"ja\":\"はさみ\",\"nb_NO\":\"Saks\",\"nl\":\"Schaar\",\"pt\":\"Tesoura\",\"pt_BR\":\"Tesoura\",\"ru\":\"Ножницы\",\"si\":null,\"sk\":\"Nožnice\",\"sq\":\"Gërshërë\",\"sr\":\"маказе\",\"sv\":\"Sax\",\"szl\":null,\"tzm\":null,\"uk\":\"Ножиці\",\"vi\":\"Cái kéo\",\"zh_Hans\":\"剪刀\",\"zh_Hant\":\"剪刀\"}},{\"number\":46,\"emoji\":\"🔒\",\"description\":\"Lock\",\"unicode\":\"U+1F512\",\"translated_descriptions\":{\"ar\":\"قُفل\",\"bg\":\"Катинар\",\"ca\":\"Cadenat\",\"cs\":\"Zámek\",\"de\":\"Schloss\",\"eo\":\"Seruro\",\"es\":\"Candado\",\"et\":\"Lukk\",\"fa\":\"قفل\",\"fi\":\"Lukko\",\"fr\":\"Cadenas\",\"hr\":\"zaključati\",\"hu\":\"Lakat\",\"id\":\"Gembok\",\"it\":\"Lucchetto\",\"ja\":\"錠前\",\"nb_NO\":\"Lås\",\"nl\":\"Slot\",\"pt\":\"Cadeado\",\"pt_BR\":\"Cadeado\",\"ru\":\"Замок\",\"si\":null,\"sk\":\"Zámka\",\"sq\":\"Dry\",\"sr\":\"катанац\",\"sv\":\"Lås\",\"szl\":null,\"tzm\":null,\"uk\":\"Замок\",\"vi\":\"Ổ khóa\",\"zh_Hans\":\"锁\",\"zh_Hant\":\"鎖頭\"}},{\"number\":47,\"emoji\":\"🔑\",\"description\":\"Key\",\"unicode\":\"U+1F511\",\"translated_descriptions\":{\"ar\":\"مِفتَاح\",\"bg\":\"Ключ\",\"ca\":\"Clau\",\"cs\":\"Klíč ke dveřím\",\"de\":\"Schlüssel\",\"eo\":\"Ŝlosilo\",\"es\":\"Llave\",\"et\":\"Võti\",\"fa\":\"کلید\",\"fi\":\"Avain\",\"fr\":\"Clé\",\"hr\":\"ključ\",\"hu\":\"Kulcs\",\"id\":\"Kunci\",\"it\":\"Chiave\",\"ja\":\"鍵\",\"nb_NO\":\"Nøkkel\",\"nl\":\"Sleutel\",\"pt\":\"Chave\",\"pt_BR\":\"Chave\",\"ru\":\"Ключ\",\"si\":null,\"sk\":\"Kľúč\",\"sq\":\"Çelës\",\"sr\":\"кључ\",\"sv\":\"Nyckel\",\"szl\":null,\"tzm\":\"Tasarut\",\"uk\":\"Ключ\",\"vi\":\"Chìa khóa\",\"zh_Hans\":\"钥匙\",\"zh_Hant\":\"鑰匙\"}},{\"number\":48,\"emoji\":\"🔨\",\"description\":\"Hammer\",\"unicode\":\"U+1F528\",\"translated_descriptions\":{\"ar\":\"مِطرَقَة\",\"bg\":\"Чук\",\"ca\":\"Martell\",\"cs\":\"Kladivo\",\"de\":\"Hammer\",\"eo\":\"Martelo\",\"es\":\"Martillo\",\"et\":\"Haamer\",\"fa\":\"چکش\",\"fi\":\"Vasara\",\"fr\":\"Marteau\",\"hr\":\"čekić\",\"hu\":\"Kalapács\",\"id\":\"Palu\",\"it\":\"Martello\",\"ja\":\"金槌\",\"nb_NO\":\"Hammer\",\"nl\":\"Hamer\",\"pt\":\"Martelo\",\"pt_BR\":\"Martelo\",\"ru\":\"Молоток\",\"si\":null,\"sk\":\"Kladivo\",\"sq\":\"Çekiç\",\"sr\":\"чекић\",\"sv\":\"Hammare\",\"szl\":null,\"tzm\":null,\"uk\":\"Молоток\",\"vi\":\"Búa\",\"zh_Hans\":\"锤子\",\"zh_Hant\":\"鎚子\"}},{\"number\":49,\"emoji\":\"☎️\",\"description\":\"Telephone\",\"unicode\":\"U+260EU+FE0F\",\"translated_descriptions\":{\"ar\":\"تِلِفُون\",\"bg\":\"Телефон\",\"ca\":\"Telèfon\",\"cs\":\"Telefon\",\"de\":\"Telefon\",\"eo\":\"Telefono\",\"es\":\"Teléfono\",\"et\":\"Telefon\",\"fa\":\"تلفن\",\"fi\":\"Puhelin\",\"fr\":\"Téléphone\",\"hr\":\"telefon\",\"hu\":\"Telefon\",\"id\":\"Telepon\",\"it\":\"Telefono\",\"ja\":\"電話機\",\"nb_NO\":\"Telefon\",\"nl\":\"Telefoon\",\"pt\":\"Telefone\",\"pt_BR\":\"Telefone\",\"ru\":\"Телефон\",\"si\":null,\"sk\":\"Telefón\",\"sq\":\"Telefon\",\"sr\":\"телефон\",\"sv\":\"Telefon\",\"szl\":null,\"tzm\":\"Atilifun\",\"uk\":\"Телефон\",\"vi\":\"Điện thoại\",\"zh_Hans\":\"电话\",\"zh_Hant\":\"電話\"}},{\"number\":50,\"emoji\":\"🏁\",\"description\":\"Flag\",\"unicode\":\"U+1F3C1\",\"translated_descriptions\":{\"ar\":\"عَلَم\",\"bg\":\"Флаг\",\"ca\":\"Bandera\",\"cs\":\"Vlajka\",\"de\":\"Flagge\",\"eo\":\"Flago\",\"es\":\"Bandera\",\"et\":\"Lipp\",\"fa\":\"پرچم\",\"fi\":\"Lippu\",\"fr\":\"Drapeau\",\"hr\":\"zastava\",\"hu\":\"Zászló\",\"id\":\"Bendera\",\"it\":\"Bandiera\",\"ja\":\"旗\",\"nb_NO\":\"Flagg\",\"nl\":\"Vlag\",\"pt\":\"Bandeira\",\"pt_BR\":\"Bandeira\",\"ru\":\"Флаг\",\"si\":null,\"sk\":\"Zástava\",\"sq\":\"Flamur\",\"sr\":\"застава\",\"sv\":\"Flagga\",\"szl\":null,\"tzm\":\"Acenyal\",\"uk\":\"Прапор\",\"vi\":\"Lá cờ\",\"zh_Hans\":\"旗帜\",\"zh_Hant\":\"旗幟\"}},{\"number\":51,\"emoji\":\"🚂\",\"description\":\"Train\",\"unicode\":\"U+1F682\",\"translated_descriptions\":{\"ar\":\"قِطَار\",\"bg\":\"Влак\",\"ca\":\"Tren\",\"cs\":\"Vlak\",\"de\":\"Zug\",\"eo\":\"Vagonaro\",\"es\":\"Tren\",\"et\":\"Rong\",\"fa\":\"قطار\",\"fi\":\"Juna\",\"fr\":\"Train\",\"hr\":\"vlak\",\"hu\":\"Vonat\",\"id\":\"Kereta Api\",\"it\":\"Treno\",\"ja\":\"電車\",\"nb_NO\":\"Tog\",\"nl\":\"Trein\",\"pt\":\"Comboio\",\"pt_BR\":\"Trem\",\"ru\":\"Поезд\",\"si\":null,\"sk\":\"Vlak\",\"sq\":\"Tren\",\"sr\":\"воз\",\"sv\":\"Tåg\",\"szl\":null,\"tzm\":null,\"uk\":\"Потяг\",\"vi\":\"Xe lửa\",\"zh_Hans\":\"火车\",\"zh_Hant\":\"火車\"}},{\"number\":52,\"emoji\":\"🚲\",\"description\":\"Bicycle\",\"unicode\":\"U+1F6B2\",\"translated_descriptions\":{\"ar\":\"دَرّاجَة\",\"bg\":\"Колело\",\"ca\":\"Bicicleta\",\"cs\":\"Kolo\",\"de\":\"Fahrrad\",\"eo\":\"Biciklo\",\"es\":\"Bicicleta\",\"et\":\"Jalgratas\",\"fa\":\"دوچرخه\",\"fi\":\"Polkupyörä\",\"fr\":\"Vélo\",\"hr\":\"bicikl\",\"hu\":\"Kerékpár\",\"id\":\"Sepeda\",\"it\":\"Bicicletta\",\"ja\":\"自転車\",\"nb_NO\":\"Sykkel\",\"nl\":\"Fiets\",\"pt\":\"Bicicleta\",\"pt_BR\":\"Bicicleta\",\"ru\":\"Велосипед\",\"si\":null,\"sk\":\"Bicykel\",\"sq\":\"Biçikletë\",\"sr\":\"бицикл\",\"sv\":\"Cykel\",\"szl\":null,\"tzm\":null,\"uk\":\"Велосипед\",\"vi\":\"Xe đạp\",\"zh_Hans\":\"自行车\",\"zh_Hant\":\"腳踏車\"}},{\"number\":53,\"emoji\":\"✈️\",\"description\":\"Aeroplane\",\"unicode\":\"U+2708U+FE0F\",\"translated_descriptions\":{\"ar\":\"طَائِرة\",\"bg\":\"Самолет\",\"ca\":\"Avió\",\"cs\":\"Letadlo\",\"de\":\"Flugzeug\",\"eo\":\"Aviadilo\",\"es\":\"Avión\",\"et\":\"Lennuk\",\"fa\":\"هواپیما\",\"fi\":\"Lentokone\",\"fr\":\"Avion\",\"hr\":\"avion\",\"hu\":\"Repülő\",\"id\":\"Pesawat\",\"it\":\"Aeroplano\",\"ja\":\"飛行機\",\"nb_NO\":\"Fly\",\"nl\":\"Vliegtuig\",\"pt\":\"Avião\",\"pt_BR\":\"Avião\",\"ru\":\"Самолет\",\"si\":null,\"sk\":\"Lietadlo\",\"sq\":\"Avion\",\"sr\":\"авион\",\"sv\":\"Flygplan\",\"szl\":null,\"tzm\":null,\"uk\":\"Літак\",\"vi\":\"Máy bay\",\"zh_Hans\":\"飞机\",\"zh_Hant\":\"飛機\"}},{\"number\":54,\"emoji\":\"🚀\",\"description\":\"Rocket\",\"unicode\":\"U+1F680\",\"translated_descriptions\":{\"ar\":\"صَارُوخ\",\"bg\":\"Ракета\",\"ca\":\"Coet\",\"cs\":\"Raketa\",\"de\":\"Rakete\",\"eo\":\"Raketo\",\"es\":\"Cohete\",\"et\":\"Rakett\",\"fa\":\"موشک\",\"fi\":\"Raketti\",\"fr\":\"Fusée\",\"hr\":\"raketa\",\"hu\":\"Rakáta\",\"id\":\"Roket\",\"it\":\"Razzo\",\"ja\":\"ロケット\",\"nb_NO\":\"Rakett\",\"nl\":\"Raket\",\"pt\":\"Foguetão\",\"pt_BR\":\"Foguete\",\"ru\":\"Ракета\",\"si\":null,\"sk\":\"Raketa\",\"sq\":\"Raketë\",\"sr\":\"ракета\",\"sv\":\"Raket\",\"szl\":null,\"tzm\":null,\"uk\":\"Ракета\",\"vi\":\"Tên lửa\",\"zh_Hans\":\"火箭\",\"zh_Hant\":\"火箭\"}},{\"number\":55,\"emoji\":\"🏆\",\"description\":\"Trophy\",\"unicode\":\"U+1F3C6\",\"translated_descriptions\":{\"ar\":\"كَأسُ النَّصر\",\"bg\":\"Трофей\",\"ca\":\"Trofeu\",\"cs\":\"Pohár\",\"de\":\"Pokal\",\"eo\":\"Trofeo\",\"es\":\"Trofeo\",\"et\":\"Auhind\",\"fa\":\"جام\",\"fi\":\"Palkinto\",\"fr\":\"Trophée\",\"hr\":\"trofej\",\"hu\":\"Trófea\",\"id\":\"Piala\",\"it\":\"Trofeo\",\"ja\":\"トロフィー\",\"nb_NO\":\"Pokal\",\"nl\":\"Trofee\",\"pt\":\"Troféu\",\"pt_BR\":\"Troféu\",\"ru\":\"Кубок\",\"si\":null,\"sk\":\"Trofej\",\"sq\":\"Trofe\",\"sr\":\"пехар\",\"sv\":\"Trofé\",\"szl\":null,\"tzm\":null,\"uk\":\"Приз\",\"vi\":\"Cúp\",\"zh_Hans\":\"奖杯\",\"zh_Hant\":\"獎盃\"}},{\"number\":56,\"emoji\":\"⚽\",\"description\":\"Ball\",\"unicode\":\"U+26BD\",\"translated_descriptions\":{\"ar\":\"كُرَة\",\"bg\":\"Топка\",\"ca\":\"Pilota\",\"cs\":\"Míč\",\"de\":\"Ball\",\"eo\":\"Pilko\",\"es\":\"Bola\",\"et\":\"Pall\",\"fa\":\"توپ\",\"fi\":\"Pallo\",\"fr\":\"Ballon\",\"hr\":\"lopta\",\"hu\":\"Labda\",\"id\":\"Bola\",\"it\":\"Palla\",\"ja\":\"ボール\",\"nb_NO\":\"Ball\",\"nl\":\"Bal\",\"pt\":\"Bola\",\"pt_BR\":\"Bola\",\"ru\":\"Мяч\",\"si\":null,\"sk\":\"Lopta\",\"sq\":\"Top\",\"sr\":\"лопта\",\"sv\":\"Boll\",\"szl\":null,\"tzm\":\"Tcama\",\"uk\":\"М'яч\",\"vi\":\"Banh\",\"zh_Hans\":\"球\",\"zh_Hant\":\"足球\"}},{\"number\":57,\"emoji\":\"🎸\",\"description\":\"Guitar\",\"unicode\":\"U+1F3B8\",\"translated_descriptions\":{\"ar\":\"غيتار\",\"bg\":\"Китара\",\"ca\":\"Guitarra\",\"cs\":\"Kytara\",\"de\":\"Gitarre\",\"eo\":\"Gitaro\",\"es\":\"Guitarra\",\"et\":\"Kitarr\",\"fa\":\"گیتار\",\"fi\":\"Kitara\",\"fr\":\"Guitare\",\"hr\":\"gitara\",\"hu\":\"Gitár\",\"id\":\"Gitar\",\"it\":\"Chitarra\",\"ja\":\"ギター\",\"nb_NO\":\"Gitar\",\"nl\":\"Gitaar\",\"pt\":\"Guitarra\",\"pt_BR\":\"Guitarra\",\"ru\":\"Гитара\",\"si\":null,\"sk\":\"Gitara\",\"sq\":\"Kitarë\",\"sr\":\"гитара\",\"sv\":\"Gitarr\",\"szl\":null,\"tzm\":\"Agiṭaṛ\",\"uk\":\"Гітара\",\"vi\":\"Ghi-ta\",\"zh_Hans\":\"吉他\",\"zh_Hant\":\"吉他\"}},{\"number\":58,\"emoji\":\"🎺\",\"description\":\"Trumpet\",\"unicode\":\"U+1F3BA\",\"translated_descriptions\":{\"ar\":\"بُوق\",\"bg\":\"Тромпет\",\"ca\":\"Trompeta\",\"cs\":\"Trumpeta\",\"de\":\"Trompete\",\"eo\":\"Trumpeto\",\"es\":\"Trompeta\",\"et\":\"Trompet\",\"fa\":\"شیپور\",\"fi\":\"Trumpetti\",\"fr\":\"Trompette\",\"hr\":\"truba\",\"hu\":\"Trombita\",\"id\":\"Terompet\",\"it\":\"Trombetta\",\"ja\":\"トランペット\",\"nb_NO\":\"Trompet\",\"nl\":\"Trompet\",\"pt\":\"Trompete\",\"pt_BR\":\"Trombeta\",\"ru\":\"Труба\",\"si\":null,\"sk\":\"Trúbka\",\"sq\":\"Trombë\",\"sr\":\"труба\",\"sv\":\"Trumpet\",\"szl\":null,\"tzm\":null,\"uk\":\"Труба\",\"vi\":\"Kèn\",\"zh_Hans\":\"喇叭\",\"zh_Hant\":\"喇叭\"}},{\"number\":59,\"emoji\":\"🔔\",\"description\":\"Bell\",\"unicode\":\"U+1F514\",\"translated_descriptions\":{\"ar\":\"جَرَس\",\"bg\":\"Звънец\",\"ca\":\"Campana\",\"cs\":\"Zvonek\",\"de\":\"Glocke\",\"eo\":\"Sonorilo\",\"es\":\"Campana\",\"et\":\"Kelluke\",\"fa\":\"زنگ\",\"fi\":\"Soittokello\",\"fr\":\"Cloche\",\"hr\":\"zvono\",\"hu\":\"Harang\",\"id\":\"Lonceng\",\"it\":\"Campana\",\"ja\":\"ベル\",\"nb_NO\":\"Bjelle\",\"nl\":\"Bel\",\"pt\":\"Sino\",\"pt_BR\":\"Sino\",\"ru\":\"Колокол\",\"si\":null,\"sk\":\"Zvonec\",\"sq\":\"Kambanë\",\"sr\":\"звоно\",\"sv\":\"Bjällra\",\"szl\":null,\"tzm\":null,\"uk\":\"Дзвін\",\"vi\":\"Chuông\",\"zh_Hans\":\"铃铛\",\"zh_Hant\":\"鈴鐺\"}},{\"number\":60,\"emoji\":\"⚓\",\"description\":\"Anchor\",\"unicode\":\"U+2693\",\"translated_descriptions\":{\"ar\":\"مِرسَاة\",\"bg\":\"Котва\",\"ca\":\"Àncora\",\"cs\":\"Kotva\",\"de\":\"Anker\",\"eo\":\"Ankro\",\"es\":\"Ancla\",\"et\":\"Ankur\",\"fa\":\"لنگر\",\"fi\":\"Ankkuri\",\"fr\":\"Ancre\",\"hr\":\"sidro\",\"hu\":\"Horgony\",\"id\":\"Jangkar\",\"it\":\"Ancora\",\"ja\":\"いかり\",\"nb_NO\":\"Anker\",\"nl\":\"Anker\",\"pt\":\"Âncora\",\"pt_BR\":\"Âncora\",\"ru\":\"Якорь\",\"si\":null,\"sk\":\"Kotva\",\"sq\":\"Spirancë\",\"sr\":\"сидро\",\"sv\":\"Ankare\",\"szl\":null,\"tzm\":null,\"uk\":\"Якір\",\"vi\":\"Mỏ neo\",\"zh_Hans\":\"锚\",\"zh_Hant\":\"船錨\"}},{\"number\":61,\"emoji\":\"🎧\",\"description\":\"Headphones\",\"unicode\":\"U+1F3A7\",\"translated_descriptions\":{\"ar\":\"سَمّاعَة رَأس\",\"bg\":\"Слушалки\",\"ca\":\"Auriculars\",\"cs\":\"Sluchátka\",\"de\":\"Kopfhörer\",\"eo\":\"Kapaŭdilo\",\"es\":\"Cascos\",\"et\":\"Kõrvaklapid\",\"fa\":\"هدفون\",\"fi\":\"Kuulokkeet\",\"fr\":\"Casque audio\",\"hr\":\"slušalice\",\"hu\":\"Fejhallgató\",\"id\":\"Headphone\",\"it\":\"Cuffie\",\"ja\":\"ヘッドホン\",\"nb_NO\":\"Hodetelefoner\",\"nl\":\"Koptelefoon\",\"pt\":\"Fones\",\"pt_BR\":\"Fones de ouvido\",\"ru\":\"Наушники\",\"si\":null,\"sk\":\"Slúchadlá\",\"sq\":\"Kufje\",\"sr\":\"слушалице\",\"sv\":\"Hörlurar\",\"szl\":null,\"tzm\":null,\"uk\":\"Навушники\",\"vi\":\"Tai nghe\",\"zh_Hans\":\"耳机\",\"zh_Hant\":\"耳機\"}},{\"number\":62,\"emoji\":\"📁\",\"description\":\"Folder\",\"unicode\":\"U+1F4C1\",\"translated_descriptions\":{\"ar\":\"مُجَلَّد\",\"bg\":\"Папка\",\"ca\":\"Carpeta\",\"cs\":\"Složka\",\"de\":\"Ordner\",\"eo\":\"Dosierujo\",\"es\":\"Carpeta\",\"et\":\"Kaust\",\"fa\":\"پوشه\",\"fi\":\"Kansio\",\"fr\":\"Dossier\",\"hr\":\"mapu\",\"hu\":\"Mappa\",\"id\":\"Map\",\"it\":\"Cartella\",\"ja\":\"フォルダー\",\"nb_NO\":\"Mappe\",\"nl\":\"Map\",\"pt\":\"Pasta\",\"pt_BR\":\"Pasta\",\"ru\":\"Папка\",\"si\":null,\"sk\":\"Fascikel\",\"sq\":\"Dosje\",\"sr\":\"фасцикла\",\"sv\":\"Mapp\",\"szl\":null,\"tzm\":\"Asdaw\",\"uk\":\"Тека\",\"vi\":\"Thư mục\",\"zh_Hans\":\"文件夹\",\"zh_Hant\":\"資料夾\"}},{\"number\":63,\"emoji\":\"📌\",\"description\":\"Pin\",\"unicode\":\"U+1F4CC\",\"translated_descriptions\":{\"ar\":\"دَبُّوس\",\"bg\":\"Кабърче\",\"ca\":\"Xinxeta\",\"cs\":\"Špendlík\",\"de\":\"Stecknadel\",\"eo\":\"Pinglo\",\"es\":\"Alfiler\",\"et\":\"Nööpnõel\",\"fa\":\"سنجاق\",\"fi\":\"Nuppineula\",\"fr\":\"Punaise\",\"hr\":\"pribadača\",\"hu\":\"Rajszeg\",\"id\":\"Pin\",\"it\":\"Puntina\",\"ja\":\"ピン\",\"nb_NO\":\"Tegnestift\",\"nl\":\"Duimspijker\",\"pt\":\"Pionés\",\"pt_BR\":\"Alfinete\",\"ru\":\"Булавка\",\"si\":null,\"sk\":\"Špendlík\",\"sq\":\"Karficë\",\"sr\":\"чиода\",\"sv\":\"Häftstift\",\"szl\":null,\"tzm\":null,\"uk\":\"Кнопка\",\"vi\":\"Ghim\",\"zh_Hans\":\"图钉\",\"zh_Hant\":\"圖釘\"}}]`), _3 = new Map(\n  b3.map(({ emoji: e, description: t, translated_descriptions: n }) => [\n    e,\n    [\n      t,\n      // Normalize the translation keys\n      Object.keys(n).reduce((r, o) => {\n        for (const i of v1(o))\n          r[i] = n[o];\n        return r;\n      }, {})\n    ]\n  ])\n);\nfunction w3(e, t) {\n  const n = _3.get(e);\n  if (!n)\n    throw new Error(`Emoji mapping not found for emoji ${e}`);\n  const [r, o] = n;\n  for (const i of v1(t))\n    if (o[i])\n      return o[i];\n  return r;\n}\nconst E3 = \"_container_1lqqy_8\", S3 = \"_segment_1lqqy_15\", T3 = \"_emoji_1lqqy_23\", A3 = \"_label_1lqqy_29\", Jr = {\n  container: E3,\n  segment: S3,\n  emoji: T3,\n  label: A3\n};\nfunction H8({ emoji: e, className: t }) {\n  const { language: n } = Pe(), r = e.map((o, i) => /* @__PURE__ */ p.createElement(\"div\", { className: Jr.segment, key: i }, /* @__PURE__ */ p.createElement(\"div\", { className: Jr.emoji, \"aria-hidden\": !0 }, o), /* @__PURE__ */ p.createElement(\"div\", { className: Jr.label }, w3(o, n))));\n  return /* @__PURE__ */ p.createElement(\"div\", { className: pe(Jr.container, t) }, r);\n}\nconst I3 = \"_container_sq5fu_8\", j3 = \"_title_sq5fu_34\", O3 = \"_subtitle_sq5fu_35\", Ma = {\n  container: I3,\n  title: j3,\n  subtitle: O3\n};\nfunction $8({\n  icon: e,\n  title: t,\n  subtitle: n,\n  className: r,\n  children: o,\n  ref: i\n}) {\n  return /* @__PURE__ */ p.createElement(\"div\", { className: pe(Ma.container, r), ref: i }, e, /* @__PURE__ */ p.createElement(\"div\", { className: Ma.title }, t), n && /* @__PURE__ */ p.createElement(\"div\", { className: Ma.subtitle }, n), o);\n}\nfunction U8({ vm: e }) {\n  const t = me(e);\n  return /* @__PURE__ */ p.createElement(\"div\", { className: \"mx_TextualEvent\" }, t.content);\n}\nfunction C1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M12 4.5a1 1 0 0 1 1 1v10.586l4.293-4.293a1 1 0 0 1 1.414 1.414l-6 6a1 1 0 0 1-1.414 0l-6-6a1 1 0 1 1 1.414-1.414L11 16.086V5.5a1 1 0 0 1 1-1\"\n    })\n  });\n}\nC1.displayName = \"ArrowDownIcon\";\nconst P3 = $(C1);\nfunction N1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M12 22a9.7 9.7 0 0 1-3.9-.788 10.1 10.1 0 0 1-3.175-2.137q-1.35-1.35-2.137-3.175A9.7 9.7 0 0 1 2 12q0-2.075.788-3.9a10.1 10.1 0 0 1 2.137-3.175q1.35-1.35 3.175-2.137A9.7 9.7 0 0 1 12 2q2.075 0 3.9.788a10.1 10.1 0 0 1 3.175 2.137q1.35 1.35 2.137 3.175A9.7 9.7 0 0 1 22 12a9.7 9.7 0 0 1-.788 3.9 10.1 10.1 0 0 1-2.137 3.175q-1.35 1.35-3.175 2.137A9.7 9.7 0 0 1 12 22m0-2q3.35 0 5.675-2.325T20 12q0-1.35-.437-2.6A8 8 0 0 0 18.3 7.1L7.1 18.3q1.05.825 2.3 1.262T12 20m-6.3-3.1L16.9 5.7a8 8 0 0 0-2.3-1.263A7.8 7.8 0 0 0 12 4Q8.65 4 6.325 6.325T4 12q0 1.35.438 2.6A8 8 0 0 0 5.7 16.9\"\n    })\n  });\n}\nN1.displayName = \"BlockIcon\";\nconst Ef = $(N1);\nfunction x1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"m1.5 21.25 1.45-4.95a10.2 10.2 0 0 1-.712-2.1A10.2 10.2 0 0 1 2 12q0-2.075.788-3.9a10.1 10.1 0 0 1 2.137-3.175q1.35-1.35 3.175-2.137A9.7 9.7 0 0 1 12 2q2.075 0 3.9.788a10.1 10.1 0 0 1 3.175 2.137q1.35 1.35 2.137 3.175A9.7 9.7 0 0 1 22 12a9.7 9.7 0 0 1-.788 3.9 10.1 10.1 0 0 1-2.137 3.175q-1.35 1.35-3.175 2.137A9.7 9.7 0 0 1 12 22q-1.125 0-2.2-.238a10.2 10.2 0 0 1-2.1-.712L2.75 22.5a.94.94 0 0 1-1-.25.94.94 0 0 1-.25-1m2.45-1.2 3.2-.95a1 1 0 0 1 .275-.062q.15-.013.275-.013.225 0 .438.038.212.036.412.137a7.4 7.4 0 0 0 1.675.6Q11.1 20 12 20q3.35 0 5.675-2.325T20 12t-2.325-5.675T12 4 6.325 6.325 4 12q0 .9.2 1.775t.6 1.675q.176.325.188.688t-.088.712z\"\n    })\n  });\n}\nx1.displayName = \"ChatIcon\";\nconst z1 = $(x1);\nfunction B1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M9.55 17.575q-.2 0-.375-.062a.9.9 0 0 1-.325-.213L4.55 13q-.274-.274-.262-.713.012-.437.287-.712a.95.95 0 0 1 .7-.275q.425 0 .7.275L9.55 15.15l8.475-8.475q.274-.275.713-.275.437 0 .712.275.275.274.275.713 0 .437-.275.712l-9.2 9.2q-.15.15-.325.212a1.1 1.1 0 0 1-.375.063\"\n    })\n  });\n}\nB1.displayName = \"CheckIcon\";\nconst F1 = $(B1);\nfunction D1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M12 14.95q-.2 0-.375-.062a.9.9 0 0 1-.325-.213l-4.6-4.6a.95.95 0 0 1-.275-.7q0-.425.275-.7a.95.95 0 0 1 .7-.275q.425 0 .7.275l3.9 3.9 3.9-3.9a.95.95 0 0 1 .7-.275q.425 0 .7.275a.95.95 0 0 1 .275.7.95.95 0 0 1-.275.7l-4.6 4.6q-.15.15-.325.212a1.1 1.1 0 0 1-.375.063\"\n    })\n  });\n}\nD1.displayName = \"ChevronDownIcon\";\nconst q1 = $(D1);\nfunction L1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M6.293 6.293a1 1 0 0 1 1.414 0L12 10.586l4.293-4.293a1 1 0 1 1 1.414 1.414L13.414 12l4.293 4.293a1 1 0 0 1-1.414 1.414L12 13.414l-4.293 4.293a1 1 0 0 1-1.414-1.414L10.586 12 6.293 7.707a1 1 0 0 1 0-1.414\"\n    })\n  });\n}\nL1.displayName = \"CloseIcon\";\nconst k3 = $(L1);\nfunction H1(e, t) {\n  return /* @__PURE__ */ R.jsxs(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: [/* @__PURE__ */ R.jsx(\"path\", {\n      fillRule: \"evenodd\",\n      d: \"M16.937 2.82a2 2 0 0 1 2.828 0l1.415 1.414a2 2 0 0 1 0 2.829l-7.071 7.07c-.195.196-.42.342-.66.44a1 1 0 0 1-.168.072l-3.993 1.331a1 1 0 0 1-1.265-1.265l1.331-3.992q.03-.09.073-.168m10.338-4.903-6.717 6.718-1.414-1.414 6.717-6.718z\",\n      clipRule: \"evenodd\"\n    }), /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M3 5a2 2 0 0 1 2-2h6a1 1 0 1 1 0 2H5v14h14v-6a1 1 0 1 1 2 0v6a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2z\"\n    })]\n  });\n}\nH1.displayName = \"ComposeIcon\";\nconst $1 = $(H1);\nfunction U1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M7 21q-.824 0-1.412-.587A1.93 1.93 0 0 1 5 19V6a.97.97 0 0 1-.713-.287A.97.97 0 0 1 4 5q0-.424.287-.713A.97.97 0 0 1 5 4h4q0-.424.287-.712A.97.97 0 0 1 10 3h4q.424 0 .713.288Q15 3.575 15 4h4q.424 0 .712.287Q20 4.576 20 5t-.288.713A.97.97 0 0 1 19 6v13q0 .824-.587 1.413A1.93 1.93 0 0 1 17 21zM7 6v13h10V6zm2 10q0 .424.287.712Q9.576 17 10 17t.713-.288A.97.97 0 0 0 11 16V9a.97.97 0 0 0-.287-.713A.97.97 0 0 0 10 8a.97.97 0 0 0-.713.287A.97.97 0 0 0 9 9zm4 0q0 .424.287.712.288.288.713.288.424 0 .713-.288A.97.97 0 0 0 15 16V9a.97.97 0 0 0-.287-.713A.97.97 0 0 0 14 8a.97.97 0 0 0-.713.287A.97.97 0 0 0 13 9z\"\n    })\n  });\n}\nU1.displayName = \"DeleteIcon\";\nconst R3 = $(U1);\nfunction K1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M12 18.6c-.99 0-1.8.81-1.8 1.8s.81 1.8 1.8 1.8 1.8-.81 1.8-1.8-.81-1.8-1.8-1.8M6.6 2.4c-.99 0-1.8.81-1.8 1.8S5.61 6 6.6 6s1.8-.81 1.8-1.8-.81-1.8-1.8-1.8m0 5.4c-.99 0-1.8.81-1.8 1.8s.81 1.8 1.8 1.8 1.8-.81 1.8-1.8-.81-1.8-1.8-1.8m0 5.4c-.99 0-1.8.81-1.8 1.8s.81 1.8 1.8 1.8 1.8-.81 1.8-1.8-.81-1.8-1.8-1.8M17.4 6c.99 0 1.8-.81 1.8-1.8s-.81-1.8-1.8-1.8-1.8.81-1.8 1.8.81 1.8 1.8 1.8M12 13.2c-.99 0-1.8.81-1.8 1.8s.81 1.8 1.8 1.8 1.8-.81 1.8-1.8-.81-1.8-1.8-1.8m5.4 0c-.99 0-1.8.81-1.8 1.8s.81 1.8 1.8 1.8 1.8-.81 1.8-1.8-.81-1.8-1.8-1.8m0-5.4c-.99 0-1.8.81-1.8 1.8s.81 1.8 1.8 1.8 1.8-.81 1.8-1.8-.81-1.8-1.8-1.8m-5.4 0c-.99 0-1.8.81-1.8 1.8s.81 1.8 1.8 1.8 1.8-.81 1.8-1.8-.81-1.8-1.8-1.8m0-5.4c-.99 0-1.8.81-1.8 1.8S11.01 6 12 6s1.8-.81 1.8-1.8-.81-1.8-1.8-1.8\"\n    })\n  });\n}\nK1.displayName = \"DialPadIcon\";\nconst M3 = $(K1);\nfunction G1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M4 4h16a2 2 0 0 1 2 2v12a2 2 0 0 1-2 2H4a2 2 0 0 1-2-2V6a2 2 0 0 1 2-2m0 5.111a1 1 0 0 0 .514.874l7 3.89a1 1 0 0 0 .972 0l7-3.89a1 1 0 1 0-.972-1.748L12 11.856 5.486 8.237A1 1 0 0 0 4 9.111\"\n    })\n  });\n}\nG1.displayName = \"EmailSolidIcon\";\nconst C3 = $(G1);\nfunction V1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M12 13a.97.97 0 0 1-.713-.287A.97.97 0 0 1 11 12q0-.424.287-.713A.97.97 0 0 1 12 11q.424 0 .713.287.287.288.287.713 0 .424-.287.713A.97.97 0 0 1 12 13m0 9a9.7 9.7 0 0 1-3.9-.788 10.1 10.1 0 0 1-3.175-2.137q-1.35-1.35-2.137-3.175A9.7 9.7 0 0 1 2 12q0-2.075.788-3.9a10.1 10.1 0 0 1 2.137-3.175q1.35-1.35 3.175-2.137A9.7 9.7 0 0 1 12 2q2.075 0 3.9.788a10.1 10.1 0 0 1 3.175 2.137q1.35 1.35 2.137 3.175A9.7 9.7 0 0 1 22 12a9.7 9.7 0 0 1-.788 3.9 10.1 10.1 0 0 1-2.137 3.175q-1.35 1.35-3.175 2.137A9.7 9.7 0 0 1 12 22m0-2q3.35 0 5.675-2.325T20 12t-2.325-5.675T12 4 6.325 6.325 4 12t2.325 5.675T12 20m0 0q-3.35 0-5.675-2.325T4 12t2.325-5.675T12 4t5.675 2.325T20 12t-2.325 5.675T12 20m1.675-5.85q.15-.075.275-.2t.2-.275l2.925-6.25q.125-.25-.062-.437-.188-.188-.438-.063l-6.25 2.925q-.15.075-.275.2t-.2.275l-2.925 6.25q-.125.25.063.438.186.186.437.062z\"\n    })\n  });\n}\nV1.displayName = \"ExploreIcon\";\nconst N3 = $(V1);\nfunction Y1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M13.905 9.378 12 5.52l-1.905 3.86-4.259.618 3.082 3.004-.727 4.242L12 15.24l3.81 2.003-.728-4.242 3.082-3.004zM8.767 7.55l2.336-4.733a1 1 0 0 1 1.794 0l2.336 4.733 5.223.76a1 1 0 0 1 .555 1.705L17.23 13.7l.892 5.202a1 1 0 0 1-1.45 1.054L12 17.5l-4.672 2.456a1 1 0 0 1-1.451-1.054l.892-5.202-3.78-3.685a1 1 0 0 1 .555-1.706z\"\n    })\n  });\n}\nY1.displayName = \"FavouriteIcon\";\nconst x3 = $(Y1);\nfunction W1(e, t) {\n  return /* @__PURE__ */ R.jsxs(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: [/* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M18.93 8A8 8 0 1 1 4 12a1 1 0 1 0-2 0c0 5.523 4.477 10 10 10s10-4.477 10-10a10 10 0 0 0-.832-4A10 10 0 0 0 12 2a9.99 9.99 0 0 0-8 3.999V4a1 1 0 0 0-2 0v4a1 1 0 0 0 1 1h4a1 1 0 0 0 0-2H5.755A7.99 7.99 0 0 1 12 4a8 8 0 0 1 6.93 4\"\n    }), /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M13 8a1 1 0 1 0-2 0v4a1 1 0 0 0 .293.707l2.83 2.83a1 1 0 0 0 1.414-1.414L13 11.586z\"\n    })]\n  });\n}\nW1.displayName = \"HistoryIcon\";\nconst z3 = $(W1);\nfunction Z1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      fillRule: \"evenodd\",\n      d: \"M16 11v8h3V9.177l-7-3.889-7 3.889V19h3v-8zm-6 10H5a2 2 0 0 1-2-2V9.177a2 2 0 0 1 1.029-1.748l7-3.89a2 2 0 0 1 1.942 0l7 3.89A2 2 0 0 1 21 9.177V19a2 2 0 0 1-2 2h-5v-8h-4z\",\n      clipRule: \"evenodd\"\n    })\n  });\n}\nZ1.displayName = \"HomeIcon\";\nconst B3 = $(Z1);\nfunction J1(e, t) {\n  return /* @__PURE__ */ R.jsxs(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: [/* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M14 13q.424 0 .713-.287A.97.97 0 0 0 15 12a.97.97 0 0 0-.287-.713A.97.97 0 0 0 14 11a.97.97 0 0 0-.713.287A.97.97 0 0 0 13 12q0 .424.287.713.288.287.713.287\"\n    }), /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M10.385 21.788A1 1 0 0 1 10 21V3a1.003 1.003 0 0 1 1.242-.97l8 2A1 1 0 0 1 20 5v14a1 1 0 0 1-.758.97l-8 2a1 1 0 0 1-.857-.182M18 5.781l-6-1.5v15.438l6-1.5zM9 6H7v12h2v2H7a2 2 0 0 1-2-2V6a2 2 0 0 1 2-2h2z\"\n    })]\n  });\n}\nJ1.displayName = \"LeaveIcon\";\nconst F3 = $(J1);\nfunction Q1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M12 19.071q-1.467 1.467-3.536 1.467-2.067 0-3.535-1.467t-1.467-3.535q0-2.07 1.467-3.536L7.05 9.879q.3-.3.707-.3t.707.3.301.707-.3.707l-2.122 2.121a2.9 2.9 0 0 0-.884 2.122q0 1.237.884 2.12.884.885 2.121.885t2.122-.884l2.121-2.121q.3-.3.707-.3t.707.3.3.707q0 .405-.3.707zm-1.414-4.243q-.3.3-.707.301a.97.97 0 0 1-.707-.3q-.3-.3-.301-.708 0-.405.3-.707l4.243-4.242q.3-.3.707-.3t.707.3.3.707-.3.707zm6.364-.707q-.3.3-.707.3a.97.97 0 0 1-.707-.3q-.3-.3-.301-.707 0-.405.3-.707l2.122-2.121q.884-.885.884-2.121 0-1.238-.884-2.122a2.9 2.9 0 0 0-2.121-.884q-1.237 0-2.122.884l-2.121 2.122q-.3.3-.707.3a.97.97 0 0 1-.707-.3q-.3-.3-.3-.708 0-.405.3-.707L12 4.93q1.467-1.467 3.536-1.467t3.535 1.467 1.467 3.536T19.071 12z\"\n    })\n  });\n}\nQ1.displayName = \"LinkIcon\";\nconst D3 = $(Q1);\nfunction X1(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M21.324 9.13c0-.66-.339-1.237-.862-1.558l-7.37-4.318a1.81 1.81 0 0 0-1.851 0L3.87 7.572C3.348 7.892 3 8.47 3 9.13v9.167c0 1.008.825 1.833 1.833 1.833H19.5a1.84 1.84 0 0 0 1.833-1.833zm-10.129 3.978-6.6-4.124 6.646-3.896a1.81 1.81 0 0 1 1.851 0l6.646 3.896-6.6 4.124a1.85 1.85 0 0 1-1.943 0\"\n    })\n  });\n}\nX1.displayName = \"MarkAsReadIcon\";\nconst q3 = $(X1);\nfunction eh(e, t) {\n  return /* @__PURE__ */ R.jsxs(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: [/* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M20 7a2 2 0 1 0 0-4 2 2 0 0 0 0 4\"\n    }), /* @__PURE__ */ R.jsx(\"path\", {\n      fillRule: \"evenodd\",\n      d: \"M17 5H5a2 2 0 0 0-2 2v10.4a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2V7.83a3 3 0 0 1-2 0q-.316-.113-.595-.288L12 11.89 5 7.138V7h12.764A3 3 0 0 1 17 5m-4.438 8.927L19 9.555V17.4H5V9.555l6.438 4.372a1 1 0 0 0 1.124 0\",\n      clipRule: \"evenodd\"\n    })]\n  });\n}\neh.displayName = \"MarkAsUnreadIcon\";\nconst L3 = $(eh);\nfunction th(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M12 4a8 8 0 1 0 0 16 1 1 0 1 1 0 2C6.477 22 2 17.523 2 12S6.477 2 12 2s10 4.477 10 10v1.5a3.5 3.5 0 0 1-6.396 1.966A5 5 0 1 1 17 12v1.5a1.5 1.5 0 0 0 3 0V12a8 8 0 0 0-8-8m3 8a3 3 0 1 0-6 0 3 3 0 0 0 6 0\"\n    })\n  });\n}\nth.displayName = \"MentionIcon\";\nconst H3 = $(th);\nfunction nh(e, t) {\n  return /* @__PURE__ */ R.jsxs(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: [/* @__PURE__ */ R.jsx(\"path\", {\n      d: \"m4.917 2.083 17 17a1 1 0 0 1-1.414 1.414L19.006 19H4.414c-.89 0-1.337-1.077-.707-1.707L5 16v-6s0-2.034 1.096-3.91L3.504 3.498a1 1 0 0 1 1.414-1.414M19 13.35 9.136 3.484C9.93 3.181 10.874 3 12 3c7 0 7 7 7 7z\"\n    }), /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M10 20h4a2 2 0 0 1-4 0\"\n    })]\n  });\n}\nnh.displayName = \"NotificationsOffSolidIcon\";\nconst rh = $(nh);\nfunction oh(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M20.293 17.293c.63.63.184 1.707-.707 1.707H4.414c-.89 0-1.337-1.077-.707-1.707L5 16v-6s0-7 7-7 7 7 7 7v6zM12 22a2 2 0 0 1-2-2h4a2 2 0 0 1-2 2\"\n    })\n  });\n}\noh.displayName = \"NotificationsSolidIcon\";\nconst $3 = $(oh);\nfunction ih(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M6 14q-.824 0-1.412-.588A1.93 1.93 0 0 1 4 12q0-.825.588-1.412A1.93 1.93 0 0 1 6 10q.824 0 1.412.588Q8 11.175 8 12t-.588 1.412A1.93 1.93 0 0 1 6 14m6 0q-.825 0-1.412-.588A1.93 1.93 0 0 1 10 12q0-.825.588-1.412A1.93 1.93 0 0 1 12 10q.825 0 1.412.588Q14 11.175 14 12t-.588 1.412A1.93 1.93 0 0 1 12 14m6 0q-.824 0-1.413-.588A1.93 1.93 0 0 1 16 12q0-.825.587-1.412A1.93 1.93 0 0 1 18 10q.824 0 1.413.588Q20 11.175 20 12t-.587 1.412A1.93 1.93 0 0 1 18 14\"\n    })\n  });\n}\nih.displayName = \"OverflowHorizontalIcon\";\nconst Fc = $(ih);\nfunction ah(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      fillRule: \"evenodd\",\n      d: \"M6.5 2h11a4.5 4.5 0 1 1 0 9h-11a4.5 4.5 0 0 1 0-9m0 2h7.258A4.5 4.5 0 0 0 13 6.5c0 .925.28 1.785.758 2.5H6.5a2.5 2.5 0 0 1 0-5M15 6.5a2.5 2.5 0 1 1 5 0 2.5 2.5 0 0 1-5 0m-13 11A4.5 4.5 0 0 1 6.5 13h11a4.5 4.5 0 1 1 0 9h-11q-.233 0-.46-.023A4.5 4.5 0 0 1 2 17.5m8.242-2.5H17.5a2.5 2.5 0 0 1 0 5h-7.258A4.5 4.5 0 0 0 11 17.5c0-.925-.28-1.785-.758-2.5M6.5 15a2.5 2.5 0 1 0 0 5 2.5 2.5 0 0 0 0-5\",\n      clipRule: \"evenodd\"\n    })\n  });\n}\nah.displayName = \"PreferencesIcon\";\nconst U3 = $(ah);\nfunction sh(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M18.93 8A8 8 0 1 1 4 12a1 1 0 1 0-2 0c0 5.523 4.477 10 10 10s10-4.477 10-10a10 10 0 0 0-.832-4A10 10 0 0 0 12 2a9.99 9.99 0 0 0-8 3.999V4a1 1 0 0 0-2 0v4a1 1 0 0 0 1 1h4a1 1 0 0 0 0-2H5.755A7.99 7.99 0 0 1 12 4a8 8 0 0 1 6.93 4\"\n    })\n  });\n}\nsh.displayName = \"RestartIcon\";\nconst Sf = $(sh);\nfunction ch(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"m8.566 17-.944 4.094q-.086.406-.372.656t-.687.25q-.543 0-.887-.469a1.18 1.18 0 0 1-.2-1.031l.801-3.5H3.158q-.572 0-.916-.484a1.27 1.27 0 0 1-.2-1.078 1.12 1.12 0 0 1 1.116-.938H6.85l1.145-5h-3.12q-.57 0-.915-.484a1.27 1.27 0 0 1-.2-1.078A1.12 1.12 0 0 1 4.875 7h3.691l.945-4.094q.085-.406.372-.656.286-.25.686-.25.544 0 .887.469.345.468.2 1.031l-.8 3.5h4.578l.944-4.094q.085-.406.372-.656.286-.25.687-.25.543 0 .887.469t.2 1.031L17.723 7h3.119q.573 0 .916.484.343.485.2 1.079a1.12 1.12 0 0 1-1.116.937H17.15l-1.145 5h3.12q.57 0 .915.484.343.485.2 1.079a1.12 1.12 0 0 1-1.116.937h-3.691l-.944 4.094q-.087.406-.373.656t-.686.25q-.544 0-.887-.469a1.18 1.18 0 0 1-.2-1.031l.8-3.5zm.573-2.5h4.578l1.144-5h-4.578z\"\n    })\n  });\n}\nch.displayName = \"RoomIcon\";\nconst lh = $(ch);\nfunction uh(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M15.05 16.463a7.5 7.5 0 1 1 1.414-1.414l3.243 3.244a1 1 0 0 1-1.414 1.414zM16 10.5a5.5 5.5 0 1 0-11 0 5.5 5.5 0 0 0 11 0\"\n    })\n  });\n}\nuh.displayName = \"SearchIcon\";\nconst K3 = $(uh);\nfunction fh(e, t) {\n  return /* @__PURE__ */ R.jsxs(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: [/* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M16 12a4 4 0 1 1-8 0 4 4 0 0 1 8 0m-2 0a2 2 0 1 0-4 0 2 2 0 0 0 4 0\"\n    }), /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M11.312 2h1.376A2.31 2.31 0 0 1 15 4.312v.247l.002.003c.01.014.031.033.064.047.03.013.056.013.07.01h.002l.177-.177a2.31 2.31 0 0 1 3.27 0l.973.974a2.31 2.31 0 0 1 0 3.269l-.177.177v.003a.13.13 0 0 0 .01.07.15.15 0 0 0 .047.063l.003.002h.247A2.31 2.31 0 0 1 22 11.312v1.376A2.31 2.31 0 0 1 19.688 15h-.247l-.003.002a.15.15 0 0 0-.047.064.13.13 0 0 0-.01.07v.002l.177.177a2.31 2.31 0 0 1 0 3.27l-.974.973a2.31 2.31 0 0 1-3.269 0l-.177-.177h-.003a.13.13 0 0 0-.07.01.15.15 0 0 0-.063.047l-.002.003v.247A2.31 2.31 0 0 1 12.688 22h-1.376A2.31 2.31 0 0 1 9 19.688v-.247l-.002-.003a.15.15 0 0 0-.064-.047.13.13 0 0 0-.07-.01h-.002l-.177.177a2.31 2.31 0 0 1-3.27 0l-.973-.974a2.31 2.31 0 0 1 0-3.269l.177-.177v-.003a.14.14 0 0 0-.01-.07.15.15 0 0 0-.047-.063L4.559 15h-.247A2.31 2.31 0 0 1 2 12.688v-1.376A2.31 2.31 0 0 1 4.312 9h.247l.003-.002a.15.15 0 0 0 .047-.064.14.14 0 0 0 .01-.07v-.002l-.177-.177a2.31 2.31 0 0 1 0-3.27l.974-.973a2.31 2.31 0 0 1 3.269 0l.177.177h.003a.14.14 0 0 0 .07-.01.15.15 0 0 0 .063-.047L9 4.559v-.247A2.31 2.31 0 0 1 11.312 2M11 4.312v.257c0 .893-.59 1.593-1.299 1.887-.716.297-1.622.21-2.248-.418l-.182-.182a.31.31 0 0 0-.441 0l-.974.974a.31.31 0 0 0 0 .44l.182.183c.627.626.715 1.531.418 2.248C6.162 10.41 5.462 11 4.569 11h-.257a.31.31 0 0 0-.312.312v1.376c0 .172.14.312.312.312h.257c.893 0 1.593.59 1.887 1.299.297.716.21 1.622-.418 2.248l-.182.182a.31.31 0 0 0 0 .441l.974.973a.31.31 0 0 0 .44 0l.183-.181c.626-.627 1.532-.715 2.248-.418.709.294 1.299.994 1.299 1.887v.257c0 .172.14.312.312.312h1.376c.172 0 .312-.14.312-.312v-.257c0-.893.59-1.593 1.299-1.887.716-.297 1.622-.21 2.249.418l.181.181c.122.122.32.122.441 0l.973-.973a.31.31 0 0 0 0-.44l-.181-.183c-.627-.626-.715-1.532-.418-2.248.294-.709.994-1.299 1.887-1.299h.257c.172 0 .312-.14.312-.312v-1.376a.31.31 0 0 0-.312-.312h-.257c-.893 0-1.593-.59-1.887-1.299-.297-.717-.21-1.622.418-2.248l.181-.182a.31.31 0 0 0 0-.441l-.973-.974a.31.31 0 0 0-.44 0l-.183.182c-.626.627-1.532.715-2.248.418C13.59 6.162 13 5.462 13 4.569v-.257A.31.31 0 0 0 12.688 4h-1.376a.31.31 0 0 0-.312.312\"\n    })]\n  });\n}\nfh.displayName = \"SettingsIcon\";\nconst G3 = $(fh);\nfunction dh(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M10 12q-1.65 0-2.825-1.175T6 8t1.175-2.825T10 4t2.825 1.175T14 8t-1.175 2.825T10 12m-8 6v-.8q0-.85.438-1.562.437-.713 1.162-1.088a14.8 14.8 0 0 1 3.15-1.163A13.8 13.8 0 0 1 10 13q1.65 0 3.25.387 1.6.388 3.15 1.163.724.375 1.163 1.087Q18 16.35 18 17.2v.8q0 .824-.587 1.413A1.93 1.93 0 0 1 16 20H4q-.824 0-1.412-.587A1.93 1.93 0 0 1 2 18m2 0h12v-.8a.97.97 0 0 0-.5-.85q-1.35-.675-2.725-1.012a11.6 11.6 0 0 0-5.55 0Q5.85 15.675 4.5 16.35a.97.97 0 0 0-.5.85zm6-8q.825 0 1.412-.588Q12 8.826 12 8q0-.824-.588-1.412A1.93 1.93 0 0 0 10 6q-.825 0-1.412.588A1.93 1.93 0 0 0 8 8q0 .825.588 1.412Q9.175 10 10 10m7 1h2v2q0 .424.288.713.287.287.712.287.424 0 .712-.287A.97.97 0 0 0 21 13v-2h2q.424 0 .712-.287A.97.97 0 0 0 24 10a.97.97 0 0 0-.288-.713A.97.97 0 0 0 23 9h-2V7a.97.97 0 0 0-.288-.713A.97.97 0 0 0 20 6a.97.97 0 0 0-.712.287A.97.97 0 0 0 19 7v2h-2a.97.97 0 0 0-.712.287A.97.97 0 0 0 16 10q0 .424.288.713.287.287.712.287\"\n    })\n  });\n}\ndh.displayName = \"UserAddIcon\";\nconst ph = $(dh);\nfunction hh(e, t) {\n  return /* @__PURE__ */ R.jsxs(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: [/* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M12 15q-1.65 0-2.825-1.175T8 11t1.175-2.825T12 7t2.825 1.175T16 11t-1.175 2.825T12 15\"\n    }), /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M19.528 18.583A9.96 9.96 0 0 0 22 12c0-5.523-4.477-10-10-10S2 6.477 2 12c0 2.52.933 4.824 2.472 6.583A9.98 9.98 0 0 0 12 22a9.98 9.98 0 0 0 7.528-3.417M8.75 16.388q-1.373.332-2.709.95a8 8 0 1 1 11.918 0 14.7 14.7 0 0 0-2.709-.95A13.8 13.8 0 0 0 12 16q-1.65 0-3.25.387\"\n    })]\n  });\n}\nhh.displayName = \"UserProfileSolidIcon\";\nconst V3 = $(hh);\nfunction mh(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M6 4h10a2 2 0 0 1 2 2v4.286l3.35-2.871a1 1 0 0 1 1.65.76v7.65a1 1 0 0 1-1.65.76L18 13.715V18a2 2 0 0 1-2 2H6a4 4 0 0 1-4-4V8a4 4 0 0 1 4-4\"\n    })\n  });\n}\nmh.displayName = \"VideoCallSolidIcon\";\nconst Y3 = $(mh);\nfunction gh(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"M2 8a4 4 0 0 1 4-4h10a2 2 0 0 1 2 2v4.286l3.35-2.871a1 1 0 0 1 1.65.76v7.65a1 1 0 0 1-1.65.76L18 13.715V18a2 2 0 0 1-2 2H6a4 4 0 0 1-4-4zm4-2a2 2 0 0 0-2 2v8a2 2 0 0 0 2 2h10V6zm15 7.652v-3.303L19.073 12z\"\n    })\n  });\n}\ngh.displayName = \"VideoCallIcon\";\nconst W3 = $(gh);\nfunction yh(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"m16.1 13.3-1.45-1.45q.225-1.175-.675-2.2t-2.325-.8L10.2 7.4q.424-.2.863-.3A4.2 4.2 0 0 1 12 7q1.875 0 3.188 1.312Q16.5 9.625 16.5 11.5q0 .5-.1.938t-.3.862m3.2 3.15-1.45-1.4a11 11 0 0 0 1.688-1.588A9 9 0 0 0 20.8 11.5q-1.25-2.524-3.588-4.013Q14.875 6 12 6q-.724 0-1.425.1a10 10 0 0 0-1.375.3L7.65 4.85A11.1 11.1 0 0 1 12 4q3.575 0 6.425 1.887T22.7 10.8a.8.8 0 0 1 .1.313q.025.188.025.387a2 2 0 0 1-.125.7 10.9 10.9 0 0 1-3.4 4.25m-.2 5.45-3.5-3.45q-.874.274-1.762.413Q12.95 19 12 19q-3.575 0-6.425-1.887T1.3 12.2a.8.8 0 0 1-.1-.312 3 3 0 0 1 0-.763.8.8 0 0 1 .1-.3Q1.825 9.7 2.55 8.75A13.3 13.3 0 0 1 4.15 7L2.075 4.9a.93.93 0 0 1-.275-.688q0-.412.3-.712a.95.95 0 0 1 .7-.275q.425 0 .7.275l17 17q.275.275.288.688a.93.93 0 0 1-.288.712.95.95 0 0 1-.7.275.95.95 0 0 1-.7-.275M5.55 8.4q-.725.65-1.325 1.425A9 9 0 0 0 3.2 11.5q1.25 2.524 3.588 4.012T12 17q.5 0 .975-.062.475-.063.975-.138l-.9-.95q-.274.075-.525.113A3.5 3.5 0 0 1 12 16q-1.875 0-3.187-1.312Q7.5 13.375 7.5 11.5q0-.274.038-.525.037-.25.112-.525z\"\n    })\n  });\n}\nyh.displayName = \"VisibilityOffIcon\";\nconst Z3 = $(yh);\nfunction vh(e, t) {\n  return /* @__PURE__ */ R.jsx(\"svg\", {\n    xmlns: \"http://www.w3.org/2000/svg\",\n    width: \"1em\",\n    height: \"1em\",\n    fill: \"currentColor\",\n    viewBox: \"0 0 24 24\",\n    ref: t,\n    ...e,\n    children: /* @__PURE__ */ R.jsx(\"path\", {\n      d: \"m20.958 16.374.039 3.527q0 .427-.33.756-.33.33-.756.33a16 16 0 0 1-6.57-1.105 16.2 16.2 0 0 1-5.563-3.663 16.1 16.1 0 0 1-3.653-5.573 16.3 16.3 0 0 1-1.115-6.56q0-.427.33-.757T4.095 3l3.528.039a1.07 1.07 0 0 1 1.085.93l.543 3.954q.039.271-.039.504a1.1 1.1 0 0 1-.271.426l-1.64 1.64q.505 1.008 1.154 1.909c.433.6 1.444 1.696 1.444 1.696s1.095 1.01 1.696 1.444q.9.65 1.909 1.153l1.64-1.64q.193-.193.426-.27t.504-.04l3.954.543q.406.059.668.359t.262.727\"\n    })\n  });\n}\nvh.displayName = \"VoiceCallSolidIcon\";\nconst J3 = $(vh), Q3 = \"_content_1uqu1_8\", X3 = \"_error_1uqu1_14\", eE = \"_icon_1uqu1_23\", So = {\n  content: Q3,\n  error: X3,\n  icon: eE\n};\nvar tE = /* @__PURE__ */ ((e) => (e.MEGOLM_KEY_WITHHELD_FOR_UNVERIFIED_DEVICE = \"MEGOLM_KEY_WITHHELD_FOR_UNVERIFIED_DEVICE\", e.HISTORICAL_MESSAGE_NO_KEY_BACKUP = \"HISTORICAL_MESSAGE_NO_KEY_BACKUP\", e.HISTORICAL_MESSAGE_BACKUP_UNCONFIGURED = \"HISTORICAL_MESSAGE_BACKUP_UNCONFIGURED\", e.HISTORICAL_MESSAGE_USER_NOT_JOINED = \"HISTORICAL_MESSAGE_USER_NOT_JOINED\", e.SENDER_IDENTITY_PREVIOUSLY_VERIFIED = \"SENDER_IDENTITY_PREVIOUSLY_VERIFIED\", e.UNSIGNED_SENDER_DEVICE = \"UNSIGNED_SENDER_DEVICE\", e.UNABLE_TO_DECRYPT = \"UNABLE_TO_DECRYPT\", e))(tE || {});\nfunction nE(e, t, n) {\n  const r = e.translate;\n  switch (t) {\n    case \"MEGOLM_KEY_WITHHELD_FOR_UNVERIFIED_DEVICE\":\n      return r(\"timeline|decryption_failure|blocked\");\n    case \"HISTORICAL_MESSAGE_NO_KEY_BACKUP\":\n      return r(\"timeline|decryption_failure|historical_event_no_key_backup\");\n    case \"HISTORICAL_MESSAGE_BACKUP_UNCONFIGURED\":\n      if (n === !1)\n        return r(\"timeline|decryption_failure|historical_event_unverified_device\");\n      break;\n    case \"HISTORICAL_MESSAGE_USER_NOT_JOINED\":\n      return r(\"timeline|decryption_failure|historical_event_user_not_joined\");\n    case \"SENDER_IDENTITY_PREVIOUSLY_VERIFIED\":\n      return /* @__PURE__ */ p.createElement(\"span\", null, /* @__PURE__ */ p.createElement(Ef, { className: So.icon, width: \"16px\", height: \"16px\" }), r(\"timeline|decryption_failure|sender_identity_previously_verified\"));\n    case \"UNSIGNED_SENDER_DEVICE\":\n      return /* @__PURE__ */ p.createElement(\"span\", null, /* @__PURE__ */ p.createElement(Ef, { className: So.icon, width: \"16px\", height: \"16px\" }), r(\"timeline|decryption_failure|sender_unsigned_device\"));\n  }\n  return r(\"timeline|decryption_failure|unable_to_decrypt\");\n}\nfunction rE(e) {\n  switch (e) {\n    case \"SENDER_IDENTITY_PREVIOUSLY_VERIFIED\":\n    case \"UNSIGNED_SENDER_DEVICE\":\n      return So.error;\n  }\n  return null;\n}\nfunction K8({ vm: e, ref: t }) {\n  const n = Pe(), { decryptionFailureReason: r, isLocalDeviceVerified: o, extraClassNames: i } = me(e), a = pe(So.content, rE(r), i);\n  return /* @__PURE__ */ p.createElement(\"div\", { className: a, ref: t }, nE(n, r, o));\n}\nfunction G8({\n  vm: e,\n  children: t\n}) {\n  const { formattedSenders: n, caption: r, tooltipOpen: o } = me(e);\n  return n ? /* @__PURE__ */ p.createElement(Ih, { description: n, caption: r, placement: \"right\", open: o }, t) : /* @__PURE__ */ p.createElement(p.Fragment, null, t);\n}\nconst oE = \"_timelineSeparator_yq5ye_8\", iE = {\n  timelineSeparator: oE\n}, V8 = ({ label: e, className: t, children: n }) => /* @__PURE__ */ p.createElement(\n  Q,\n  {\n    className: pe(t, iE.timelineSeparator),\n    role: \"separator\",\n    \"aria-label\": e,\n    align: \"center\"\n  },\n  /* @__PURE__ */ p.createElement(\"hr\", { role: \"none\" }),\n  n,\n  /* @__PURE__ */ p.createElement(\"hr\", { role: \"none\" })\n), aE = \"_pill_1i8jm_8\", sE = \"_label_1i8jm_14\", Tf = {\n  pill: aE,\n  label: sE\n};\nfunction Y8({ className: e, children: t, label: n, onClick: r, ...o }) {\n  const i = To(), { translate: a } = Pe();\n  return /* @__PURE__ */ p.createElement(\n    Q,\n    {\n      display: \"inline-flex\",\n      gap: \"var(--cpd-space-1-5x)\",\n      align: \"center\",\n      className: pe(Tf.pill, e),\n      ...o\n    },\n    t,\n    /* @__PURE__ */ p.createElement(\"span\", { id: i, className: Tf.label }, n),\n    r && /* @__PURE__ */ p.createElement(\n      ft,\n      {\n        \"aria-describedby\": i,\n        size: \"16px\",\n        onClick: r,\n        \"aria-label\": a(\"action|delete\"),\n        className: \"mx_Dialog_nonDialogButton\"\n      },\n      /* @__PURE__ */ p.createElement(k3, null)\n    )\n  );\n}\nfunction cE(e) {\n  return (t) => {\n    for (const n of e) Ja(n, t);\n  };\n}\nfunction lE(e) {\n  return (t) => {\n    const n = [];\n    for (const r of e) {\n      const o = Ja(r, t), i = typeof o == \"function\";\n      n.push(i ? o : () => Ja(r, null));\n    }\n    return () => {\n      for (const r of n) r();\n    };\n  };\n}\nfunction Ja(e, t) {\n  if (typeof e == \"function\")\n    return e(t);\n  e && (e.current = t);\n}\nvar uE = parseInt(Th.split(\".\")[0], 10) >= 19 ? lE : cE;\nfunction fE(e) {\n  return st(() => uE(e), e);\n}\nconst dE = \"_pillInput_1yam9_8\", pE = \"_input_1yam9_16\", hE = \"_largerInput_1yam9_32\", Ca = {\n  pillInput: dE,\n  input: pE,\n  largerInput: hE\n};\nfunction W8({\n  className: e,\n  children: t,\n  onRemoveChildren: n,\n  inputProps: r,\n  ...o\n}) {\n  const i = yt(null), a = i7(r, [\"onKeyDown\", \"ref\"]), s = fE([i, r?.ref]), c = Ah.toArray(t).length > 0;\n  return /* @__PURE__ */ p.createElement(\n    Q,\n    {\n      ...o,\n      gap: \"var(--cpd-space-1x)\",\n      direction: \"column\",\n      className: pe(Ca.pillInput, e),\n      onClick: (l) => {\n        l.preventDefault(), l.stopPropagation(), i.current?.focus();\n      }\n    },\n    c && /* @__PURE__ */ p.createElement(Q, { gap: \"var(--cpd-space-1x)\", wrap: \"wrap\", align: \"center\" }, t),\n    /* @__PURE__ */ p.createElement(\n      \"input\",\n      {\n        ref: s,\n        autoComplete: \"off\",\n        className: pe(Ca.input, { [Ca.largerInput]: c }),\n        onKeyDown: (l) => {\n          const f = l.currentTarget.value.trim();\n          if (l.key === \"Backspace\" && !f) {\n            l.preventDefault(), n?.(l);\n            return;\n          }\n          r?.onKeyDown?.(l);\n        },\n        ...a\n      }\n    )\n  );\n}\nconst mE = \"_container_mqidv_1\", gE = \"_description_mqidv_9\", nt = {\n  container: mE,\n  description: gE\n}, or = {\n  /**\n   * Connectivity to the homeserver has been lost. The user can not take any actions\n   * until the connection is restored.\n   */\n  ConnectionLost: \"ConnectionLost\",\n  /**\n   * The homeserver has indiciated the user needs to consent to the Terms and Conditions\n   * before they can send a message.\n   */\n  NeedsConsent: \"NeedsConsent\",\n  /**\n   * The homeserver has indiciated that messages can not be sent due to a resource limit\n   * being reached. The user may use the given admin contact details.\n   */\n  ResourceLimited: \"ResourceLimited\",\n  /**\n   * There are messages stored locally that previously failed to send that the user\n   * may now retry or delete.\n   */\n  UnsentMessages: \"UnsentMessages\",\n  /**\n   * There was an error creating a room. The user may retry creation.\n   */\n  LocalRoomFailed: \"LocalRoomFailed\"\n};\nfunction Z8({ vm: e }) {\n  const { translate: t } = Pe(), n = me(e), r = To(), o = fe(\n    (c) => {\n      c.preventDefault(), e.onDeleteAllClick?.();\n    },\n    [e]\n  ), i = fe(\n    (c) => {\n      c.preventDefault(), e.onResendAllClick?.();\n    },\n    [e]\n  ), a = fe(\n    (c) => {\n      c.preventDefault(), e.onRetryRoomCreationClick?.();\n    },\n    [e]\n  ), s = fe(() => {\n    e.onTermsAndConditionsClicked?.();\n  }, [e]);\n  if (n.state === null)\n    return null;\n  switch (n.state) {\n    case or.ConnectionLost:\n      return /* @__PURE__ */ p.createElement(rr, { type: \"critical\", role: \"status\", \"aria-labelledby\": r }, /* @__PURE__ */ p.createElement(\"div\", { className: nt.container }, /* @__PURE__ */ p.createElement(mt, { id: r, weight: \"semibold\" }, t(\"room|status_bar|server_connectivity_lost_title\")), /* @__PURE__ */ p.createElement(mt, { className: nt.description, size: \"sm\" }, t(\"room|status_bar|server_connectivity_lost_description\"))));\n    case or.NeedsConsent:\n      return /* @__PURE__ */ p.createElement(\n        rr,\n        {\n          type: \"critical\",\n          role: \"status\",\n          \"aria-labelledby\": r,\n          actions: /* @__PURE__ */ p.createElement(\n            Fe,\n            {\n              onClick: s,\n              kind: \"secondary\",\n              size: \"sm\",\n              as: \"a\",\n              href: n.consentUri,\n              target: \"_blank\",\n              rel: \"noreferrer noopener\"\n            },\n            t(\"terms|tac_button\")\n          )\n        },\n        /* @__PURE__ */ p.createElement(\"div\", { className: nt.container }, /* @__PURE__ */ p.createElement(mt, { id: r, weight: \"semibold\" }, t(\"room|status_bar|requires_consent_agreement_title\")))\n      );\n    case or.ResourceLimited:\n      return /* @__PURE__ */ p.createElement(\n        rr,\n        {\n          type: \"critical\",\n          role: \"status\",\n          \"aria-labelledby\": r,\n          actions: n.adminContactHref && /* @__PURE__ */ p.createElement(\n            Fe,\n            {\n              kind: \"secondary\",\n              size: \"sm\",\n              as: \"a\",\n              href: n.adminContactHref,\n              target: \"_blank\",\n              rel: \"noreferrer noopener\"\n            },\n            \"Contact admin\"\n          )\n        },\n        /* @__PURE__ */ p.createElement(\"div\", { className: nt.container }, /* @__PURE__ */ p.createElement(mt, { id: r, weight: \"semibold\" }, {\n          monthly_active_user: t(\"room|status_bar|monthly_user_limit_reached_title\"),\n          hs_disabled: t(\"room|status_bar|homeserver_blocked_title\")\n        }[n.resourceLimit] || t(\"room|status_bar|exceeded_resource_limit_title\")), /* @__PURE__ */ p.createElement(mt, { className: nt.description, size: \"sm\" }, t(\"room|status_bar|exceeded_resource_limit_description\")))\n      );\n    case or.LocalRoomFailed:\n      return /* @__PURE__ */ p.createElement(\n        rr,\n        {\n          role: \"status\",\n          type: \"critical\",\n          \"aria-labelledby\": r,\n          actions: /* @__PURE__ */ p.createElement(\n            Fe,\n            {\n              size: \"sm\",\n              kind: \"secondary\",\n              className: nt.container,\n              Icon: Sf,\n              onClick: a\n            },\n            t(\"action|retry\")\n          )\n        },\n        /* @__PURE__ */ p.createElement(mt, { id: r, weight: \"semibold\", className: nt.container }, t(\"room|status_bar|failed_to_create_room_title\"))\n      );\n    case or.UnsentMessages:\n      return /* @__PURE__ */ p.createElement(\n        rr,\n        {\n          role: \"status\",\n          type: \"critical\",\n          actions: n.isResending ? /* @__PURE__ */ p.createElement(jh, null) : /* @__PURE__ */ p.createElement(p.Fragment, null, e.onDeleteAllClick && /* @__PURE__ */ p.createElement(\n            Fe,\n            {\n              size: \"sm\",\n              kind: \"destructive\",\n              Icon: R3,\n              disabled: n.isResending,\n              onClick: o\n            },\n            t(\"room|status_bar|delete_all\")\n          ), e.onResendAllClick && /* @__PURE__ */ p.createElement(\n            Fe,\n            {\n              size: \"sm\",\n              kind: \"secondary\",\n              Icon: Sf,\n              disabled: n.isResending,\n              onClick: i,\n              className: nt.container\n            },\n            t(\"room|status_bar|retry_all\")\n          )),\n          \"aria-labelledby\": r\n        },\n        /* @__PURE__ */ p.createElement(\"div\", { className: nt.container }, /* @__PURE__ */ p.createElement(mt, { id: r, weight: \"semibold\" }, t(\"room|status_bar|some_messages_not_sent\")), /* @__PURE__ */ p.createElement(mt, { className: nt.description, size: \"sm\" }, t(\"room|status_bar|select_messages_to_retry\")))\n      );\n    default:\n      return null;\n  }\n}\nconst yE = \"_disambiguatedProfile_oa3at_8\", vE = \"_disambiguatedProfile_displayName_oa3at_14\", bE = \"_disambiguatedProfile_mxid_oa3at_22\", Na = {\n  disambiguatedProfile: yE,\n  disambiguatedProfile_displayName: vE,\n  disambiguatedProfile_mxid: bE\n};\nfunction J8({ vm: e }) {\n  const { displayName: t, colorClass: n, displayIdentifier: r, title: o, emphasizeDisplayName: i, className: a } = me(e), s = pe(n, {\n    [Na.disambiguatedProfile_displayName]: i,\n    mx_DisambiguatedProfile_displayName: i\n  }), c = e.onClick ? (l) => {\n    (l.key === \"Enter\" || l.key === \" \") && (l.preventDefault(), e.onClick?.(l));\n  } : void 0;\n  return /* @__PURE__ */ p.createElement(\n    \"div\",\n    {\n      className: pe(a, Na.disambiguatedProfile),\n      title: o,\n      onClick: e.onClick,\n      onKeyDown: c,\n      role: e.onClick ? \"button\" : void 0,\n      tabIndex: e.onClick ? 0 : void 0\n    },\n    /* @__PURE__ */ p.createElement(\"span\", { className: s, dir: \"auto\" }, t),\n    r && /* @__PURE__ */ p.createElement(\"span\", { className: pe(\"mx_DisambiguatedProfile_mxid\", Na.disambiguatedProfile_mxid) }, r)\n  );\n}\nfunction Q8({ historyVisibility: e }) {\n  const t = {\n    color: \"var(--cpd-color-icon-info-primary)\",\n    width: \"1rem\",\n    // 16px at the default font size, per the design\n    height: \"1rem\"\n  };\n  switch (e) {\n    case \"invited\":\n    case \"joined\":\n      return /* @__PURE__ */ p.createElement(ii, { kind: \"blue\" }, /* @__PURE__ */ p.createElement(Z3, { ...t }), C(\"room|history_visibility_badge|private\"));\n    case \"shared\":\n      return /* @__PURE__ */ p.createElement(ii, { kind: \"blue\" }, /* @__PURE__ */ p.createElement(z3, { ...t }), C(\"room|history_visibility_badge|shared\"));\n    case \"world_readable\":\n      return /* @__PURE__ */ p.createElement(ii, { kind: \"blue\" }, /* @__PURE__ */ p.createElement(V3, { ...t }), C(\"room|history_visibility_badge|world_readable\"));\n    default:\n      return null;\n  }\n}\nconst _E = \"_richItem_1c0uo_8\", wE = \"_avatar_1c0uo_36\", EE = \"_title_1c0uo_41\", SE = \"_description_1c0uo_47\", TE = \"_timestamp_1c0uo_51\", AE = \"_checkmark_1c0uo_69\", jn = {\n  richItem: _E,\n  avatar: wE,\n  title: EE,\n  description: SE,\n  timestamp: TE,\n  checkmark: AE\n}, X8 = Mf(function({\n  avatar: t,\n  title: n,\n  description: r,\n  timestamp: o,\n  selected: i,\n  ...a\n}) {\n  const s = Pe();\n  return /* @__PURE__ */ p.createElement(\n    \"li\",\n    {\n      className: jn.richItem,\n      role: \"option\",\n      tabIndex: -1,\n      \"aria-selected\": i,\n      \"aria-label\": n,\n      ...a\n    },\n    i ? /* @__PURE__ */ p.createElement(IE, null) : /* @__PURE__ */ p.createElement(Q, { className: jn.avatar }, t),\n    /* @__PURE__ */ p.createElement(\"span\", { className: jn.title }, n),\n    /* @__PURE__ */ p.createElement(\"span\", { className: jn.description }, r),\n    o && /* @__PURE__ */ p.createElement(\"span\", { role: \"timer\", className: jn.timestamp }, s.humanizeTime(o))\n  );\n});\nfunction IE() {\n  return /* @__PURE__ */ p.createElement(Q, { align: \"center\", justify: \"center\", \"aria-hidden\": \"true\", className: jn.checkmark }, /* @__PURE__ */ p.createElement(F1, { width: \"24px\", height: \"24px\", color: \"var(--cpd-color-icon-on-solid-primary)\" }));\n}\nconst jE = \"_richList_1mcas_8\", OE = \"_title_1mcas_12\", PE = \"_content_1mcas_18\", kE = \"_empty_1mcas_26\", Qr = {\n  richList: jE,\n  title: OE,\n  content: PE,\n  empty: kE\n};\nfunction RE() {\n  const e = yt(null), t = fe((r) => {\n    if (e.current && r.target === e.current) {\n      let o = e.current?.firstElementChild;\n      for (const i of e.current.children)\n        if (i.getAttribute(\"aria-selected\") === \"true\") {\n          o = i;\n          break;\n        }\n      o?.focus();\n    }\n  }, []), n = fe((r) => {\n    const { key: o } = r;\n    let i = !1;\n    switch (o) {\n      case \"Enter\":\n      case \" \": {\n        i = !0, document.activeElement.click();\n        break;\n      }\n      case \"ArrowDown\": {\n        i = !0;\n        const a = document.activeElement;\n        e.current?.contains(a) && a && a.nextElementSibling?.focus();\n        break;\n      }\n      case \"ArrowUp\": {\n        i = !0;\n        const a = document.activeElement;\n        e.current?.contains(a) && a && a.previousElementSibling?.focus();\n        break;\n      }\n      case \"Home\": {\n        i = !0, e.current?.firstElementChild?.focus();\n        break;\n      }\n      case \"End\": {\n        i = !0, e.current?.lastElementChild?.focus();\n        break;\n      }\n    }\n    i && r.preventDefault();\n  }, []);\n  return { listRef: e, onKeyDown: n, onFocus: t };\n}\nfunction e5({\n  children: e,\n  title: t,\n  className: n,\n  titleAttributes: r,\n  isEmpty: o = !1,\n  ...i\n}) {\n  const a = To(), { listRef: s, onKeyDown: c, onFocus: l } = RE();\n  return /* @__PURE__ */ p.createElement(Q, { className: pe(Qr.richList, n), direction: \"column\", ...i }, /* @__PURE__ */ p.createElement(\"span\", { id: a, className: Qr.title, ...r }, t), o ? /* @__PURE__ */ p.createElement(\"span\", { className: Qr.empty }, e) : /* @__PURE__ */ p.createElement(\n    \"ul\",\n    {\n      ref: s,\n      role: \"listbox\",\n      className: Qr.content,\n      \"aria-labelledby\": a,\n      tabIndex: 0,\n      onKeyDown: c,\n      onFocus: l\n    },\n    e\n  ));\n}\nconst ME = \"_title_1qyi3_8\", CE = {\n  title: ME\n};\nfunction NE({ vm: e }) {\n  const { translate: t } = Pe(), [n, r] = Se(!1), { activeSortOption: o, isMessagePreviewEnabled: i } = me(e);\n  return /* @__PURE__ */ p.createElement(\n    xn,\n    {\n      open: n,\n      onOpenChange: r,\n      title: t(\"room_list|room_options\"),\n      showTitle: !1,\n      align: \"start\",\n      trigger: /* @__PURE__ */ p.createElement(\n        ft,\n        {\n          tooltip: t(\"room_list|room_options\"),\n          \"aria-label\": t(\"room_list|room_options\"),\n          size: \"28px\",\n          style: { padding: \"4px\" }\n        },\n        /* @__PURE__ */ p.createElement(Fc, null)\n      )\n    },\n    /* @__PURE__ */ p.createElement(Dc, { title: t(\"room_list|sort\"), className: CE.title }),\n    /* @__PURE__ */ p.createElement(\n      ai,\n      {\n        label: t(\"room_list|sort_type|activity\"),\n        checked: o === \"recent\",\n        onSelect: () => e.sort(\"recent\")\n      }\n    ),\n    /* @__PURE__ */ p.createElement(\n      ai,\n      {\n        label: t(\"room_list|sort_type|unread_first\"),\n        checked: o === \"unread-first\",\n        onSelect: () => e.sort(\"unread-first\")\n      }\n    ),\n    /* @__PURE__ */ p.createElement(\n      ai,\n      {\n        label: t(\"room_list|sort_type|atoz\"),\n        checked: o === \"alphabetical\",\n        onSelect: () => e.sort(\"alphabetical\")\n      }\n    ),\n    /* @__PURE__ */ p.createElement(Dc, { title: t(\"room_list|appearance\") }),\n    /* @__PURE__ */ p.createElement(\n      Oh,\n      {\n        label: t(\"room_list|show_message_previews\"),\n        onSelect: e.toggleMessagePreview,\n        checked: i\n      }\n    )\n  );\n}\nconst xE = \"_button_1veqf_8\", zE = {\n  button: xE\n};\nfunction BE({ vm: e }) {\n  const { translate: t } = Pe(), { canInviteInSpace: n, canAccessSpaceSettings: r, title: o } = me(e), [i, a] = Se(!1);\n  return /* @__PURE__ */ p.createElement(\n    xn,\n    {\n      open: i,\n      onOpenChange: a,\n      title: o,\n      align: \"start\",\n      trigger: /* @__PURE__ */ p.createElement(\n        ft,\n        {\n          className: zE.button,\n          \"aria-label\": t(\"room_list|open_space_menu\"),\n          size: \"24px\",\n          style: { padding: \"2px\" }\n        },\n        /* @__PURE__ */ p.createElement(q1, null)\n      )\n    },\n    /* @__PURE__ */ p.createElement(ae, { Icon: B3, label: t(\"room_list|space_menu|home\"), onSelect: e.openSpaceHome, hideChevron: !0 }),\n    n && /* @__PURE__ */ p.createElement(ae, { Icon: ph, label: t(\"action|invite\"), onSelect: e.inviteInSpace, hideChevron: !0 }),\n    /* @__PURE__ */ p.createElement(\n      ae,\n      {\n        Icon: U3,\n        label: t(\"common|preferences\"),\n        onSelect: e.openSpacePreferences,\n        hideChevron: !0\n      }\n    ),\n    r && /* @__PURE__ */ p.createElement(\n      ae,\n      {\n        Icon: G3,\n        label: t(\"room_list|space_menu|space_settings\"),\n        onSelect: e.openSpaceSettings,\n        hideChevron: !0\n      }\n    )\n  );\n}\nfunction FE({ vm: e }) {\n  const { translate: t } = Pe(), [n, r] = Se(!1), { canCreateRoom: o, canCreateVideoRoom: i } = me(e);\n  return /* @__PURE__ */ p.createElement(\n    xn,\n    {\n      open: n,\n      onOpenChange: r,\n      showTitle: !1,\n      title: t(\"action|open_menu\"),\n      align: \"start\",\n      trigger: (\n        // 28px button with a 20px icon\n        /* @__PURE__ */ p.createElement(ft, { size: \"28px\", style: { padding: \"4px\" }, tooltip: t(\"action|new_conversation\") }, /* @__PURE__ */ p.createElement($1, { \"aria-hidden\": !0 }))\n      )\n    },\n    /* @__PURE__ */ p.createElement(ae, { Icon: z1, label: t(\"action|start_chat\"), onSelect: e.createChatRoom, hideChevron: !0 }),\n    o && /* @__PURE__ */ p.createElement(ae, { Icon: lh, label: t(\"action|new_room\"), onSelect: e.createRoom, hideChevron: !0 }),\n    i && /* @__PURE__ */ p.createElement(\n      ae,\n      {\n        Icon: W3,\n        label: t(\"action|new_video_room\"),\n        onSelect: e.createVideoRoom,\n        hideChevron: !0\n      }\n    )\n  );\n}\nconst DE = \"_header_kjlxt_8\", qE = \"_container_kjlxt_13\", LE = \"_title_kjlxt_18\", xa = {\n  header: DE,\n  container: qE,\n  title: LE\n};\nfunction t5({ vm: e }) {\n  const { translate: t } = Pe(), { title: n, displaySpaceMenu: r, displayComposeMenu: o } = me(e);\n  return /* @__PURE__ */ p.createElement(\n    Q,\n    {\n      as: \"header\",\n      className: xa.header,\n      \"aria-label\": t(\"room|context_menu|title\"),\n      align: \"end\",\n      \"data-testid\": \"room-list-header\"\n    },\n    /* @__PURE__ */ p.createElement(Q, { className: xa.container, justify: \"space-between\", align: \"center\", gap: \"var(--cpd-space-3x)\" }, /* @__PURE__ */ p.createElement(Q, { className: xa.title, align: \"center\", gap: \"var(--cpd-space-1x)\" }, /* @__PURE__ */ p.createElement(Ph, { size: \"sm\", title: n }, n), r && /* @__PURE__ */ p.createElement(BE, { vm: e })), /* @__PURE__ */ p.createElement(Q, { align: \"center\", gap: \"var(--cpd-space-2x)\" }, /* @__PURE__ */ p.createElement(NE, { vm: e }), o ? /* @__PURE__ */ p.createElement(FE, { vm: e }) : /* @__PURE__ */ p.createElement(\n      ft,\n      {\n        size: \"28px\",\n        style: { padding: \"4px\" },\n        onClick: (i) => e.createChatRoom(i.nativeEvent),\n        tooltip: t(\"action|new_conversation\")\n      },\n      /* @__PURE__ */ p.createElement($1, { color: \"var(--cpd-color-icon-secondary)\", \"aria-hidden\": !0 })\n    )))\n  );\n}\nconst HE = \"_view_z7ks9_8\", $E = \"_search_z7ks9_16\", UE = \"_search_container_z7ks9_29\", KE = \"_search_text_z7ks9_41\", Xr = {\n  view: HE,\n  search: $E,\n  search_container: UE,\n  search_text: KE\n};\nfunction n5({ vm: e }) {\n  const { translate: t } = Pe(), { displayExploreButton: n, displayDialButton: r, searchShortcut: o } = me(e);\n  return /* @__PURE__ */ p.createElement(\n    Q,\n    {\n      \"data-testid\": \"room-list-search\",\n      className: Xr.view,\n      role: \"search\",\n      gap: \"var(--cpd-space-2x)\",\n      align: \"center\"\n    },\n    /* @__PURE__ */ p.createElement(\n      Fe,\n      {\n        id: \"room-list-search-button\",\n        className: Xr.search,\n        kind: \"secondary\",\n        size: \"sm\",\n        Icon: K3,\n        onClick: e.onSearchClick\n      },\n      /* @__PURE__ */ p.createElement(Q, { className: Xr.search_container, as: \"span\", justify: \"space-between\" }, /* @__PURE__ */ p.createElement(\"span\", { className: Xr.search_text }, t(\"action|search\")), /* @__PURE__ */ p.createElement(\"kbd\", null, o))\n    ),\n    r && /* @__PURE__ */ p.createElement(\n      Fe,\n      {\n        kind: \"secondary\",\n        size: \"sm\",\n        Icon: M3,\n        iconOnly: !0,\n        \"aria-label\": t(\"left_panel|open_dial_pad\"),\n        onClick: e.onDialPadClick\n      }\n    ),\n    n && /* @__PURE__ */ p.createElement(\n      Fe,\n      {\n        kind: \"secondary\",\n        size: \"sm\",\n        Icon: N3,\n        iconOnly: !0,\n        \"aria-label\": t(\"action|explore_rooms\"),\n        onClick: e.onExploreClick\n      }\n    )\n  );\n}\nfunction GE(e, t) {\n  const n = yt(null), [r, o] = Se(!1), [i, a] = Se(-1);\n  return on(() => {\n    if (!n.current) return;\n    const s = (l) => {\n      let f = !1;\n      Array.from(l.children).forEach((d, u) => {\n        const b = d;\n        if (b.setAttribute(\"aria-hidden\", \"false\"), b.classList.remove(t), e) return;\n        const h = b.previousElementSibling;\n        h && b.offsetLeft <= h.offsetLeft && (f || a(u), f = !0), b.classList.toggle(t, f), b.setAttribute(\"aria-hidden\", f.toString());\n      }), f || a(-1), o(e || f);\n    };\n    s(n.current);\n    const c = new ResizeObserver((l) => l.forEach((f) => s(f.target)));\n    return c.observe(n.current), () => {\n      c.disconnect();\n    };\n  }, [e, t]), { ref: n, isWrapping: r, wrappingIndex: i };\n}\nfunction VE(e, t, n) {\n  const [r, o] = Se(e);\n  return on(() => {\n    if (!((t ? e.indexOf(t) : -1) >= n) || n === -1) {\n      o(e);\n      return;\n    }\n    o(\n      e.slice().sort((s, c) => s === t && c !== t ? -1 : s !== t && c === t ? 1 : 0)\n    );\n  }, [e, t, n]), r;\n}\nconst YE = \"_roomListPrimaryFilters_1dmi7_8\", WE = \"_list_1dmi7_17\", ZE = \"_iconButton_1dmi7_26\", za = {\n  roomListPrimaryFilters: YE,\n  list: WE,\n  iconButton: ZE\n}, JE = (e) => {\n  switch (e) {\n    case \"unread\":\n      return C(\"room_list|filters|unread\");\n    case \"people\":\n      return C(\"room_list|filters|people\");\n    case \"rooms\":\n      return C(\"room_list|filters|rooms\");\n    case \"favourite\":\n      return C(\"room_list|filters|favourite\");\n    case \"mentions\":\n      return C(\"room_list|filters|mentions\");\n    case \"invites\":\n      return C(\"room_list|filters|invites\");\n    case \"low_priority\":\n      return C(\"room_list|filters|low_priority\");\n  }\n}, QE = ({\n  filterIds: e,\n  activeFilterId: t,\n  onToggleFilter: n\n}) => {\n  const r = To(), [o, i] = Se(!1), {\n    ref: a,\n    isWrapping: s,\n    wrappingIndex: c\n  } = GE(o, \"wrapping\"), l = VE(e, t, c);\n  return /* @__PURE__ */ p.createElement(\n    Q,\n    {\n      className: za.roomListPrimaryFilters,\n      \"data-testid\": \"primary-filters\",\n      gap: \"var(--cpd-space-3x)\",\n      direction: \"row-reverse\",\n      justify: \"space-between\"\n    },\n    s && /* @__PURE__ */ p.createElement(\n      ft,\n      {\n        kind: \"secondary\",\n        \"aria-expanded\": o,\n        \"aria-controls\": r,\n        className: za.iconButton,\n        \"aria-label\": C(o ? \"room_list|collapse_filters\" : \"room_list|expand_filters\"),\n        size: \"28px\",\n        onClick: () => i((f) => !f)\n      },\n      /* @__PURE__ */ p.createElement(q1, null)\n    ),\n    /* @__PURE__ */ p.createElement(\n      Q,\n      {\n        id: r,\n        as: \"div\",\n        role: \"listbox\",\n        \"aria-label\": C(\"room_list|primary_filters\"),\n        align: \"center\",\n        gap: \"var(--cpd-space-2x)\",\n        wrap: \"wrap\",\n        className: za.list,\n        ref: a\n      },\n      l.map((f, d) => /* @__PURE__ */ p.createElement(\n        kh,\n        {\n          key: `${f}-${d}`,\n          role: \"option\",\n          selected: f === t,\n          onClick: () => n(f)\n        },\n        JE(f)\n      ))\n    )\n  );\n}, XE = \"_skeleton_1h0mx_8\", e8 = {\n  skeleton: XE\n}, t8 = () => /* @__PURE__ */ p.createElement(\"div\", { className: e8.skeleton }), n8 = \"_genericPlaceholder_1sxid_8\", r8 = \"_title_1sxid_16\", o8 = \"_description_1sxid_21\", i8 = \"_defaultPlaceholder_1sxid_27\", ao = {\n  genericPlaceholder: n8,\n  title: r8,\n  description: o8,\n  defaultPlaceholder: i8\n}, a8 = ({ vm: e }) => {\n  const t = me(e);\n  if (!t.activeFilterId)\n    return /* @__PURE__ */ p.createElement(\n      On,\n      {\n        title: C(\"room_list|empty|no_chats\"),\n        description: t.canCreateRoom ? C(\"room_list|empty|no_chats_description\") : C(\"room_list|empty|no_chats_description_no_room_rights\")\n      },\n      /* @__PURE__ */ p.createElement(\n        Q,\n        {\n          className: ao.defaultPlaceholder,\n          align: \"center\",\n          justify: \"center\",\n          direction: \"column\",\n          gap: \"var(--cpd-space-4x)\"\n        },\n        /* @__PURE__ */ p.createElement(Fe, { size: \"sm\", kind: \"secondary\", Icon: z1, onClick: e.createChatRoom }, C(\"action|start_chat\")),\n        t.canCreateRoom && /* @__PURE__ */ p.createElement(Fe, { size: \"sm\", kind: \"secondary\", Icon: lh, onClick: e.createRoom }, C(\"action|new_room\"))\n      )\n    );\n  switch (t.activeFilterId) {\n    case \"favourite\":\n      return /* @__PURE__ */ p.createElement(\n        On,\n        {\n          title: C(\"room_list|empty|no_favourites\"),\n          description: C(\"room_list|empty|no_favourites_description\")\n        }\n      );\n    case \"people\":\n      return /* @__PURE__ */ p.createElement(\n        On,\n        {\n          title: C(\"room_list|empty|no_people\"),\n          description: C(\"room_list|empty|no_people_description\")\n        }\n      );\n    case \"rooms\":\n      return /* @__PURE__ */ p.createElement(\n        On,\n        {\n          title: C(\"room_list|empty|no_rooms\"),\n          description: C(\"room_list|empty|no_rooms_description\")\n        }\n      );\n    case \"unread\":\n      return /* @__PURE__ */ p.createElement(\n        eo,\n        {\n          title: C(\"room_list|empty|no_unread\"),\n          action: C(\"room_list|empty|show_chats\"),\n          onAction: () => e.onToggleFilter(t.activeFilterId)\n        }\n      );\n    case \"invites\":\n      return /* @__PURE__ */ p.createElement(\n        eo,\n        {\n          title: C(\"room_list|empty|no_invites\"),\n          action: C(\"room_list|empty|show_activity\"),\n          onAction: () => e.onToggleFilter(t.activeFilterId)\n        }\n      );\n    case \"mentions\":\n      return /* @__PURE__ */ p.createElement(\n        eo,\n        {\n          title: C(\"room_list|empty|no_mentions\"),\n          action: C(\"room_list|empty|show_activity\"),\n          onAction: () => e.onToggleFilter(t.activeFilterId)\n        }\n      );\n    case \"low_priority\":\n      return /* @__PURE__ */ p.createElement(\n        eo,\n        {\n          title: C(\"room_list|empty|no_lowpriority\"),\n          action: C(\"room_list|empty|show_activity\"),\n          onAction: () => e.onToggleFilter(t.activeFilterId)\n        }\n      );\n    default:\n      return /* @__PURE__ */ p.createElement(\n        On,\n        {\n          title: C(\"room_list|empty|no_chats\"),\n          description: C(\"room_list|empty|no_chats_description\")\n        }\n      );\n  }\n};\nfunction On({ title: e, description: t, children: n }) {\n  return /* @__PURE__ */ p.createElement(\n    Q,\n    {\n      \"data-testid\": \"empty-room-list\",\n      className: ao.genericPlaceholder,\n      direction: \"column\",\n      align: \"stretch\",\n      justify: \"center\",\n      gap: \"var(--cpd-space-2x)\"\n    },\n    /* @__PURE__ */ p.createElement(\"span\", { className: ao.title }, e),\n    t && /* @__PURE__ */ p.createElement(\"span\", { className: ao.description }, t),\n    n\n  );\n}\nfunction eo({ title: e, action: t, onAction: n }) {\n  return /* @__PURE__ */ p.createElement(On, { title: e }, n && /* @__PURE__ */ p.createElement(Fe, { kind: \"tertiary\", onClick: n }, t));\n}\nconst s8 = ({\n  hasAnyNotificationOrActivity: e,\n  muted: t,\n  callType: n,\n  isUnsentMessage: r,\n  invited: o,\n  isMention: i,\n  isNotification: a,\n  isActivityNotification: s,\n  count: c\n}) => !e && !t && !n ? null : /* @__PURE__ */ p.createElement(Q, { align: \"center\", justify: \"center\", gap: \"var(--cpd-space-1x)\", \"data-testid\": \"notification-decoration\" }, r && /* @__PURE__ */ p.createElement(g1, { width: \"20px\", height: \"20px\", fill: \"var(--cpd-color-icon-critical-primary)\" }), n === \"video\" && /* @__PURE__ */ p.createElement(Y3, { width: \"20px\", height: \"20px\", fill: \"var(--cpd-color-icon-accent-primary)\" }), n === \"voice\" && /* @__PURE__ */ p.createElement(J3, { width: \"20px\", height: \"20px\", fill: \"var(--cpd-color-icon-accent-primary)\" }), o && /* @__PURE__ */ p.createElement(C3, { width: \"20px\", height: \"20px\", fill: \"var(--cpd-color-icon-accent-primary)\" }), i && /* @__PURE__ */ p.createElement(H3, { width: \"20px\", height: \"20px\", fill: \"var(--cpd-color-icon-accent-primary)\" }), (i || a) && /* @__PURE__ */ p.createElement(Rh, { count: c || null }), s && /* @__PURE__ */ p.createElement(Mh, null), t && /* @__PURE__ */ p.createElement(rh, { width: \"20px\", height: \"20px\", fill: \"var(--cpd-color-icon-tertiary)\" }));\nfunction c8({ vm: e }) {\n  const [t, n] = Se(!1);\n  return /* @__PURE__ */ p.createElement(\n    xn,\n    {\n      open: t,\n      onOpenChange: n,\n      title: C(\"room_list|room|more_options\"),\n      showTitle: !1,\n      align: \"start\",\n      trigger: /* @__PURE__ */ p.createElement(\n        ft,\n        {\n          tooltip: C(\"room_list|room|more_options\"),\n          \"aria-label\": C(\"room_list|room|more_options\"),\n          size: \"24px\",\n          style: { padding: \"2px\" }\n        },\n        /* @__PURE__ */ p.createElement(Fc, null)\n      )\n    },\n    /* @__PURE__ */ p.createElement(bh, { vm: e })\n  );\n}\nfunction bh({ vm: e }) {\n  const t = me(e);\n  return (\n    // eslint-disable-next-line jsx-a11y/no-static-element-interactions\n    /* @__PURE__ */ p.createElement(\"div\", { onKeyDown: (n) => n.stopPropagation() }, t.canMarkAsRead && /* @__PURE__ */ p.createElement(\n      ae,\n      {\n        Icon: q3,\n        label: C(\"room_list|more_options|mark_read\"),\n        onSelect: e.onMarkAsRead,\n        onClick: (n) => n.stopPropagation(),\n        hideChevron: !0\n      }\n    ), t.canMarkAsUnread && /* @__PURE__ */ p.createElement(\n      ae,\n      {\n        Icon: L3,\n        label: C(\"room_list|more_options|mark_unread\"),\n        onSelect: e.onMarkAsUnread,\n        onClick: (n) => n.stopPropagation(),\n        hideChevron: !0\n      }\n    ), /* @__PURE__ */ p.createElement(\n      qc,\n      {\n        checked: t.isFavourite,\n        Icon: x3,\n        label: C(\"room_list|more_options|favourited\"),\n        onSelect: e.onToggleFavorite,\n        onClick: (n) => n.stopPropagation()\n      }\n    ), /* @__PURE__ */ p.createElement(\n      qc,\n      {\n        checked: t.isLowPriority,\n        Icon: P3,\n        label: C(\"room_list|more_options|low_priority\"),\n        onSelect: e.onToggleLowPriority,\n        onClick: (n) => n.stopPropagation()\n      }\n    ), t.canInvite && /* @__PURE__ */ p.createElement(\n      ae,\n      {\n        Icon: ph,\n        label: C(\"action|invite\"),\n        onSelect: e.onInvite,\n        onClick: (n) => n.stopPropagation(),\n        hideChevron: !0\n      }\n    ), t.canCopyRoomLink && /* @__PURE__ */ p.createElement(\n      ae,\n      {\n        Icon: D3,\n        label: C(\"room_list|more_options|copy_link\"),\n        onSelect: e.onCopyRoomLink,\n        onClick: (n) => n.stopPropagation(),\n        hideChevron: !0\n      }\n    ), /* @__PURE__ */ p.createElement(Ch, null), /* @__PURE__ */ p.createElement(\n      ae,\n      {\n        kind: \"critical\",\n        Icon: F3,\n        label: C(\"room_list|more_options|leave_room\"),\n        onSelect: e.onLeaveRoom,\n        onClick: (n) => n.stopPropagation(),\n        hideChevron: !0\n      }\n    ))\n  );\n}\nvar Ae = /* @__PURE__ */ ((e) => (e.AllMessages = \"all_messages\", e.AllMessagesLoud = \"all_messages_loud\", e.MentionsOnly = \"mentions_only\", e.Mute = \"mute\", e))(Ae || {});\nfunction l8({ vm: e }) {\n  const t = me(e), [n, r] = Se(!1), o = t.roomNotifState === Ae.Mute, i = /* @__PURE__ */ p.createElement(F1, { width: \"24px\", height: \"24px\", color: \"var(--cpd-color-icon-primary)\" });\n  return /* @__PURE__ */ p.createElement(\n    xn,\n    {\n      open: n,\n      onOpenChange: r,\n      title: C(\"room_list|notification_options\"),\n      showTitle: !1,\n      align: \"start\",\n      trigger: /* @__PURE__ */ p.createElement(\n        ft,\n        {\n          size: \"24px\",\n          style: { padding: \"2px\" },\n          tooltip: C(\"room_list|notification_options\"),\n          \"aria-label\": C(\"room_list|notification_options\")\n        },\n        o ? /* @__PURE__ */ p.createElement(rh, null) : /* @__PURE__ */ p.createElement($3, null)\n      )\n    },\n    /* @__PURE__ */ p.createElement(\n      \"div\",\n      {\n        onKeyDown: (a) => a.stopPropagation()\n      },\n      /* @__PURE__ */ p.createElement(\n        ae,\n        {\n          \"aria-selected\": t.roomNotifState === Ae.AllMessages,\n          hideChevron: !0,\n          label: C(\"notifications|default_settings\"),\n          onSelect: () => e.onSetRoomNotifState(Ae.AllMessages),\n          onClick: (a) => a.stopPropagation()\n        },\n        t.roomNotifState === Ae.AllMessages && i\n      ),\n      /* @__PURE__ */ p.createElement(\n        ae,\n        {\n          \"aria-selected\": t.roomNotifState === Ae.AllMessagesLoud,\n          hideChevron: !0,\n          label: C(\"notifications|all_messages\"),\n          onSelect: () => e.onSetRoomNotifState(Ae.AllMessagesLoud),\n          onClick: (a) => a.stopPropagation()\n        },\n        t.roomNotifState === Ae.AllMessagesLoud && i\n      ),\n      /* @__PURE__ */ p.createElement(\n        ae,\n        {\n          \"aria-selected\": t.roomNotifState === Ae.MentionsOnly,\n          hideChevron: !0,\n          label: C(\"notifications|mentions_keywords\"),\n          onSelect: () => e.onSetRoomNotifState(Ae.MentionsOnly),\n          onClick: (a) => a.stopPropagation()\n        },\n        t.roomNotifState === Ae.MentionsOnly && i\n      ),\n      /* @__PURE__ */ p.createElement(\n        ae,\n        {\n          \"aria-selected\": t.roomNotifState === Ae.Mute,\n          hideChevron: !0,\n          label: C(\"notifications|mute_room\"),\n          onSelect: () => e.onSetRoomNotifState(Ae.Mute),\n          onClick: (a) => a.stopPropagation()\n        },\n        t.roomNotifState === Ae.Mute && i\n      )\n    )\n  );\n}\nconst u8 = \"_roomListItem_1srqj_8\", f8 = \"_hoverMenu_1srqj_28\", d8 = \"_container_1srqj_42\", p8 = \"_selected_1srqj_47\", h8 = \"_notificationDecoration_1srqj_56\", m8 = \"_content_1srqj_70\", g8 = \"_ellipsis_1srqj_79\", y8 = \"_roomName_1srqj_80\", v8 = \"_bold_1srqj_107\", rt = {\n  roomListItem: u8,\n  hoverMenu: f8,\n  container: d8,\n  selected: p8,\n  notificationDecoration: h8,\n  content: m8,\n  ellipsis: g8,\n  roomName: y8,\n  bold: v8\n}, b8 = ({\n  showMoreOptionsMenu: e,\n  showNotificationMenu: t,\n  vm: n\n}) => /* @__PURE__ */ p.createElement(Q, { className: rt.hoverMenu, align: \"center\", gap: \"var(--cpd-space-1x)\" }, e && /* @__PURE__ */ p.createElement(c8, { vm: n }), t && /* @__PURE__ */ p.createElement(l8, { vm: n })), _8 = ({\n  vm: e,\n  children: t\n}) => /* @__PURE__ */ p.createElement(\n  Nh,\n  {\n    title: C(\"room_list|room|more_options\"),\n    showTitle: !1,\n    hasAccessibleAlternative: !0,\n    trigger: t\n  },\n  /* @__PURE__ */ p.createElement(bh, { vm: e })\n);\nfunction w8(e, t) {\n  return t.isUnsentMessage ? C(\"room_list|a11y|unsent_message\", { roomName: e }) : t.invited ? C(\"room_list|a11y|invitation\", { roomName: e }) : t.isMention && t.count ? C(\"room_list|a11y|mention\", { roomName: e, count: t.count }) : t.hasUnreadCount && t.count ? C(\"room_list|a11y|unread\", { roomName: e, count: t.count }) : C(\"room_list|a11y|default\", { roomName: e });\n}\nconst E8 = Mf(function({\n  vm: t,\n  isSelected: n,\n  isFocused: r,\n  onFocus: o,\n  roomIndex: i,\n  roomCount: a,\n  renderAvatar: s,\n  ...c\n}) {\n  const l = yt(null), f = me(t);\n  on(() => {\n    r && l.current?.focus({ preventScroll: !0, focusVisible: !0 });\n  }, [r]);\n  const d = w8(f.name, f.notification), u = /* @__PURE__ */ p.createElement(\n    Q,\n    {\n      as: \"button\",\n      ref: l,\n      className: pe(rt.roomListItem, \"mx_RoomListItemView\", {\n        [rt.selected]: n,\n        [rt.bold]: f.isBold,\n        mx_RoomListItemView_selected: n\n      }),\n      gap: \"var(--cpd-space-3x)\",\n      align: \"center\",\n      type: \"button\",\n      role: \"option\",\n      \"aria-posinset\": i + 1,\n      \"aria-setsize\": a,\n      \"aria-selected\": n,\n      \"aria-label\": d,\n      onClick: t.onOpenRoom,\n      onFocus: (b) => o(f.id, b),\n      tabIndex: r ? 0 : -1,\n      ...c\n    },\n    /* @__PURE__ */ p.createElement(Q, { className: rt.container, gap: \"var(--cpd-space-3x)\", align: \"center\" }, s(f.room), /* @__PURE__ */ p.createElement(Q, { className: rt.content, gap: \"var(--cpd-space-2x)\", align: \"center\", justify: \"space-between\" }, /* @__PURE__ */ p.createElement(\"div\", { className: rt.ellipsis }, /* @__PURE__ */ p.createElement(\"div\", { className: rt.roomName, title: f.name, \"data-testid\": \"room-name\" }, f.name), f.messagePreview && /* @__PURE__ */ p.createElement(mt, { as: \"div\", size: \"sm\", className: rt.ellipsis, title: f.messagePreview }, f.messagePreview)), (f.showMoreOptionsMenu || f.showNotificationMenu) && /* @__PURE__ */ p.createElement(\n      b8,\n      {\n        showMoreOptionsMenu: f.showMoreOptionsMenu,\n        showNotificationMenu: f.showNotificationMenu,\n        vm: t\n      }\n    ), /* @__PURE__ */ p.createElement(\"div\", { className: rt.notificationDecoration, \"aria-hidden\": !0 }, /* @__PURE__ */ p.createElement(s8, { ...f.notification }))))\n  );\n  return /* @__PURE__ */ p.createElement(_8, { vm: t }, u);\n}), In = {\n  ARROW_UP: \"ArrowUp\",\n  ARROW_DOWN: \"ArrowDown\",\n  HOME: \"Home\",\n  END: \"End\",\n  PAGE_UP: \"PageUp\",\n  PAGE_DOWN: \"PageDown\"\n};\nfunction S8(e) {\n  return e.ctrlKey || e.metaKey || e.shiftKey || e.altKey;\n}\nfunction T8(e) {\n  const {\n    items: t,\n    getItemComponent: n,\n    isItemFocusable: r,\n    getItemKey: o,\n    context: i,\n    onKeyDown: a,\n    totalCount: s,\n    rangeChanged: c,\n    ...l\n  } = e, f = yt(null), d = yt(null), [u, b] = Se(\n    e.items[0] ? o(e.items[0]) : void 0\n  ), [h, w] = Se(void 0), [E, m] = Se(/* @__PURE__ */ new Map()), g = yt(!1), [T, y] = Se(!1);\n  on(() => {\n    const D = /* @__PURE__ */ new Map();\n    t.forEach((K, W) => {\n      const ne = o(K);\n      D.set(ne, W);\n    }), m(D);\n  }, [t, o]), on(() => {\n    t.length && (!u || E.get(u) === void 0) && b(o(t[0]));\n  }, [t, o, u, E]);\n  const v = fe(\n    (D, K) => {\n      const W = Math.max(0, Math.min(D, t.length - 1));\n      if (!g.current && t[W]) {\n        const ne = o(t[W]);\n        g.current = !0, f.current?.scrollIntoView({\n          index: W,\n          align: K,\n          behavior: \"auto\",\n          done: () => {\n            b(ne), g.current = !1;\n          }\n        });\n      }\n    },\n    [t, o]\n  ), S = fe(\n    (D, K, W) => {\n      const ne = t.length;\n      let le;\n      for (let he = D; K ? he < ne : he >= 0; he = he + (K ? 1 : -1))\n        if (r(t[he])) {\n          le = he;\n          break;\n        }\n      le !== void 0 && v(le, W);\n    },\n    [v, t, r]\n  ), I = fe(\n    (D) => {\n      const K = u ? E.get(u) : void 0;\n      let W = !1;\n      if (!D || S8(D)) {\n        a?.(D);\n        return;\n      }\n      if (D.code === In.ARROW_UP && K !== void 0)\n        S(K - 1, !1), W = !0;\n      else if (D.code === In.ARROW_DOWN && K !== void 0)\n        S(K + 1, !0), W = !0;\n      else if (D.code === In.HOME)\n        v(0), W = !0;\n      else if (D.code === In.END)\n        v(t.length - 1), W = !0;\n      else if (D.code === In.PAGE_DOWN && h && K !== void 0) {\n        const ne = h.endIndex - h.startIndex;\n        S(Math.min(K + ne, t.length - 1), !0, \"start\"), W = !0;\n      } else if (D.code === In.PAGE_UP && h && K !== void 0) {\n        const ne = h.endIndex - h.startIndex;\n        S(Math.max(K - ne, 0), !1, \"start\"), W = !0;\n      }\n      W ? (D.stopPropagation(), D.preventDefault()) : a?.(D);\n    },\n    [v, S, u, E, h, t, a]\n  ), k = fe((D) => {\n    d.current = D;\n  }, []), M = fe(\n    (D, K) => {\n      const W = o(D);\n      y(!0), b(W), K.stopPropagation();\n    },\n    [o]\n  ), N = fe(\n    (D, K, W) => n(D, K, W, M),\n    [n, M]\n  ), L = fe(\n    (D) => {\n      if (D?.currentTarget !== d.current || typeof u != \"string\")\n        return;\n      y(!0);\n      const K = E.get(u);\n      K !== void 0 && h && (K < h.startIndex || K > h.endIndex) && v(K), D?.stopPropagation(), D?.preventDefault();\n    },\n    [E, h, v, u]\n  ), V = fe((D) => {\n    D.currentTarget.contains(D.relatedTarget) || y(!1);\n  }, []), ie = st(\n    () => ({\n      tabIndexKey: u,\n      focused: T,\n      context: e.context || {}\n    }),\n    [u, T, e.context]\n  ), ce = fe(\n    (D) => {\n      w(D), c?.(D);\n    },\n    [c]\n  );\n  return /* @__PURE__ */ p.createElement(\n    xh,\n    {\n      ref: f,\n      scrollerRef: k,\n      onKeyDown: I,\n      context: ie,\n      rangeChanged: ce,\n      overscan: e.overscan || 0,\n      data: e.items,\n      totalCount: s,\n      onFocus: L,\n      onBlur: V,\n      itemContent: N,\n      ...l\n    }\n  );\n}\nconst _h = 52, Af = 25 * _h;\nfunction A8({ vm: e, renderAvatar: t, onKeyDown: n }) {\n  const r = me(e), { roomListState: o, roomIds: i } = r, a = o.activeRoomIndex, s = yt(void 0), c = yt(void 0), l = i.length, f = fe(\n    (w) => {\n      e.updateVisibleRooms(w.startIndex, w.endIndex);\n    },\n    [e]\n  ), d = fe(\n    (w, E, m, g) => {\n      const T = a === w, y = e.getRoomItemViewModel(E), v = m.focused && m.tabIndexKey === E;\n      return /* @__PURE__ */ p.createElement(\n        E8,\n        {\n          key: E,\n          vm: y,\n          renderAvatar: t,\n          isSelected: T,\n          isFocused: v,\n          onFocus: g,\n          roomIndex: w,\n          roomCount: l\n        }\n      );\n    },\n    [a, l, t, e]\n  ), u = fe((w) => w, []), b = st(\n    () => ({ spaceId: o.spaceId || \"\", filterKeys: o.filterKeys }),\n    [o.spaceId, o.filterKeys]\n  ), h = fe(\n    (w) => {\n      const { spaceId: E, filterKeys: m } = w.context.context, g = s.current !== E || !Jw(c.current, m);\n      return c.current = m, s.current = E, g ? {\n        align: \"start\",\n        index: a || 0,\n        behavior: \"auto\"\n      } : !1;\n    },\n    [a]\n  );\n  return /* @__PURE__ */ p.createElement(\n    T8,\n    {\n      context: b,\n      scrollIntoViewOnChange: h,\n      initialTopMostItemIndex: a,\n      \"data-testid\": \"room-list\",\n      role: \"listbox\",\n      \"aria-label\": C(\"room_list|list_title\"),\n      fixedItemHeight: _h,\n      items: i,\n      getItemComponent: d,\n      getItemKey: u,\n      isItemFocusable: () => !0,\n      rangeChanged: f,\n      onKeyDown: n,\n      increaseViewportBy: {\n        bottom: Af,\n        top: Af\n      }\n    }\n  );\n}\nconst r5 = ({ vm: e, renderAvatar: t, onKeyDown: n }) => {\n  const r = me(e);\n  let o;\n  return r.isLoadingRooms ? o = /* @__PURE__ */ p.createElement(t8, null) : r.isRoomListEmpty ? o = /* @__PURE__ */ p.createElement(a8, { vm: e }) : o = /* @__PURE__ */ p.createElement(A8, { vm: e, renderAvatar: t, onKeyDown: n }), /* @__PURE__ */ p.createElement(p.Fragment, null, /* @__PURE__ */ p.createElement(\"div\", null, /* @__PURE__ */ p.createElement(\n    QE,\n    {\n      filterIds: r.filterIds,\n      activeFilterId: r.activeFilterId,\n      onToggleFilter: e.onToggleFilter\n    }\n  )), o);\n}, Ba = {\n  \"box-flex\": \"_box-flex_1odfs_9\",\n  \"box-shrink\": \"_box-shrink_1odfs_13\",\n  \"box-grow\": \"_box-grow_1odfs_17\"\n};\nfunction o5({\n  as: e = \"div\",\n  flex: t = null,\n  shrink: n = null,\n  grow: r = null,\n  className: o,\n  children: i,\n  ...a\n}) {\n  const s = st(() => {\n    const c = {};\n    return t && (c[\"--mx-box-flex\"] = t), n && (c[\"--mx-box-shrink\"] = n), r && (c[\"--mx-box-grow\"] = r), c;\n  }, [t, r, n]);\n  return p.createElement(\n    e,\n    {\n      ...a,\n      className: pe(o, {\n        [Ba[\"box-flex\"]]: !!t,\n        [Ba[\"box-shrink\"]]: !!n,\n        [Ba[\"box-grow\"]]: !!r\n      }),\n      style: s\n    },\n    i\n  );\n}\nconst i5 = ({ vm: e }) => {\n  const { translate: t } = Pe(), {\n    showStreamAudioStreamButton: n,\n    showEditButton: r,\n    showSnapshotButton: o,\n    showDeleteButton: i,\n    showRevokeButton: a,\n    showMoveButtons: s,\n    isMenuOpened: c,\n    userWidget: l,\n    trigger: f\n  } = me(e);\n  let d;\n  n && (d = /* @__PURE__ */ p.createElement(ae, { onSelect: e.onStreamAudioClick, label: t(\"widget|context_menu|start_audio_stream\") }));\n  let u;\n  r && (u = /* @__PURE__ */ p.createElement(ae, { onSelect: e.onEditClick, label: t(\"action|edit\") }));\n  let b;\n  o && (b = /* @__PURE__ */ p.createElement(ae, { onSelect: e.onSnapshotClick, label: t(\"widget|context_menu|screenshot\") }));\n  let h;\n  i && (h = /* @__PURE__ */ p.createElement(\n    ae,\n    {\n      onSelect: e.onDeleteClick,\n      label: t(l ? \"action|remove\" : \"widget|context_menu|remove\")\n    }\n  ));\n  let w;\n  a && (w = /* @__PURE__ */ p.createElement(ae, { onSelect: e.onRevokeClick, label: t(\"widget|context_menu|revoke\") }));\n  const [E, m] = s;\n  let g;\n  E && (g = /* @__PURE__ */ p.createElement(ae, { onSelect: () => e.onMoveButton(-1), label: t(\"widget|context_menu|move_left\") }));\n  let T;\n  m && (T = /* @__PURE__ */ p.createElement(ae, { onSelect: () => e.onMoveButton(1), label: t(\"widget|context_menu|move_right\") }));\n  const y = () => c ? /* @__PURE__ */ p.createElement(p.Fragment, null, d, u, w, h, b, g, T) : null, v = p.isValidElement(f) ? f : /* @__PURE__ */ p.createElement(ft, { size: \"24px\", \"aria-label\": \"context menu trigger button\", inert: !0, tabIndex: -1 }, /* @__PURE__ */ p.createElement(Fc, null));\n  return /* @__PURE__ */ p.createElement(\n    xn,\n    {\n      title: \"Widget context menu\",\n      open: c,\n      showTitle: !1,\n      side: \"right\",\n      align: \"start\",\n      trigger: v,\n      onOpenChange: e.onFinished\n    },\n    y()\n  );\n}, If = 15e3, jf = 75e3, Of = 45, Pf = 75, kf = 23, Rf = 26;\nfunction I8(e, t) {\n  let r = Date.now() - e;\n  const o = Math.abs(Math.ceil(r / 6e4)), i = Math.ceil(o / 60), a = Math.ceil(i / 24), s = t?.translate ?? C;\n  return r >= 0 ? r <= If ? s(\"time|few_seconds_ago\") : r <= jf ? s(\"time|about_minute_ago\") : o <= Of ? s(\"time|n_minutes_ago\", { num: o }) : o <= Pf ? s(\"time|about_hour_ago\") : i <= kf ? s(\"time|n_hours_ago\", { num: i }) : i <= Rf ? s(\"time|about_day_ago\") : s(\"time|n_days_ago\", { num: a }) : (r = Math.abs(r), r <= If ? s(\"time|in_few_seconds\") : r <= jf ? s(\"time|in_about_minute\") : o <= Of ? s(\"time|in_n_minutes\", { num: o }) : o <= Pf ? s(\"time|in_about_hour\") : i <= kf ? s(\"time|in_n_hours\", { num: i }) : i <= Rf ? s(\"time|in_about_day\") : s(\"time|in_n_days\", { num: a }));\n}\nfunction a5(e, t) {\n  return Number.isFinite(e) ? Number(e) : t;\n}\nfunction s5(e, t, n) {\n  return Math.min(Math.max(e, t), n);\n}\nfunction c5(...e) {\n  return [...e].reduce((t, n) => n + t, 0);\n}\nfunction l5(e, t, n) {\n  return e * (n - t) + t;\n}\nfunction u5(e, t, n) {\n  const r = (e - t) / (n - t);\n  return Number.isNaN(r) ? 0 : r;\n}\nclass f5 {\n  /**\n   * Read the current language of the user in IETF Language Tag format\n   */\n  get language() {\n    return m3();\n  }\n  /**\n   * Register translations for the module, may override app's existing translations\n   */\n  register(t) {\n    const n = {};\n    for (const r in t)\n      for (const o in t[r])\n        n[o] = n[o] || {}, n[o][r] = t[r][o];\n    for (const r in n)\n      h3(r, n[r]);\n  }\n  /**\n   * Perform a translation, with optional variables\n   * @param key - The key to translate\n   * @param variables - Optional variables to interpolate into the translation\n   */\n  translate(t, n) {\n    return C(t, n);\n  }\n  humanizeTime(t) {\n    return I8(t, this);\n  }\n}\nexport {\n  C8 as AudioPlayerView,\n  N8 as AvatarWithDetails,\n  rr as Banner,\n  k8 as BaseViewModel,\n  o5 as Box,\n  Ol as Clock,\n  K8 as DecryptionFailureBodyView,\n  tE as DecryptionFailureReason,\n  J8 as DisambiguatedProfileView,\n  zh as Disposables,\n  $8 as EventTileBubble,\n  Q as Flex,\n  Q8 as HistoryVisibilityBadge,\n  f5 as I18nApi,\n  Bf as I18nContext,\n  _7 as KEY_SEPARATOR,\n  Uh as MediaBody,\n  Dh as MockViewModel,\n  bh as MoreOptionContent,\n  s8 as NotificationDecoration,\n  Y8 as Pill,\n  W8 as PillInput,\n  am as PlayPauseButton,\n  G8 as ReactionsRowButtonTooltipView,\n  X8 as RichItem,\n  e5 as RichList,\n  a8 as RoomListEmptyStateView,\n  t5 as RoomListHeaderView,\n  _8 as RoomListItemContextMenu,\n  b8 as RoomListItemHoverMenu,\n  c8 as RoomListItemMoreOptionsMenu,\n  l8 as RoomListItemNotificationMenu,\n  E8 as RoomListItemView,\n  t8 as RoomListLoadingSkeleton,\n  QE as RoomListPrimaryFilters,\n  n5 as RoomListSearchView,\n  r5 as RoomListView,\n  Ae as RoomNotifState,\n  or as RoomStatusBarState,\n  Z8 as RoomStatusBarView,\n  H8 as SasEmoji,\n  u7 as SeekBar,\n  Bh as Snapshot,\n  U8 as TextualEventView,\n  V8 as TimelineSeparator,\n  Fh as ViewModelSubscriptions,\n  T8 as VirtualizedList,\n  A8 as VirtualizedRoomListView,\n  h5 as VirtuosoMockContext,\n  i5 as WidgetContextMenuView,\n  C as _t,\n  D8 as _tDom,\n  B8 as _td,\n  s5 as clamp,\n  a5 as defaultNumber,\n  sm as formatBytes,\n  lv as formatSeconds,\n  v3 as getLangsJson,\n  m3 as getLocale,\n  v1 as getNormalizedLanguageKeys,\n  I8 as humanizeTime,\n  F8 as lookupString,\n  b7 as normalizeLanguageKey,\n  u5 as percentageOf,\n  l5 as percentageWithin,\n  h3 as registerTranslations,\n  wf as replaceByRegexes,\n  q8 as sanitizeForTranslation,\n  L8 as setLanguage,\n  z8 as setLocale,\n  x8 as setMissingEntryGenerator,\n  M1 as substitute,\n  c5 as sum,\n  GE as useCollapseFilters,\n  R8 as useCreateAutoDisposedViewModel,\n  Pe as useI18n,\n  M8 as useMockedViewModel,\n  me as useViewModel,\n  VE as useVisibleFilters\n};\n"],"names":["_path","_path2","_path3","_path4","_extends","Object","assign","bind","n","e","arguments","length","t","r","hasOwnProperty","call","apply","SvgEmailPrompt","props","ref","xmlns","viewBox","role","fill","d","fillOpacity","ForwardRef","forwardRef","_defs","_g","SvgIconEmailPillAvatar","id","width","height","x","y","filterUnits","dy","result","stdDeviation","values","fillRule","stroke","strokeLinecap","strokeLinejoin","filter","transform","cx","cy","SvgLiveLocation","clipRule","module","exports","__webpack_public_path__","MediaPreviewValue","MEDIA_PREVIEW_ACCOUNT_DATA_TYPE","AVATAR_BG_LIGHT_COLORS","AVATAR_TEXT_LIGHT_COLORS","AVATAR_BG_DARK_COLORS","AVATAR_TEXT_DARK_COLORS","avatarUrlForMember","member","resizeMethod","url","getMxcAvatarUrl","mediaFromMxc","getThumbnailOfSourceHttp","defaultAvatarUrlForString","userId","isDarkTheme","ThemeWatcher","getEffectiveTheme","getAvatarTextColor","index","useIdColorHash","avatarUrlForUser","user","avatarUrl","colorToDataURLCache","Map","s","colorIndex","cssVariable","color","getComputedStyle","document","body","getPropertyValue","dataUrl","get","startsWith","slice","split","some","c","isNaN","parseInt","isValidHexColor","canvas","createElement","ctx","getContext","fillStyle","fillRect","toDataURL","urlForColor","set","getInitialLetter","name","console","trace","initial","substring","getFirstGrapheme","toUpperCase","avatarUrlForRoom","room","avatarMxcOverride","mxc","media","undefined","srcHttp","isSpaceRoom","DMRoomMap","shared","getUserIdForRoomId","roomId","isLocalRoom","otherMember","getAvatarFallbackMember","getPickleAdditionalData","deviceId","additionalData","Uint8Array","i","charCodeAt","async","getConfig","configJsonFilename","URL","window","location","href","searchParams","Date","now","toString","res","fetch","cache","method","status","ok","json","SSO_HOMESERVER_URL_KEY","SSO_ID_SERVER_URL_KEY","SSO_IDP_ID_KEY","UpdateCheckStatus","UPDATE_DEFER_KEY","BasePlatform","constructor","_defineProperty","Promise","resolve","dis","register","this","onAction","startUpdateCheck","relativeLocation","endsWith","domain","hostname","trimEnd","specificConfigPromise","generalConfigPromise","configJson","keys","Error","getVectorConfig","payload","action","Action","ClientNotViable","OnLoggedOut","setNotificationCount","count","notificationCount","updateFavicon","setErrorStatus","errorDidOccur","canSelfUpdate","hideUpdateToast","localStorage","removeItem","dispatch","CheckUpdates","Checking","installUpdate","shouldShowUpdate","newVersion","MatrixClientPeg","userRegisteredWithinLastHours","version","deferUntil","JSON","parse","getItem","deferUpdate","date","setHours","setItem","stringify","getTime","supportsSpellCheckSettings","allowOverridingNativeContextMenus","supportsNotifications","maySendNotifications","displayNotification","title","msg","ev","notifBody","silent","notification","Notification","onclick","ViewRoom","room_id","metricsTrigger","getThread","event_id","getId","focus","closeHandler","close","once","MatrixEventEvent","BeforeRedaction","onclose","off","loudNotification","clearNotification","notif","needsUrlTooltips","supportsSetting","settingName","getSettingValue","setSettingValue","value","getEventIndexingManager","setLanguage","preferredLangs","setSpellCheckEnabled","enabled","getSpellCheckEnabled","setSpellCheckLanguages","getSpellCheckLanguages","getDesktopCapturerSources","options","supportsDesktopCapturer","supportsJitsiScreensharing","overrideBrowserShortcuts","navigateForwardBack","back","getAvailableSpellCheckLanguages","getSSOCallbackUrl","fragmentAfterLogin","hash","startSingleSignOn","mxClient","loginType","idpId","getHomeserverUrl","getIdentityServerUrl","callbackUrl","getSsoLoginUrl","getPickleKey","_await$buildAndEncode","data","idbLoad","logger","error","_crypto2","crypto","subtle","encrypted","iv","cryptoKey","pickleKeyBuf","decrypt","encodeUnpaddedBase64","buildAndEncodePickleKey","createPickleKey","randomArray","getRandomValues","pickleKey","_crypto","generateKey","encrypt","encryptPickleKey","idbSave","destroyPickleKey","idbDelete","clearStorage","sessionStorage","clear","baseUrl","origin","pathname","defaultOidcClientUri","getOidcClientMetadata","_config$oidc_metadata","_config$oidc_metadata2","_config$oidc_metadata3","_config$oidc_metadata4","_config$oidc_metadata5","_config$oidc_metadata6","_config$oidc_metadata7","_config$terms_and_con","_config$oidc_metadata8","_config$oidc_metadata9","config","SdkConfig","clientName","brand","clientUri","oidc_metadata","client_uri","redirectUris","getOidcCallbackUrl","logoUri","logo_uri","applicationType","contacts","tosUri","tos_uri","terms_and_conditions_links","policyUri","policy_uri","privacy_policy_url","getOidcClientState","favicon","_favicon","Favicon","badge","bgColor","startUpdater","MINUTE_MS","HOUR_MS","DAY_MS","getDaysArray","weekday","format","Intl","DateTimeFormat","getUserLanguage","timeZone","Array","map","day","getTwelveHourOptions","showTwelveHour","hourCycle","formatDate","locale","_locale","toDateString","formatTime","_objectSpread","hour","minute","getUserTimezone","getFullYear","month","formatFullDate","formatFullDateNoTime","year","showSeconds","second","formatDateForInput","padStart","getMonth","getDate","formatFullTime","formatTimeLeft","inSeconds","hours","Math","floor","toFixed","minutes","seconds","_t","withinPast24Hours","prevDate","nextDate","abs","wantsDateSeparator","prevEventDate","nextEventDate","getDay","formatFullDateNoDay","toLocaleDateString","replace","time","toLocaleTimeString","formatFullDateNoDayISO","toISOString","formatFullDateNoDayNoTime","formatRelativeTime","relativeDate","m","UTC","getMonthsArray","withinCurrentYear","formatDuration","durationMs","round","formatPreciseDuration","days","formatLocalDateShort","timestamp","editorRoomKey","context","editorStateKey","eventId","SURROGATE_PAIR_PATTERN","SYMBOL_PATTERN","EMOJI_SEPARATOR_REGEX","EMOJI_REGEX","RegExp","BIGEMOJI_REGEX","source","mightContainEmoji","str","test","unicodeToShortcode","char","_getEmojiFromUnicode","shortcodes","getEmojiFromUnicode","sanitizedHtmlNode","insaneHtml","saneHtml","sanitizeHtml","sanitizeHtmlParams","React","dangerouslySetInnerHTML","__html","dir","getHtmlText","allowedTags","allowedAttributes","selfClosing","allowedSchemes","disallowedTagsMode","isUrlPermitted","inputUrl","PERMITTED_URL_SCHEMES","includes","protocol","composerSanitizeHtmlParams","transformTags","topicSanitizeHtmlParams","BaseHighlighter","highlightClass","highlightLink","applyHighlights","safeSnippet","safeHighlights","offset","lastOffset","nodes","safeHighlight","toLowerCase","indexOf","subSnippet","concat","applySubHighlights","endOffset","push","processSnippet","HtmlHighlighter","snippet","highlight","span","encodeURI","emojiToHtmlSpan","emoji","emojiToJsxSpan","key","className","formatEmojis","message","isHtmlMessage","emojiToSpan","text","graphemeSegmenter","segment","analyseEvent","content","highlights","opts","_sanitizeParams$trans","sanitizeParams","_sanitizeParams","_sanitizeParams$allow","_sanitizeParams$allow2","_sanitizeParams$allow3","forComposerQuote","mediaIsVisible","img","tagName","attribs","linkify","allowedClasses","a","isFormattedBody","formatted_body","safeBody","bodyHasEmoji","formattedBody","plainBody","stripReplyFallback","stripHTMLReply","strippedBody","stripPlainReply","highlighter","textFilter","safeText","join","unsafeBody","linkifyHtml","phtml","DOMParser","parseFromString","innerHTML","textContent","SettingsStore","getValue","querySelectorAll","forEach","outerHTML","katex","decode","getAttribute","throwOnError","displayMode","output","escapeHtml","bodyToNode","eventInfo","emojiBody","disableBigEmoji","_eventInfo$safeBody","_match$","contentBody","contentBodyTrimmed","trim","match","exec","classNames","emojiBodyElements","bodyToHtml","topicToHtml","topic","htmlTopic","allowExtendedHtml","isFormattedTopic","topicHasEmoji","safeTopic","checkBlockNode","node","nodeName","hasAttribute","BugReportEndpointURLLocal","AbortedIdentityActionError","IdentityAuthClient","identityUrl","tempClient","createClient","idBaseUrl","identityClient","_this$tempClient","matrixClient","safeGet","writeToken","accessToken","readToken","getAccessToken","check","authEnabled","token","registerForToken","checkToken","TermsNotSignedError","identityServerUrl","getIdentityAccount","MatrixError","errcode","log","startTermsFlow","Service","SERVICE_TYPES","IS","doesAccountDataHaveIdentityServer","doesIdentityServerHaveTerms","finished","Modal","createDialog","QuestionDialog","description","server","abbreviateUrl","button","confirmed","setToDefaultIdentityServer","hsOpenIdToken","getOpenIdToken","access_token","registerWithIdentityServer","identityAccessToken","getBindingsByCategory","category","CATEGORIES","settingNames","reduce","bindings","_getKeyboardShortcuts","keyCombo","getKeyboardShortcuts","default","defaultBindingsProvider","getMessageComposerBindings","messageComposerBindings","CategoryName","COMPOSER","KeyBindingAction","SendMessage","Key","ENTER","ctrlOrCmdKey","NewLine","shiftKey","IS_MAC","altKey","getAutocompleteBindings","autocompleteBindings","AUTOCOMPLETE","ForceCompleteAutocomplete","TAB","ctrlKey","CompleteAutocomplete","getRoomListBindings","roomListBindings","ROOM_LIST","getRoomBindings","roomBindings","ROOM","SearchInRoom","F","getNavigationBindings","navigationBindings","NAVIGATION","getAccessibilityBindings","accessibilityBindings","ACCESSIBILITY","getCallBindings","callBindings","CALLS","getLabsBindings","labsBindings","LABS","isKeyComboMatch","combo","onMac","_combo$ctrlKey","_combo$altKey","_combo$shiftKey","_combo$metaKey","_ev$ctrlKey","_ev$altKey","_ev$shiftKey","_ev$metaKey","comboCtrl","comboAlt","comboShift","comboMeta","metaKey","evCtrl","evAlt","evShift","evMeta","manager","getAction","getters","getter","binding","find","it","getMessageComposerAction","bindingsProviders","getAutocompleteAction","getRoomListAction","getRoomAction","getNavigationAction","getAccessibilityAction","getCallAction","getLabsAction","getKeyBindingsManager","HOME","END","PAGE_UP","PAGE_DOWN","BACKSPACE","DELETE","ARROW_UP","ARROW_DOWN","ARROW_LEFT","ARROW_RIGHT","F6","ESCAPE","ALT","CONTROL","META","SHIFT","CONTEXT_MENU","COMMA","PERIOD","LESS_THAN","GREATER_THAN","BACKTICK","SPACE","SLASH","SQUARE_BRACKET_LEFT","SQUARE_BRACKET_RIGHT","SEMICOLON","A","B","C","D","E","G","H","I","J","K","L","M","N","O","P","Q","R","S","T","U","V","W","X","Y","Z","navigator","platform","IS_ELECTRON","electron","isOnlyCtrlOrCmdKeyEvent","IncomingLegacyCallToast","super","LegacyCallHandler","instance","addListener","LegacyCallHandlerEvent","SilencedCallsChanged","onSilencedCallsChanged","setState","silenced","isCallSilenced","callId","stopPropagation","answerCall","hangupOrReject","state","unSilenceCall","silenceCall","roomIdForCall","componentWillUnmount","removeListener","render","getRoom","isVoice","type","CallType","Voice","callForcedSilent","isForcedSilent","silenceButtonTooltip","RoomAvatar","size","getCallStateIcon","AccessibleButton","onClick","onRejectClick","kind","EndCallIcon","onAnswerClick","VoiceCallSolidIcon","VideoCallSolidIcon","disabled","onSilenceClick","VolumeOffSolidIcon","VolumeOnSolidIcon","PROTOCOL_PSTN","PROTOCOL_PSTN_PREFIXED","MEDIA_ERROR_EVENT_TYPES","MEDIA_EVENT_TYPES","AudioID","TypedEventEmitter","args","Set","BackgroundAudio","_MatrixClientPeg$get","_cli$getCrypto","supportsVoip","mappedRoomId","getCallForRoom","addCallForRoom","setCallListeners","onCallStateChanged","cli","getCrypto","prepareToEncrypt","newState","oldState","matchesCallForThisRoom","setCallState","CallState","Ringing","pause","Ring","InviteSent","Ringback","silencedCalls","delete","incomingCallPushRule","pushProcessor","getPushRuleById","RuleId","IncomingCall","pushRuleEnabled","tweakSetToRing","actions","set_tweak","TweakName","Sound","play","Ended","hangupReason","isNotNull","removeCallForRoom","hangupParty","CallParty","Remote","Busy","CallErrorCode","UserHangup","UserBusy","ErrorDialog","AnsweredElsewhere","Connecting","Fledgling","CallEnd","logCallStats","mxLegacyCallHandler","_call$roomId","shouldObeyAssertedfIdentity","nativeUser","assertedIdentityNativeUsers","findDMForUser","start","UIFeature","Voip","on","CallEventHandlerEvent","Incoming","onCallIncoming","checkProtocols","stop","handleEvent","target","audioId","debuglog","localNotificationsAreSilenced","add","emit","areAnyCallsUnsilenced","has","calls","setCallSidebarShown","sidebarShown","shownSidebars","ShownSidebarsChanged","isCallSidebarShown","_this$shownSidebars$g","maxTries","protocols","getThirdpartyProtocols","supportsPstnProtocol","Boolean","pstnSupportPrefixed","ProtocolSupport","setTimeout","_SdkConfig$getObject","getObject","getSupportsPstnProtocol","_this$supportsPstnPro","pstnLookup","phoneNumber","getThirdpartyUser","warn","getCallById","getAllActiveCalls","activeCalls","getAllActiveCallsNotInRoom","notInThisRoomId","callsNotInThatRoom","entries","getAllActiveCallsForPip","WidgetLayoutStore","hasMaximisedWidget","getTransfereeForCallId","transferees","logPrefix","debug","audioInfo","urlPrefix","loop","backgroundAudio","pickFormatAndPlay","playingSources","isPlaying","callForThisRoom","CallEvent","err","code","NoUserMedia","getTurnServers","showICEFallbackPrompt","showMediaCaptureError","Hangup","State","Replaced","newCall","AssertedIdentityChanged","_call$getRemoteAssert","getRemoteAssertedIdentity","newAssertedIdentity","ensureDMExists","newMappedRoomId","stats","getCurrentCallStats","direction","ourPartyId","cand","item","address","ip","candidateType","port","relayProtocol","networkType","pair","localCandidateId","remoteCandidateId","nominated","requestsSent","requestsReceived","responsesReceived","responsesSent","bytesReceived","bytesSent","toastKey","ToastStore","sharedInstance","addOrReplaceToast","priority","component","bodyClassName","dismissToast","CallsChanged","homeserverDomain","getDomain","sub","FALLBACK_ICE_SERVER","cancelButton","then","allow","setValue","SettingLevel","DEVICE","Video","placeMatrixCall","transferee","timeUntilTurnCresExpire","getTurnServersExpiry","createCall","setActiveCallRoomId","placeVoiceCall","placeVideoCall","placeCall","isManagedHybridWidgetEnabled","addManagedHybridWidget","getSyncState","SyncState","members","getJoinedNonFunctionalMembers","Jitsi","getInstance","useFor1To1Calls","placeJitsiCall","info","hangupAllCalls","stopRingingIfPossible","hangup","reject","answer","dialNumber","number","results","userid","startTransferToPhoneNumber","destination","consultFirst","startTransferToMatrixID","dmRoomId","should_peek","joining","transfer","activeCallRoomId","setRemoteOnHold","hasAnyUnheldCall","isRemoteOnHold","client","show","widget","WidgetStore","getApps","app","WidgetType","JITSI","matches","moveToContainer","Container","Top","WidgetUtils","addJitsiWidget","hangupCallApp","roomInfo","widgets","w","messaging","WidgetMessagingStore","getMessagingForUid","getWidgetUid","widgetApi","transport","send","ElementWidgetActions","HangupCall","showTransferDialog","OpenInviteDialog","InviteKind","CallTransfer","analyticsName","onFinishedCallback","changedRooms","CallChangeRoom","COLOR_REGEX","MEDIA_API_MXC_REGEX","tryTransformPermalinkToLocalHref","ELEMENT_URL_PATTERN","rel","src","requestedWidth","Number","requestedHeight","min","style","class","classes","cl","customCSSMapper","customAttributeKey","cssAttributeKey","customAttributeValue","font","div","ol","allowProtocolRelative","nestingLimit","Linkify","as","children","_Linkify","merge","linkifyMatrixOptions","_linkifyHtml","linkifyAndSanitizeHtml","dirtyHtml","_linkifyString","linkifyString","ALLOWED_HTML_TAGS","TEXT_NODES","isAllowedHtmlTag","literal","tag","isMultiLine","par","parent","firstChild","lastChild","getTextUntilEndOrLinebreak","currentNode","next","formattingChangesByNodeType","emph","strong","innerNodeLiteral","walker","step","currentNodeLiteral","entering","emptyItemWithNoSiblings","prev","Markdown","input","parser","commonmark","parsed","repairLinks","event","isInPara","previousNode","shouldUnlinkFormattingNode","_previousNode","thisPart","nextParts","reverse","part","nextNode","insertAfter","resumeAt","foundLinks","_node$firstChild","nonEmphasizedText","newText","emphasisTextNode","unlink","isPlainText","toHTML","externalLinks","renderer","safe","softbreak","realParagraph","paragraph","_node$parent","link","attrs","esc","html_inline","lit","escape","html_block","toPlaintext","createSyncAction","prevState","createAccountDataAction","accountDataEvent","previousAccountDataEvent","event_type","getType","event_content","getContent","previousEvent","createRoomAccountDataAction","createRoomAction","createRoomTagsAction","roomTagsEvent","createRoomReceiptAction","createRoomTimelineAction","timelineEvent","toStartOfTimeline","removed","isLiveEvent","liveEvent","isLiveUnfilteredRoomTimelineEvent","timeline","getTimelineSet","getUnfilteredTimelineSet","createRoomStateEventsAction","lastStateEvent","createSelfMembershipAction","membership","oldMembership","createEventDecryptedAction","matrixClientListenersStop","addMatrixClientListener","eventName","actionCreator","listener","ClientEvent","Sync","AccountData","RoomEvent","Room","Tags","Receipt","Timeline","MyMembership","Decrypted","RoomStateEvent","Events","stopListener","initialSyncLimit","_PlatformPeg$get2","stopClient","store","destroy","isGuest","_PlatformPeg$get","PlatformPeg","getHumanReadableName","reload","UserFriendlyError","unset","MatrixActionCreators","setJustRegisteredUserId","uid","justRegisteredUserId","registrationTime","currentUserIsJustRegistered","credentials","userRegisteredAfter","replaceUsingCreds","creds","tokenRefreshFunction","assignOpts","_this$matrixClient$st","_this$matrixClient$st2","dbType","promise","startup","MemoryStore","onUnexpectedStoreClose","initClientCrypto","rustCryptoStoreKey","rustCryptoStorePassword","utils","pendingEventOrdering","PendingEventOrdering","Detached","lazyLoadMembers","clientWellKnownPollPeriod","threadSupport","slidingSync","SlidingSyncManager","setup","checkSupport","MatrixClientBackedSettingsHandler","MatrixClientBackedController","initRustCrypto","storageKey","storagePassword","StorageManager","setDeviceIsolationMode","initialiseDehydrationIfEnabled","onlyIfKeyCached","rehydrate","startClient","namesToRoomName","names","countWithoutMe","memberNamesToRoomName","formatList","inviteeNamesToRoomName","user1","user2","homeserverUrl","refreshToken","timelineSupport","forceTURN","fallbackICEServerAllowed","iceCandidatePoolSize","verificationMethods","VerificationMethod","Sas","ShowQrCode","Reciprocate","identityServer","cryptoCallbacks","crossSigningCallbacks","enableEncryptedStateEvents","roomNameGenerator","_","RoomNameType","Generated","subtype","EmptyRoom","oldName","createMatrixClient","setGuest","guest","notifTimelineSet","EventTimelineSet","pendingEvents","getLiveTimeline","setPaginationToken","EventTimeline","BACKWARDS","setNotifTimelineSet","mxMatrixClientPeg","MediaDeviceKindEnum","MediaDeviceHandlerEvent","MediaDeviceHandler","EventEmitter","internalInstance","hasAnyLabeledDevices","mediaDevices","enumerateDevices","label","getDevices","devices","AudioOutput","AudioInput","VideoInput","device","loadDevices","audioDeviceId","videoDeviceId","getMediaHandler","setAudioInput","setVideoInput","updateAudioSettings","setAudioSettings","autoGainControl","getAudioAutoGainControl","echoCancellation","getAudioEchoCancellation","noiseSuppression","getAudioNoiseSuppression","setAudioOutput","AudioOutputChanged","setDevice","setAudioAutoGainControl","setAudioEchoCancellation","setAudioNoiseSuppression","getAudioOutput","getValueAt","getAudioInput","getVideoInput","getDevice","startWithAudioMuted","startWithVideoMuted","unshift","AsyncWrapper","getDerivedStateFromError","BaseDialog","onFinished","DialogButtons","primaryButton","onPrimaryButtonClick","hasCancel","Suspense","fallback","Spinner","ModalManagerEvent","getOrCreateContainer","container","getElementById","appendChild","ModalManager","getOrCreateRoot","root","createRoot","getOrCreateStaticRoot","staticRoot","forceCloseAllModals","modal","getCurrentModal","closeReason","defaultDispatcher","toggleCurrentDialogVisibility","hidden","hasDialogs","priorityModal","staticModal","modals","closeCurrentModal","reason","filterBoolean","_modal$deferred","deferred","emitClosed","reRender","buildModal","Component","onBeforeClose","elem","closeDialog","onFinishedProm","getCloseFn","modalCount","counter","withResolvers","_modal$deferred2","beforeClosePromise","shouldClose","splice","isPriorityModal","isStaticModal","beforeModal","emitIfChanged","appendDialog","Opened","Closed","staticDialog","StrictMode","TooltipProvider","Glass","onBackgroundClick","mx_Dialog_wrapperWithStaticUnder","dialog","singletonModalManager","getNotificationEventSendTs","sendTs","sender_ts","getTs","JoinCallButtonWithCall","disabledTooltip","isRinging","Tooltip","Button","Icon","CheckIcon","DeclineCallButtonWithNotificationEvent","notificationEvent","onDeclined","declining","setDeclining","useState","useCallback","_notificationEvent$ge","sendRtcDecline","destructive","CloseIcon","IncomingCallToast","_MatrixClientPeg$safe","getRoomId","notificationContent","useCall","connectedCalls","setConnectedCalls","from","CallStore","useEventEmitter","CallStoreEvent","ConnectedCalls","otherCallIsOngoing","soundHasStarted","useRef","useEffect","notification_type","current","useTypedEventEmitter","_ev$getRelation","getRelation","onCall","callRoomId","participants","onTimelineChange","getUserId","EventType","RTCDecline","getSender","relationEventId","onParticipantChange","prevParticipants","p","_notificationContent$","lifetime","timeout","clearTimeout","useDispatcher","view_call","skipLobbyToggle","setSkipLobbyToggle","onJoinClick","skipLobby","voiceOnly","onCloseClick","Call","Participants","otherUserId","participantCount","useParticipantCount","detailsInformation","LiveContentSummary","LiveContentType","active","VoiceCallIcon","position","top","VideoCallIcon","AvatarWithDetails","avatar","details","ToggleInput","onChange","checked","msgTypeHandlers","MsgType","KeyVerificationRequest","_event$sender","sender","M_LOCATION","TextForEvent","altName","Audio","NotifierEvent","NotifierClass","Syncing","isSyncing","Stopped","fromCache","createLocalNotificationSettingsIfNeeded","threadListType","decryptEventIfNeeded","isBeingDecrypted","isDecryptionFailure","pendingEncryptedEventIds","shift","evaluateEvent","idx","getUnreadNotificationCount","plaf","notifsByRoom","notificationMessageForEvent","msgType","msgtype","displayPopupNotification","isBodyEnabled","Avatar","getSoundForRoom","playAudioNotification","sound","onEvent","onRoomReceipt","onEventDecrypted","onSyncStateChange","toolbarHidden","supportsDesktopNotifications","_PlatformPeg$get$supp","setEnabled","enable","callback","isLevelSupported","isEnabled","requestNotificationPermission","PosthogAnalytics","trackEvent","permission","granted","setPromptHidden","isPossible","isAudioEnabled","persistent","hideNotificationsToast","global","String","NotificationHiddenChange","shouldShowPrompt","isPushNotifyDisabled","isPromptHidden","getPushActionsForEvent","notify","performCustomEventHandling","SdkContextClass","roomViewStore","isViewingRoom","threadId","threadRootId","isViewingThread","getThreadId","UserActivity","userActiveRecently","tweaks","handleRTCNotification","toaster","_rtcSession$slotDescr","_callMembership$getCo","rtcSession","matrixRTC","getRoomSession","slotDescription","application","memberships","referencedMembershipEventId","rel_type","callMembership","findEventById","MatrixEvent","fetchRoomEvent","ex","getIncomingCallToastKey","call_id","hasToast","RTCNotification","mxNotifier","Notifier","PageType","platformPromise","platformPromiseWithResolvers","mxPlatformPeg","Anonymity","whitelistedScreens","_instance","posthog","Disabled","layout","Layout","IRC","Bubble","Group","setProperty","SettingUpdated","onLayoutUpdated","properties","lastScreen","anonymity","Anonymous","posthogConfig","init","api_host","autocapture","mask_all_text","mask_all_element_attributes","capture_pageview","sanitize_properties","sanitizeProperties","respect_dnt","advanced_disable_decide","monitorSetting","updateCryptoSuperProperty","registerSuperProperties","getPlatformProperties","appVersion","getAppVersion","appPlatform","capture","hashStr","beforeFirstSlash","screen","getRedactedCurrentLocation","propertiesForNextEvent","setAnonymity","reset","platformSuperProperties","getRandomAnalyticsId","identifyUser","analyticsIdGenerator","Pseudonymous","_this$posthog$persist","accountData","getAccountDataFromServer","ANALYTICS_EVENT_TYPE","analyticsID","setAccountData","get_distinct_id","persistence","get_property","identify","getAnonymity","logout","unwatchSetting","watchSettingRef","_ref","_objectWithoutProperties","_excluded","userPropertyCache","setPropertyOnce","updatePlatformSuperProperties","currentCryptoBackend","cryptoSDK","updateAnonymityFromSettings","pseudonymousOptIn","getVersion","trackNewUserEvent","startListeningToSettingsChanges","watchSetting","originalSettingName","changedInRoomId","atLevel","newValueAtLevel","newValue","setAuthenticationType","authenticationType","notLoggedInMap","Views","LOADING","CONFIRM_LOCK_THEFT","WELCOME","LOGIN","REGISTER","FORGOT_PASSWORD","COMPLETE_SECURITY","E2E_SETUP","PENDING_CLIENT_START","SOFT_LOGOUT","LOCK_STOLEN","loggedInPageTypeMap","HomePage","RoomView","UserView","PosthogTrackers","trackPageChange","view","pageType","override","trackPage","screenName","LOGGED_IN","$current_url","trackOverride","clearOverride","trackInteraction","interactionType","trackPinUnpinMessage","PosthogScreenTracker","PureComponent","componentDidMount","componentDidUpdate","Resend","resendUnsentEvents","all","getPendingEvents","EventStatus","NOT_SENT","resend","cancelUnsentEvents","removeFromQueue","resendEvent","cancelPendingEvent","levelRoleMap","usersDefault","textualPowerLevel","level","LEVEL_ROLE_MAP","storeRoomAliasInCache","alias","viaServers","getCachedRoomIdForAlias","inviteMultipleToRoom","addresses","inviter","MultiInviter","states","invite","showStartChatInviteDialog","initialText","InviteDialog","Dm","showRoomInviteDialog","Invite","isValid3pidInvite","RoomThirdPartyInvite","showAnyInviteErrors","userMap","failedUsers","fatal","roomName","getErrorText","errorList","addr","RoomName","_getMxcAvatarUrl","_ref2","getUser","rawDisplayName","BaseAvatar","getSquareThumbnailHttp","idName","RoomNotifState","getRoomNotifsState","_roomRule","AllMessages","findOverrideMuteRule","Mute","roomRule","getRoomPushRule","isMuteRule","MentionsOnly","PushProcessor","actionListToActionsObject","AllMessagesLoud","setRoomNotifsState","promises","deletePushRule","PushRuleKind","RoomSpecific","rule_id","addPushRule","Override","conditions","ConditionKind","EventMatch","pattern","PushRuleActionName","DontNotify","setRoomNotifsStateMuted","overrideMuteRule","Notify","setRoomNotifsStateUnmuted","includeThreads","getCountShownForRoom","getRoomUnreadNotificationCount","getThreadUnreadNotificationCount","msc3946ProcessDynamicPredecessor","predecessor","findPredecessor","oldRoomId","oldRoom","NotificationCountType","Highlight","_cli$pushRules","pushRules","rule","isRuleRoomMuteRuleForRoomId","isRuleMaybeRoomMuteRule","_rule$conditions","determineUnreadState","symbol","NotificationLevel","None","invited","getUnsentMessages","Unsent","getEffectiveMembership","getMyMembership","EffectiveMembership","isKnockDenied","redNotifs","greyNotifs","Total","trueCount","markedUnreadState","getMarkedUnreadState","hasUnread","thread","doesRoomOrThreadHaveUnreadMessages","doesRoomHaveUnreadMessages","Activity","getDisplayAliasForRoom","getDisplayAliasForAliasSet","getCanonicalAlias","getAltAliases","canonicalAlias","altAliases","AliasCustomisations","guessAndSetDMRoom","isDirect","newTarget","myUserId","oldestTs","oldestUser","getJoinedMembers","_user$events$member","events","currentState","getMembers","_user$events$member2","guessDMRoomTargetId","getSafeUserId","setDMRoom","_mDirectEvent$getCont","mDirectEvent","getAccountData","Direct","filteredContent","filterValidMDirect","thisUserId","DEFAULTS","help_url","help_encryption_url","help_key_storage_url","integrations_ui_url","integrations_rest_url","uisi_autorageshake_app","show_labs_settings","force_verification","jitsi","preferred_domain","element_call","use_exclusively","desktopBuilds","available","logo","require","feedback","existing_issues_url","new_issue_url","desktop_builds","url_macos","url_win64","url_win64arm","url_linux","mobile_builds","ios","android","fdroid","mergeConfig","changes","mergeWith","objectClone","objValue","srcValue","isArray","isObject","setInstance","SnakedObject","mxReactSdkConfig","altCaseName","val","put","cfg","parseSsoRedirectOptions","sso_redirect_options","sso_immediate_redirect","immediate","AccessSecretStorageDialog","debounce","validateRecoveryKey","recoveryKey","validateRecoveryKeyOnChange","preventDefault","keyParams","_this$inputRef$curren","inputRef","recoveryKeyCorrect","_this$props$keyInfo","_this$props$keyInfo2","hasPassphrase","keyInfo","passphrase","salt","iterations","checkPrivateKey","getRecoveryKeyFeedback","ErrorSolidIcon","Flex","align","recoveryKeyFeedback","onSubmit","onRecoveryKeyNext","spellCheck","autoComplete","PasswordInput","placeholder","onRecoveryKeyChange","autoFocus","EncryptionCardButtons","onCancel","fixedWidth","EncryptionCard","LockSolidIcon","secretStorageKeys","secretStorageKeyInfo","secretStorageBeingAccessed","rootLogger","getChild","isSecretStorageBeingAccessed","AccessCancelledError","cacheSecretStorageKey","keyId","getSecretStorageKey","keyInfos","secretName","defaultKeyId","secretStorage","getDefaultKeyId","usefulKeys","keyFromCustomisations","ModuleRunner","extensions","cryptoSetup","inputToKey","deriveRecoveryKeyFromPassphrase","decodeRecoveryKey","makeInputToKey","checkKey","withSecretStorageKeyCache","func","accessSecretStorage","forceReset","lazy","hasKey","bootstrapCrossSigning","authUploadDeviceSigningKeys","InteractiveAuthDialog","makeRequest","bootstrapSecretStorage","catchAccessSecretStorageError","doAccessSecretStorage","SendHistoryManager","prefix","itemJSON","history","lastIndex","currentIndex","createItem","model","replyEvent","parts","serializeParts","replyEventId","save","editorModel","clamp","REQUIRED_STATE_LIST","RoomJoinRules","RoomCanonicalAlias","RoomTombstone","RoomEncryption","RoomCreate","SpaceChild","MSC3575_WILDCARD","SpaceParent","RoomMember","MSC3575_STATE_KEY_ME","DEFAULT_ROOM_SUBSCRIPTION_INFO","timeline_limit","include_old_rooms","required_state","UNENCRYPTED_SUBSCRIPTION_NAME","UNENCRYPTED_SUBSCRIPTION","MSC3575_STATE_KEY_LAZY","ENCRYPTED_SUBSCRIPTION","sssLists","spaces","ranges","filters","room_types","invites","is_invite","favourites","tags","dms","is_dm","not_tags","untagged","configure","proxyUrl","lists","listName","SlidingSync","addCustomSubscription","configureDefer","ensureListRegistered","listKey","updateArgs","list","getListParams","updatedList","sort","setListRanges","setList","setRoomVisible","_this$client","subscriptions","getRoomSubscriptions","shouldLazyLoad","_this$client2","isEncryptionEnabledInRoom","useCustomSubscription","modifyRoomSubscriptions","_this$client4","waitForRoom","_this$client3","startSpidering","batchSize","gapBetweenRequestsMs","listToUpperBound","lifecycle","SlidingSyncState","Complete","sleep","hasSetRanges","currentUpperBound","_slidingSync$getListD","getListData","joinedCount","newUpperBound","SlidingSyncEvent","Lifecycle","nativeSlidingSyncSupport","support","doesServerSupportUnstableFeature","serverSupportsSlidingSync","_SlidingSyncManager","LOCAL_STORAGE_KEY","TOAST_KEY","SUPPORTED_DEVICE_TYPES","DeviceType","Web","Desktop","onLearnMoreClick","onDismissClick","open","getBrowserNameVersion","browser","browserName","browserVersion","getBrowserSupport","browsers","browserlist","minimumBrowserVersions","parseUserAgent","userAgent","supported","deviceType","minimumVersion","checkBrowserSupport","secondaryLabel","SecondaryIcon","PopOutIcon","onSecondaryClick","primaryLabel","onPrimaryClick","GenericToast","TermsCheckbox","currentTarget","TermsDialog","agreedUrls","nameForServiceType","serviceType","host","IM","summaryForServiceType","rows","policiesAndService","policiesAndServicePairs","parsedBaseUrl","parseUrl","service","policyValues","policies","internationalisedPolicy","pickBestPolicyLanguage","serviceName","summary","ExternalLink","onTermsCheckboxChange","enableSubmit","docsAgreedForService","terms","docAgreed","lang","onCancelClick","contentId","onNextClick","primaryDisabled","policy","pickBestLanguage","k","services","interactionCallback","dialogTermsInteractionCallback","_client$getAccountDat","termsPromises","getTerms","currentAcceptedTerms","agreedUrlSet","accepted","unagreedPoliciesAndServicePairs","unagreedPolicies","policyName","policyAgreed","numAcceptedBeforeAgreement","newlyAgreedUrls","newAcceptedTerms","agreePromises","urlsForService","agreeToTerms","extraClassNames","done","_agreedUrls","getSenderName","_event$sender$name","getRoomMemberDisplayname","_client$getRoom","getMember","textForCallEvent","_client$getRoom2","Modification","getModification","Changed","Unset","onViewJoinRuleSettingsClick","initial_tab_id","RoomSettingsTab","Security","textForMessageEvent","isLocationEvent","textForLocationEvent","senderDisplayName","isRedacted","textForRedactedPollAndMessageEvent","Emote","Image","Sticker","onPinnedMessagesClick","RightPanelStore","setCard","phase","RightPanelPhases","PinnedMessages","textForMjolnirEvent","senderName","entity","prevEntity","getPrevContent","recommendation","USER_RULE_TYPES","glob","ROOM_RULE_TYPES","SERVER_RULE_TYPES","oldGlob","newGlob","_unsigned$redacted_be","unsigned","getUnsigned","redactedBecauseUserId","redacted_because","textForPollStartEvent","_event$unstableExtens","pollQuestion","unstableExtensibleEvent","question","textForPollEndEvent","handlers","RoomMessage","CallInvite","_event$getContent$off","offer","sdp","isSupported","M_POLL_START","M_POLL_END","stateHandlers","oldAlias","oldAltAliases","alt_aliases","newAlias","newAltAliases","removedAltAliases","addedAltAliases","oldRoomName","newRoomName","RoomTopic","ContentHelpers","allowJSX","showHiddenEvents","_ev$sender","_ev$target","targetName","getStateKey","prevContent","KnownMembership","threePidContent","third_party_invite","display_name","displayName","Ban","Join","modDisplayname","displayname","modAvatarUrl","avatar_url","oldDisplayName","removeDirectionOverrideChars","state_key","Leave","_ev$sender2","targetDisplayName","RoomHistoryVisibility","history_visibility","HistoryVisibility","Invited","Joined","Shared","WorldReadable","visibility","RoomPowerLevels","_event$getPrevContent","_event$getContent","users","previousUserDefault","users_default","currentUserDefault","diffs","isInteger","to","powerLevelDiffText","diff","fromPowerLevel","Roles","toPowerLevel","RoomPinnedEvents","pinned","previouslyPinned","newlyPinned","newlyUnpinned","messageId","pop","highlightEvent","b","join_rule","JoinRule","Public","Knock","Restricted","RoomGuestAccess","guest_access","GuestAccess","CanJoin","Forbidden","prevName","prevType","prevUrl","widgetName","WIDGET_LAYOUT_EVENT_TYPE","evType","ALL_RULE_TYPES","ElementCallEventType","hasText","handler","isState","textForEvent","_handler","USER_TIMEZONE_KEY","setUserTimezone","timezone","getAllTimezones","supportedValuesOf","shortBrowserTimezone","_Intl$DateTimeFormat$","_Intl$DateTimeFormat$2","timeZoneName","formatToParts","arg","isNotUndefined","eventTriggersUnreadCount","CallAnswer","CallHangup","RoomServerAcl","M_BEACON","haveRendererForEvent","toCheck","getThreads","withTimeline","doesTimelineHaveUnreadMessages","_findLatestImportantE","latestImportantEventId","isImportantEvent","findLatestImportantEvent","hasUserReadEvent","_timeline$at","earliestUnimportantEventId","at","doesRoomHaveUnreadThreads","roomOrThread","Thread","getEvents","shouldHideEvent","visibilityState","activeNowTimeout","abort","activeRecentlyTimeout","onUserActivity","hasFocus","isMouseEvent","screenX","lastScreenX","screenY","lastScreenY","isRunning","restart","runTimersUntilTimeout","attachedActiveNowTimers","attachedActiveRecentlyTimers","Timer","mxUserActivity","timeWhileActiveNow","timer","timeWhile","userActiveNow","timeWhileActiveRecently","attachedTimers","finally","catch","addEventListener","onPageVisibilityChanged","onWindowBlurred","passive","removeEventListener","emailRegex","mxUserIdRegex","mxRoomIdRegex","AddressType","getAddressType","inputText","Email","MatrixUserId","MatrixRoomId","WorkerManager","worker","pendingDeferredMap","seq","onmessage","onMessage","request","postMessage","getUIOnlyShortcuts","ctrlEnterToSend","keyboardShortcuts","_td","SwitchToSpaceByNumber","DIGITS","KEYBOARD_SHORTCUTS","_KEYBOARD_SHORTCUTS$k","controller","settingDisabled","MAC_ONLY_SHORTCUTS","DESKTOP_SHORTCUTS","o","getKeyboardShortcutsForUI","acc","getKeyboardShortcutValue","getKeyboardShortcutDisplayName","_getKeyboardShortcuts2","keyboardShortcutDisplayName","ALTERNATE_KEY_NAME","KEY_ICON","categoryLabel","FormatBold","FormatItalics","FormatQuote","FormatLink","FormatCode","EditUndo","EditRedo","MoveCursorToStart","MoveCursorToEnd","CancelReplyOrEdit","EditNextMessage","EditPrevMessage","SelectNextSendHistory","SelectPrevSendHistory","ShowStickerPicker","ToggleMicInCall","ToggleWebcamInCall","UploadFile","DismissReadMarker","JumpToOldestUnread","ScrollUp","ScrollDown","JumpToFirstMessage","JumpToLatestMessage","SelectRoomInRoomList","ClearRoomFilter","CollapseRoomListSection","ExpandRoomListSection","NextRoom","PrevRoom","Escape","Enter","Space","Backspace","Delete","Home","End","ArrowLeft","ArrowUp","ArrowRight","ArrowDown","Comma","Save","ToggleUserMenu","ToggleRoomSidePanel","ToggleSpacePanel","ShowKeyboardSettings","GoToHome","FilterRooms","SelectNextUnreadRoom","SelectPrevUnreadRoom","SelectNextRoom","SelectPrevRoom","OpenUserSettings","PreviousVisitedRoomOrSpace","NextVisitedRoomOrSpace","NextLandmark","PreviousLandmark","CancelAutocomplete","NextSelectionInAutocomplete","PrevSelectionInAutocomplete","ToggleHiddenEventVisibility","Landmark","ORDERED_LANDMARKS","ACTIVE_SPACE_BUTTON","ROOM_SEARCH","MESSAGE_COMPOSER_OR_HOME","LandmarkNavigation","getLandmark","currentLandmark","backwards","findIndex","l","findAndFocusNextLandmark","_element","landmark","element","landmarkToDomElementMap","focusVisible","querySelector","_document$activeEleme","inThread","activeElement","closest","FocusSendMessageComposer","TimelineRenderingType","RovingTabIndexWrapper","onFocus","isActive","useRovingTabIndex","RovingAccessibleButton","onMouseOver","focusOnMouseOver","onFocusInternal","tabIndex","checkInputableElement","el","RovingTabIndexContext","createContext","Type","nodeSorter","compareDocumentPosition","Node","DOCUMENT_POSITION_FOLLOWING","DOCUMENT_POSITION_CONTAINED_BY","DOCUMENT_POSITION_PRECEDING","DOCUMENT_POSITION_CONTAINS","reducer","Register","activeNode","Unregister","oldIndex","findSiblingElement","_state$activeNode","SetFocus","Update","startIndex","_nodes$i","offsetParent","_nodes$i2","RovingTabIndexProvider","handleHomeEnd","handleUpDown","handleLeftRight","handleLoop","handleInputFields","scrollIntoView","onKeyDown","useReducer","useMemo","onKeyDownHandler","defaultPrevented","handled","focusNode","Tab","_focusNode","_focusNode2","onDragEndHandler","Provider","useContext","nodeRef","click","ContextMenuButton","isExpanded","onContextMenu","ContextMenuTooltipButton","disableTooltip","MenuItemRadio","RoomListActions","tagRoom","oldTag","newTag","newIndex","metaData","RoomListStore","getTagSorting","SortAlgorithm","Manual","newList","orderedLists","order","indexBefore","indexAfter","prevOrder","nextOrder","fn","DefaultTagID","DM","Rooms","_err$message","hasChangedSubLists","promiseToDelete","deleteRoomTag","_err$message2","promiseToAdd","setRoomTag","_err$message3","pendingFn","AsyncActionPayload","formatMap","mp3","ogg","createAudioContext","formats","pickFormat","sounds","response","buffer","arrayBuffer","audioContext","decodeAudioData","createBufferSource","connect","resume","onended","suspend","audioElement","canPlayType","PlaybackClock","SimpleObservable","force","timeSeconds","lastCheck","observable","update","durationSeconds","clipDuration","placeholderDuration","currentTime","clipStart","liveData","populatePlaceholdersFrom","_event$getContent$inf","isFinite","flagLoadTime","flagStart","stopped","timerId","setInterval","checkTime","flagStop","syncTo","contextTime","clipTime","clearInterval","PlaybackEncoder","Worker","getPlaybackWaveform","resp","waveform","_PlaybackEncoder","PlaybackState","Playback","buf","seedWaveform","DEFAULT_WAVEFORM","Decoding","clock","fileSize","byteLength","resampledWaveform","arrayFastResample","PLAYBACK_WAVEFORM_SAMPLES","thumbnailWaveform","waveformObservable","sizeBytes","waveformData","clockInfo","Playing","UPDATE_EVENT","removeAllListeners","revokeObjectURL","remove","prepare","_this$element$duratio","_this$element","Preparing","onloadeddata","onerror","createObjectURL","Blob","audioBuf","wav","decodeOgg","getChannelData","duration","disconnectSource","makeNewSourceBuffer","_this$source","_this$source2","disconnect","onPlaybackEnd","_this$audioBuf","createMediaElementSource","Paused","toggle","skipTo","ManagedPlayback","pauseAllExcept","destroyPlaybackInstance","PlaybackManager","playback","instances","createPlaybackInstance","FixedRollingArray","padValue","samples","arraySeed","pushValue","swap","arrayFastClone","SAMPLE_RATE","RECORDING_PLAYBACK_SAMPLES","voiceRecorderOptions","bitrate","encoderApplication","highQualityRecorderOptions","RecordingState","VoiceRecording","processAudioUpdate","playbackTime","recording","liveWaveform","v","targetMaxLength","secondsLeft","recorderSeconds","Singleflight","for","do","EndingSoon","Void","contentType","recorder","recorderContext","isRecording","disableMaxLength","shouldRecordInHighQuality","makeRecorder","recorderStream","getUserMedia","audio","channelCount","ideal","recorderSource","createMediaStreamSource","audioWorklet","addModule","mxRecorderWorkletPath","recorderWorklet","AudioWorkletNode","WORKLET_NAME","PayloadEvent","Timekeep","AmplitudeMark","amplitudes","recorderProcessor","createScriptProcessor","onAudioProcess","recorderOptions","Recorder","encoderPath","encoderSampleRate","streamPages","encoderFrameSize","numberOfChannels","sourceNode","encoderBitRate","encoderComplexity","resampleQuality","ondataavailable","_this$onDataAvailable","onDataAvailable","DOMException","getTracks","encodedSamplePosition","_this$recorder","Started","_this$observable","forgetAllFor","AudioContext","audioBuffer","decoderWasmPath","typedArray","decoderWorker","decoderPath","wavWorker","wavEncoderPath","command","decoderSampleRate","outputBufferSampleRate","wavBitDepth","wavSampleRate","buffers","page","pages","AutocompleteProvider","commandRegex","forcedCommandRegex","renderingType","getCurrentCommand","query","selection","shouldForceComplete","end","range","COMMAND_RE","CommandProvider","matcher","QueryMatcher","Commands","funcs","aliases","getCompletions","limit","CommandMap","hideCompletionAfterSpace","cmd","display","renderingTypes","completion","getCommand","usedAlias","TextualCompletion","subtitle","getName","renderCompletions","completions","ariaSelectedAttribute","restProps","PillCompletion","_excluded2","objects","_options","setObjects","shouldMatchWordsOnly","_items","object","keyValues","f","keyValue","processQuery","keyWeight","candidates","resultKey","candidate","dedupped","uniq","maxLength","fuzzy","removeHiddenChars","USER_REGEX","FORCED_USER_REGEX","UserProvider","onUserSpoke","obj","onRoomTimeline","onRoomStateUpdate","_MatrixClientPeg$get2","rawQuery","makeUsers","fullMatch","_UserIdentifierCustom","UserIdentifierCustomisations","getDisplayUserIdentifier","withDisplayName","completionId","suffix","beginning","makeUserPermalink","MemberAvatar","lastSpoken","currentUserId","getMembersWithMembership","sortBy","JitsiCallMemberEventType","NamespacedValue","GroupCallPrefix","ElementCallMemberEventType","GroupCallMemberPrefix","AutoHideScrollbar","_this$props$wrappedRe","_this$props","containerRef","onScroll","wrappedRef","_this$props$wrappedRe2","_this$props2","_this$props3","otherProps","MenuItem","ariaLabel","MenuItemCheckbox","StyledMenuItemCheckbox","onClose","StyledCheckbox","onKeyUp","StyledMenuItemRadio","StyledRadioButton","ContextualMenuContainerId","ChevronFace","ContextMenu","_this$props$onFinishe","first","contextMenuElem","clientX","clientY","_document$elementFrom","clickEvent","MouseEvent","relatedTarget","elementFromPoint","dispatchEvent","_this$props$onFinishe2","_this$props$onFinishe3","closeOnInteraction","managed","initialFocus","onModalOpen","renderMenu","hasBackground","_this$props4","bottom","left","right","bottomAligned","rightAligned","menuClassName","menuHeight","menuWidth","menuPaddingLeft","menuPaddingRight","menuPaddingBottom","menuPaddingTop","zIndex","focusLock","wrapperClassName","chevronFace","propsChevronFace","chevronOffset","propsChevronOffset","mountAsChild","Left","Right","contextMenuRect","getBoundingClientRect","hasChevron","Bottom","windowWidth","windowHeight","UIStore","maxTop","maxLeft","chevron","menuClasses","mx_ContextualMenu","mx_ContextualMenu_left","mx_ContextualMenu_right","mx_ContextualMenu_top","mx_ContextualMenu_bottom","mx_ContextualMenu_withChevron_left","mx_ContextualMenu_withChevron_right","mx_ContextualMenu_withChevron_top","mx_ContextualMenu_withChevron_bottom","mx_ContextualMenu_rightAligned","mx_ContextualMenu_bottomAligned","menuStyle","wrapperStyle","background","FocusLock","returnFocus","_hasBackground","_onFinished","divProps","onContextMenuPreventBubbling","collectContextMenuRect","ReactDOM","toRightOf","elementRect","scrollX","scrollY","aboveLeftOf","vPadding","menuOptions","buttonRight","buttonBottom","buttonTop","aboveRightOf","buttonLeft","alwaysMenuProps","alwaysAboveRightOf","useContextMenu","isOpen","setIsOpen","ERROR_USER_CANCELLED","InteractiveAuthComponent","createRef","email","secret","attempt","session","busy","requestEmailToken","stageType","stageState","oldStage","authStage","errorText","errorCode","setFocus","_this$stageComponent$","_this$stageComponent$2","stageComponent","attemptFailed","auth","AuthType","Sso","SsoUnstable","authData","authLogic","submitAuthDict","newPhase","_this$props$onStagePh","_this$state$authStage","onStagePhaseChange","onAuthFinished","sid","setEmailSid","submitButtonEnabled","InteractiveAuth","doRequest","requestCallback","busyChanged","onBusyChanged","inputs","stateUpdated","authStateUpdated","sessionId","clientSecret","emailSid","supportedStages","Password","Recaptcha","Msisdn","Terms","RegistrationToken","UnstableRegistrationToken","OAuth","CustomAuthType","MasCrossSigningReset","unmounted","poll","intervalId","attemptAuth","extra","getEmailSid","getClientSecret","_this$stageComponent$3","_this$stageComponent$4","stage","StageComponent","getEntryComponentForLoginType","authSessionId","getSessionId","stageParams","getStageParams","fail","onAuthStageFailed","onPhaseChange","continueText","continueKind","onStageCancel","LegacyCallEventGrouperEvent","CONNECTING_STATES","WaitLocalMedia","CreateOffer","CreateAnswer","SUPPORTED_STATES","Connected","buildLegacyCallEventGroupers","callEventGroupers","newCallEventGroupers","eventType","LegacyCallEventGrouper","SilencedChanged","LengthChanged","StateChanged","setCall","CallReject","selectAnswer","CallSelectAnswer","_invite$getContent","_this$call$hangupReas","_this$call","_this$hangup","rejectParty","_this$reject","gotRejected","_this$hangup2","_this$selectAnswer","callWasMissed","_2","onLengthChanged","ScrollPanel","_this$context","_this$scrollTimeout","_this$props$onScroll","resizeNotifier","isResizing","getScrollNode","scrollTop","scrollTimeout","saveScrollState","updatePreventShrinking","checkFillState","checkScroll","preventShrinkingState","preventShrinking","isFromPropsUpdate","restoreSavedScrollState","sn","scrollHeight","clientHeight","depth","isFirstCall","isFilling","isFillingDueToPropsUpdate","fillRequestWhileRunning","pendingFillDueToPropsUpdate","itemlist","firstTile","firstElementChild","fillPromises","offsetTop","maybeFill","refillDueToPropsUpdate","scrollState","stuckAtBottom","startAtBottom","bottomGrowth","minListHeight","heightUpdateInProgress","multiple","scrollNode","delta","scrollBy","scrollRelative","scrollToTop","scrollToBottom","scrollToken","pixelOffset","offsetBase","trackedScrollToken","trackedNode","getTrackedNode","divScroll","messageList","tiles","lastTileNode","dataset","scrollTokens","clearPreventShrinking","offsetFromBottom","offsetNode","balanceElement","parentElement","removeProperty","shouldClear","offsetDiff","paddingBottom","resetScrollState","_this$context2","onResize","_this$context3","getExcessHeight","contentHeight","getMessagesHeight","clippedHeight","getListHeight","unclippedScrollTop","checkUnfillState","excessHeight","origExcessHeight","tile","markerScrollToken","unfillDebouncer","_this$props$onUnfillR","onUnfillRequest","pendingFillRequests","_this$props$onFillReq","onFillRequest","hasMoreResults","_dataset$scrollTokens","stickyBottom","isAtBottom","viewportBottom","messages","_htmlMessage$dataset","htmlMessage","topFromBottom","bottomOffset","_scrollState$bottomOf","newBottomOffset","bottomDiff","newHeight","updateHeight","_this$scrollTimeout2","ceil","oldTop","topDiff","_m$dataset$scrollToke","_offsetTop","_itemlist$firstElemen","lastNode","lastElementChild","collectScroll","fixedChildren","SDKContext","SearchBox","search","searchTerm","onSearch","throttle","_this$search$current$","_this$search$current","trailing","leading","clearSearch","blurred","select","onBlur","initialValue","_this$props$onCleared","onCleared","blurredPlaceholder","collapsed","clearButton","mx_SearchBox_blurred","SpacePillButton","icon","labelClassName","useActiveTabWithDefault","tabs","defaultTabID","initialTabID","activeTabId","setActiveTabId","TabLocation","domIDForTabID","tabId","TabPanel","tab","TabLabel","showToolip","mx_TabbedView_tabLabel_active","tabIcon","TabbedView","_props$tabLocation","_tab$screenName","tabLocation","LEFT","useWindowWidth","setWidth","UI_EVENTS","Resize","labels","panel","tabbedViewClasses","mx_TabbedView","mx_TabbedView_tabsOnLeft","mx_TabbedView_tabsOnTop","TOP","mx_TabbedView_responsive","responsive","ViewSource","isEditing","onEdit","viewSourceContent","mxEvent","replacingEvent","ignoreEdits","isEncrypted","decryptedEventSource","clearEvent","originalEventSource","copyOriginalFunc","copyDecryptedFunc","CopyableText","getTextToCopy","SyntaxHighlight","language","editSourceContent","isStateEvent","MatrixClientContext","Consumer","DevtoolsContext","StateEventEditor","onBack","TimelineEventEditor","canSendStateEvent","mayClientSendStateEvent","canEdit","canEditContent","border","AuthHeaderContext","AuthHeaderActionType","AuthHeaderProvider","Add","Remove","isEqual","PlayPauseButton","toggleState","playbackPhase","SharedPlayPauseButton","togglePlay","playing","onPlaybackUpdate","onUpdate","onTimeUpdate","_this$props$defaultDi","defaultDisplaySeconds","Clock","AudioPlayerBase","_this$playPauseRef$cu","_this$seekRef$current","_this$seekRef$current2","playPauseRef","seekRef","renderComponent","LegacySeekBar","MarkedExecution","doUpdate","requestAnimationFrame","animationFrameFn","trigger","percentage","percentageOf","mark","onMouseDown","max","PlaybackWaveform","heights","toHeights","progress","onWaveformUpdate","seed","arrayTrimFill","Waveform","relHeights","PlaybackLayout","RecordingPlayback","renderComposerLook","renderTimelineLook","Composer","h","isCompleteBar","mx_Waveform_bar","mx_Waveform_bar_100pct","AuthHeaderModifier","_context$dispatch","DIV_ID","CaptchaForm","isRecaptchaReady","onCaptchaLoaded","_this$recaptchaContai","mxOnRecaptchaLoaded","scriptTag","setAttribute","recaptchaContainer","resetRecaptcha","iframes","iframe","_parentBeforeBody2","parentBeforeBody","_parentBeforeBody","grecaptcha","renderRecaptcha","divId","_global$grecaptcha","publicKey","sitePublicKey","captchaWidgetId","sitekey","onCaptchaResponse","_global","PasswordAuthEntry","identifier","password","passwordBoxClass","submitButtonOrSpinner","errorSection","Field","onPasswordFieldChange","RecaptchaAuthEntry","public_key","TermsAuthEntry","_this$props$stagePara","allChecked","toggledPolicies","allPolicies","initToggles","pickedPolicies","policyId","langPolicy","togglePolicy","newToggles","checkboxes","trySubmit","EmailIdentityAuthEntry","requested","requesting","_this$props$inputs","_this$props$stageStat","emailAddress","EmailPromptIcon","alt","hideServerPicker","Fragment","onTooltipOpenChange","_this$props$requestEm","MsisdnAuthEntry","submitUrl","submitMsisdnTokenOtherUrl","success","client_secret","threepid_creds","requestingToken","requestMsisdnToken","_this$props$inputs$ph","_this$props$inputs2","_this$props$inputs$ph2","_this$props$inputs3","requestRegisterMsisdnToken","phoneCountry","submit_url","msisdn","submitClasses","mx_InteractiveAuthEntryComponents_msisdnSubmit","mx_GeneralButton","onFormSubmit","onTokenChange","RegistrationTokenAuthEntry","registrationToken","registrationTokenBoxClass","onRegistrationTokenFieldChange","SSOAuthEntry","popupWindow","ssoUrl","PHASE_POSTAUTH","getFallbackAuthUrl","PHASE_PREAUTH","onReceiveMessage","_this$props$onCancel","continueButton","onStartAuthClick","onConfirmClick","FallbackAuthEntry","_this$fallbackButton$","fallbackButton","_this$popupWindow","onShowFallbackClick","MasUnlockCrossSigningAuthEntry","_this$props$stagePara2","UserProfileSolidIcon","serverName","onGoToAccountClick","onRetryClick","calculateUrls","urls","lowBandwidth","_urls","altText","imageUrl","onError","useImageUrl","_roomContext$lowBandw","roomContext","useScopedRoomContext","imageUrls","setUrls","urlsIndex","setIndex","onClientSync","syncState","extraProps","BUSY_PRESENCE_NAME","UnstableValue","tooltipText","variant","Globe","PresenceOnline","PresenceAway","PresenceOffline","PresenceBusy","DecoratedRoomAvatar","isUnmounted","newIcon","calculateIcon","getPresenceIcon","notificationState","RoomNotificationStateStore","getRoomState","isWatchingTimeline","dmUser","isPublicRoom","getJoinRule","_dmUser","oldUser","UserEvent","CurrentlyActive","onPresenceUpdate","Presence","isOnline","currentlyActive","presence","isPresenceEnabled","displayBadge","hideIfDot","oobData","viewAvatarOnClick","tooltipProps","_this$props$tooltipPr","_this$props$tooltipPr2","NotificationBadge","PublicIcon","mx_DecoratedRoomAvatar_cutout","placement","_member$name","_member$userId2","viewUserOnClick","forceHistorical","fallbackUserId","hideTitle","propsMember","card","CardContext","useRoomMemberProfile","_member$getMxcAvatarU","_member$userId","_member$roomId","ViewUser","isCard","_room$name","_room$getType","avatarEvent","useRoomState","getStateEvents","roomIdName","dmMember","useDmMember","LocalRoom","targets","useRoomIdName","showAvatarsOnInvites","useSettingValue","invite_avatars","On","onRoomAvatarClick","params","ImageView","myMembership","sizeInt","oobAvatar","roomType","RoomType","SearchResultAvatar","isEmail","emailPillAvatar","Online","Away","Offline","getDmMember","setDmMember","updateDmMember","Members","getPresence","usePresence","setPresence","updatePresence","WithPresenceIndicator","_tooltipProps$tabInde","useMsRemaining","beacon","beaconInfo","useEventEmitterState","BeaconEvent","msRemaining","setMsRemaining","getBeaconMsUntilExpiry","updateMsRemaining","ms","useInterval","LiveTimeRemaining","timeRemaining","liveTimeRemaining","BeaconExpiryTime","expiryTime","getBeaconExpiryTimestamp","displayStatus","displayLiveTimeRemaining","withIcon","rest","isIdle","BeaconDisplayStatus","Loading","StyledLiveBeaconIcon","withError","Active","hasLocationPublishError","hasStopSharingError","stoppingInProgress","onStopSharing","onResetLocationPublishError","useOwnLiveBeacons","ownDisplayStatus","BeaconStatus","preventDefaultWrapper","LiveLocationIcon","mx_StyledLiveBeaconIcon_error","mx_StyledLiveBeaconIcon_idle","getBeaconDisplayStatus","isLive","latestLocationState","waitingToStart","GenericFeatureFeedbackDialog","subheading","rageshakeLabel","rageshakeData","comment","setComment","canContact","setCanContact","hasCancelButton","buttonDisabled","submitFeedback","InfoDialog","hasCloseButton","BetaFeedbackDialog","featureId","_SettingsStore$getBet","getBetaInfo","featureName","feedbackSubheading","feedbackLabel","fromEntries","extraSettings","ViewUserSettings","initialTabId","UserTab","Labs","BetaPill","tooltipTitle","tooltipCaption","caption","BetaCard","titleOverride","useFeatureEnabled","setBusy","faq","image","requiresRefresh","feedbackButton","refreshWarning","shouldShowFeedback","InlineSpinner","SettingsFlag","IconizedContextMenuRadio","mx_IconizedContextMenu_item","mx_IconizedContextMenu_active","IconizedContextMenuCheckbox","marker","words","IconizedContextMenuOption","_ref3","isDestructive","_excluded3","mx_IconizedContextMenu_itemDestructive","IconizedContextMenuOptionList","red","mx_IconizedContextMenu_optionList_notFirst","mx_IconizedContextMenu_optionList_red","_ref4","compact","_excluded4","mx_IconizedContextMenu_compact","EndPollDialog","endPoll","polls","responses","getResponses","topAnswer","findTopAnswer","endEvent","PollEndEvent","serialize","sendEvent","ReplyInThreadButton","closeMenu","_mxEvent$getRelation","relationType","RelationType","ThreadsIcon","isThreadRoot","ShowThread","rootEvent","initialEvent","scroll_into_view","highlighted","MessageContextMenu","canRedact","maySendRedactionForEvent","canPin","PinningUtils","canUnpin","reaction","getUnsentReactions","relatedEventId","OpenReportEventDialog","onCloseDialog","createRedactEventDialog","forwardableEvent","_this$props$permalink","OpenForwardDialog","permalinkCreator","isPinned","pinOrUnpinEvent","_this$props$eventTile","eventTileOps","unhideWidget","ShareDialog","copyPlaintext","_this$props$collapseR","collapseReplyChain","getSelectedText","selectedText","quotedText","line","ComposerInsert","timelineRenderingType","editEvent","getRelationsForEvent","reactionPickerDisplayed","RoomMemberEvent","PowerLevel","checkPermissions","Status","canEndPoll","isPollEnded","isSelectionWithinSingleTextBody","getSelection","rangeCount","getRangeAt","getParentByClass","HTMLElement","classList","contains","parentNode","startTextBody","startContainer","endTextBody","endContainer","getReactions","_room$getPendingEvent","relation","Annotation","_this$props$permalink2","_mxEvent$getThread","me","rightClick","reactions","other","eventStatus","unsentReactionsCount","contentActionable","isContentActionable","permalink","forEvent","isSent","SENT","canReact","canSendMessages","isThreadRootEvent","ThreadsList","resendReactionsButton","redactButton","openInMapSiteButton","RestartIcon","unsentCount","onResendReactionsClick","DeleteIcon","onRedactClick","shareableLocationEvent","getShareableLocationEvent","mapSiteLink","createMapSiteLinkFromEvent","forwardButton","getForwardableEvent","ForwardIcon","onForwardClick","viewSourceButton","InlineCodeIcon","onViewSourceClick","unhidePreviewButton","permalinkButton","endPollButton","externalURLButton","collapseReplyChainButton","jumpToRelatedEventButton","isWidgetHidden","VisibilityOnIcon","onUnhidePreviewClick","ShareIcon","onShareClick","onEndPollClick","external_url","LinkIcon","ChevronUpIcon","onCollapseReplyChainClick","getAssociatedId","reportEventButton","copyLinkButton","TreeIcon","onJumpToRelatedEventClick","onReportEventClick","CopyIcon","onCopyLinkClick","copyButton","quoteButton","editButton","replyButton","replyInThreadButton","reactButton","pinButton","viewInRoomButton","nativeItemsList","quickItemsList","triggerOnMouseDown","onCopyClick","QuoteIcon","onQuoteClick","EditIcon","onEditClick","ReplyIcon","onReplyClick","hasServerSideSupport","ReactionAddIcon","onReactClick","reactButtonRef","UnpinIcon","PinIcon","onPinClick","viewInRoom","commonItemsList","redactItemList","reactionPicker","_this$reactButtonRef$","buttonRect","ReactionPicker","onCloseReactionPicker","IconizedContextMenu","RoomContext","DeveloperToolsOption","DevtoolsDialog","LabsIcon","RoomGeneralContextMenu","onPostFavoriteClick","onPostLowPriorityClick","onPostInviteClick","onPostCopyLinkClick","onPostSettingsClick","onPostLeaveClick","onPostForgetClick","onPostMarkAsReadClick","onPostMarkAsUnreadClick","roomTags","LISTS_UPDATE_EVENT","getTagsForRoom","isDm","wrapHandler","postHandler","onTagRoom","tagId","Favourite","LowPriority","inverseTag","isApplied","removeTag","addTag","isFavorite","favoriteOption","FavouriteSolidIcon","isLowPriority","lowPriorityOption","ArrowDownIcon","inviteOption","canInvite","shouldShowComponent","UIComponent","InviteUsers","UserAddIcon","copyLinkOption","settingsOption","SettingsSolidIcon","leaveOption","Archived","LeaveIcon","useUnreadNotifications","markAsReadOption","clearRoomNotification","MarkAsReadIcon","setMarkedUnreadState","MarkAsUnreadIcon","developerToolsOption","RoomNotificationContextMenu","setNotificationState","useNotificationState","defaultOption","allMessagesOption","mentionsOption","muteOption","space","hideHeader","videoRoomsEnabled","elementCallVideoRoomsEnabled","onInviteClick","showSpaceInvite","shouldShowSpaceSettings","onSettingsClick","showSpaceSettings","onLeaveClick","leaveSpace","devtoolsOption","onViewTimelineClick","forceTimeline","hasPermissionToAddSpaceChild","maySendStateEvent","canAddRooms","CreateRooms","canAddVideoRooms","canAddSubSpaces","CreateSpaces","newRoomSection","onNewRoomClick","showCreateNewRoom","onNewVideoRoomClick","UnstableCall","ElementVideo","onNewSubspaceClick","showCreateNewSubspace","PlusIcon","openSpace","HomeSolidIcon","SearchIcon","PreferencesIcon","showSpacePreferences","Entry","useId","getScrollState","numItems","prevGroupSizes","heightBefore","GROUP_MARGIN","viewportTop","listTop","listBottom","AddExistingToSpace","footerPrompt","emptySelectionButton","filterPlaceholder","roomsRenderer","dmsRenderer","spacesRenderer","visibleRooms","_cli$getVisibleRooms$","getVisibleRooms","scrollRef","setScrollState","selectedToAdd","setSelectedToAdd","setProgress","setError","setQuery","lcQuery","existingSubspacesSet","SpaceStore","getChildSpaces","existingRoomsSet","getChildRooms","rooms","joinRule","sortRooms","arr","addRooms","via","calculateRoomVia","addRoomToSpace","retry_after_ms","footer","ErrorIcon","ProgressBar","numSpaces","numRooms","numDms","noResults","roomsScrollState","spacesScrollState","dmsScrollState","_scrollRef$current","defaultRendererFactory","LazyRenderList","itemHeight","items","renderItem","defaultRoomsRenderer","defaultSpacesRenderer","defaultDmsRenderer","SubspaceSelector","Dropdown","onOptionChange","mx_SubspaceSelector_dropdownOptionActive","AddExistingToSpaceDialog","onCreateRoomClick","onAddSubspaceClick","selectedSpace","setSelectedSpace","AskInviteAnywayDialog","onGiveUp","onInviteAnyways","unknownProfileUsers","descriptionProp","inviteNeverWarnLabel","inviteLabel","onInviteClicked","onInviteNeverWarnClicked","ACCOUNT","onGiveUpClicked","_this$props$onKeyDown","headerImage","lockProps","I18nContext","mxModuleApi","i18n","mx_Dialog_fixedWidth","mx_Dialog_headerWithButton","headerButton","Heading","titleClass","BugReportDialog","issueUrl","userText","sendProgressCallback","isLocalOnly","sendBugReport","bug_report_endpoint_url","sendLogs","progressCallback","sendSentryReport","downloadBusy","downloadProgressCallback","downloadBugReport","downloadProgress","issueRef","_this$issueRef$curren","DumpDebugLogs","_error$errorcode","RageshakeError","errorcode","policyURL","Link","warning","Modernizr","Text","weight","onDownload","onIssueUrlChange","onTextChange","ConfirmRedactDialog","TextInputDialog","proceed","withRelTypes","redactEvent","statusCode","ConfirmUserActionDialog","confirmButtonClass","danger","reasonBox","askReason","onOk","onReasonChange","displayUserIdentifier","primaryButtonClass","CreateRoomDialog","_this$props$defaultEn","_this$props$defaultSt","nameField","blur","validate","allowEmpty","aliasField","nameIsValid","isValid","field","focused","roomCreateOptions","evt","isStateEncrypted","detailsOpen","noFederate","validateRoomName","fieldState","valid","isPublicKnockRoom","askToJoinEnabled","advancedSettingsEnabled","AdvancedSettings","allowCreatingPublicRooms","AllowCreatingPublicRooms","supportsRestricted","parentSpace","defaultPublic","defaultEncrypted","privateShouldBeEncrypted","defaultStateEncrypted","defaultName","default_federate","canChangeEncryption","createOpts","Visibility","preset","Preset","PublicChat","guestAccess","room_alias_name","encryptedStateFeature","encryption","stateEncryption","creation_content","Private","_this$nameField$curre","checkUserIsAllowedToChangeEncryption","PrivateChat","allowChange","forcedValue","isVideoRoom","publicPrivateLabel","visibilitySection","e2eeSection","e2eeStateSection","RoomAliasField","onAliasChange","SpaceName","_this$props$parentSpa","_this$props$parentSpa2","_this$props$parentSpa3","_this$props$parentSpa4","SettingsToggleInput","onIsPublicKnockRoomChange","microcopy","onEncryptedChange","helpMessage","onStateEncryptedChange","federateLabel","Form","onNameChange","onValidate","onNameValidate","onTopicChange","JoinRuleDropdown","labelInvite","labelKnock","labelPublic","labelRestricted","onJoinRuleChange","onToggle","onDetailsToggled","onNoFederateChange","withValidation","rules","invalid","ServersInRoom","servers","_servers$server","BaseTool","numUsers","SettingExplorer","setting","setSetting","editing","setEditing","EditSetting","ViewSetting","onView","SettingsList","CanEditLevelField","canSetValue","renderExplicitSettingValues","vals","LEVEL_ORDER","explicitValue","setExplicitValue","explicitRoomValue","setExplicitRoomValue","actionLabel","parsedExplicit","parsedExplicitRoom","SETTINGS","lvl","renderSettingValue","allSettings","WidgetExplorer","setWidget","FilteredList","UserButton","_member$events$member","_member$membership","verificationStatus","useAsyncMemo","getUserVerificationStatus","isCrossSigningVerified","e2eIcon","E2EIcon","isUser","hideTooltip","E2EStatus","Verified","wasCrossSigningVerified","Warning","needsUserApproval","Normal","_devices$get","getUserDeviceInfo","DeviceView","memberEventContent","DeviceButton","verificationIcon","getDeviceVerificationStatus","crossSigningVerified","signedByOwner","keyIdSuffix","deviceKeys","dehydrated","AccountDataEventEditor","fields","eventTypeField","defaultContent","EventEditor","fieldDefs","onSend","RoomAccountDataEventEditor","setRoomAccountData","BaseAccountDataExplorer","Editor","setTool","setEvent","EventViewer","UserReadUpTo","_target$getReadReceip","_target$getReadReceip2","_target$getReadReceip3","_target$getReadReceip4","_target$getReadReceip5","_target$getReadReceip6","_target$getReadReceip7","_target$getReadReceip8","hasPrivate","getReadReceiptForUserId","ReceiptType","ReadPrivate","KeyStorage","useMatrixClientContext","keyStorageData","backupInfo","getKeyBackupInfo","backupKeyStored","isKeyBackupKeyStored","backupKeyFromCache","getSessionBackupPrivateKey","backupKeyCached","backupKeyWellFormed","activeBackupVersion","getActiveSessionBackupVersion","secretStorageKeyInAccount","secretStorageReady","isSecretStorageReady","scope","algorithm","CrossSigning","crossSigningData","crossSigningStatus","getCrossSigningStatus","crossSigningPublicKeysOnDevice","publicKeysOnDevice","crossSigningPrivateKeysInStorage","privateKeysInSecretStorage","masterPrivateKeyCached","privateKeysCachedLocally","masterKey","selfSigningPrivateKeyCached","selfSigningKey","userSigningPrivateKeyCached","userSigningKey","crossSigningReady","isCrossSigningReady","Session","sessionData","fingerprint","getOwnDeviceKeys","ed25519","SettingsField","settingKey","isExplicit","_onSave","settingsValue","onSave","EditInPlace","getDisplayName","saveButtonLabel","cancelButtonLabel","savedLabel","savingLabel","Category","categoryLabels","Other","Tools","RoomStateExplorer","RoomAccountDataExplorer","isRoomEncrypted","useIsEncrypted","humanReadableNotificationLevel","total","dot","roomHasUnread","threadHasUnread","_thread$lastReply","_thread$lastReply2","_thread$lastReply3","lastReply","UserList","showOnlyJoined","setShowOnlyJoined","setMember","AccountDataExplorer","ServerInfo","ManualDeviceKeyVerificationDialog","RestoreKeyBackupDialog","tool","Tool","tools","extractErrorMessageFromError","translatedFallbackMessage","translatedMessage","authError","newStage","uiaStage","uiaStagePhase","getDefaultDialogAesthetics","ssoAesthetics","LOGIN_TYPE","UNSTABLE_LOGIN_TYPE","_this$props$title","dialogAesthetics","aestheticsForStagePhases","aesthetics","onUpdateStagePhase","TabId","DMUserTile","onRemove","Pill","toMember","DirectoryMember","user_id","DMRoomTile","avatarSize","EmailPillAvatarIcon","userIdentifier","RichItem","lastActiveTs","selected","isSelected","convertFilter","profilesStores","directoryMembers","getOrFetchProfile","unknownProfiles","lookupError","getProfileLookupError","UNKNOWN_PROFILE_ERRORS","extractTargetUnknownProfiles","profilesStore","showAskInviteAnywayDialog","startDm","startDmOnFirstMessage","targetIds","inhibitProgressDialog","shouldAbortAfterInviteError","currentTabId","UserDirectory","dialPadValue","searchUserDirectory","term","filterText","profile","shouldThrow","serverResultsMixin","u","canUseIdentityServer","canInviteThirdParty","IdentityServer","threepidResultsMixin","ThreepidMember","authClient","lookup","lookupThreePid","mxid","tryingIdentityServer","debounceTimer","updateSuggestions","numRecentsShown","numSuggestionsShown","editorRef","clipboardData","getData","potentialAddresses","parseFilter","possibleMembers","recents","suggestions","toAdd","failed","unableToAddMore","canInviteMore","csvNames","uniqBy","fire","transferCall","digit","_this$numberEntryFiel","numberEntryFieldRef","_this$numberEntryFiel2","userProfilesStore","excludedIds","isRoomInvite","_room$currentState$ge","isFederated","ourHomeserver","excludeExternals","buildRecents","buildSuggestions","encryptionByDefault","homeserver","excludedTargetIds","buildMemberScores","getUniqueRoomsWithIndividuals","dmTaggedRooms","dmRoom","otherMembers","roomMember","searchTypes","maxSearchEvents","lastEventTs","lastActive","activityScores","buildActivityScores","memberScores","memberComparator","compareMembers","newMember","newTargets","renderSection","sourceMembers","showNum","showMoreFn","showMoreRecents","showMoreSuggestions","sectionName","priorityAdditionalMembers","otherAdditionalMembers","hasMixins","notAlreadyExists","hasAdditionalMembers","filterBy","RichList","titleAttributes","isEmpty","toRender","showMore","toggleMember","renderEditor","removeMember","PillInput","inputProps","updateFilter","onPaste","onRemoveChildren","renderIdentityServerWarning","defaultIdentityServerUrl","getDefaultIdentityServerUrl","defaultIdentityServerName","onUseDefaultIdentityServerClick","settings","onManageSettingsClick","onLinkClick","selectText","hasFilterAtLeastOneEmail","hasSelection","renderSuggestions","onlyOneThreepidNote","extraSection","renderMainTab","helpText","buttonText","goButtonFn","identityServersEnabled","checkProfileAndStartDm","helpTextUntranslated","makeRoomPermalink","inviteUsers","goButton","InviteProgressBody","renderRegularDialog","spaceName","renderCallTransferDialog","usersSection","backspaceButton","DialPadBackspaceButton","onBackspacePress","onDeletePress","dialPadField","onDialChange","postfixComponent","dialPadSection","onDialFormSubmit","Dialpad","hasDial","onDigitPress","DialPad","DialPadIcon","consultConnectSection","onConsultFirstChange","dialogContent","onTabChange","setDeviceId","setFingerprint","onDialogFinished","confirm","manuallyVerifyDevice","onDeviceIdChange","onFingerprintChange","cause","getDeviceCryptoInfo","deviceTrust","isVerified","getFingerprint","fprint","crossSignDevice","doManuallyVerifyDevice","quitOnly","extraButtons","idNameForRoom","dmMapUserId","RoomProfileSettings","_avatarEvent$getConte","file","avatarFile","avatarRemovalPending","profileFieldsTouched","avatarUpload","isSaveEnabled","originalDisplayName","originalTopic","setRoomName","content_uri","uri","uploadContent","sendStateEvent","originalAvatarUrl","html","htmlSerializeFromMdIfNeeded","forceHTML","setRoomTopic","topicEvent","nameEvent","canSetName","canSetTopic","canSetAvatar","_this$state$avatarFil","profileSettingsButtons","cancelProfileChanges","saveProfile","canRemove","noValidate","onDisplayNameChanged","onTopicChanged","AvatarSetting","avatarAccessibleName","onAvatarChanged","removeAvatar","placeholderId","placeholderName","UrlPreviewSettings","isLoading","SettingsFieldset","legend","Description","PreviewsForRoom","ROOM_DEVICE","onClickUserSettings","urlPreviewsEnabled","useSettingValueAt","previewsForAccount","previewsForRoom","GeneralRoomSettingsTab","isRoomPublished","canSetCanonical","canonicalAliasEv","urlPreviewSettings","URLPreviews","leaveSection","SettingsSubsection","heading","SettingsTab","SettingsSection","AliasSettings","canSetCanonicalAlias","canSetAliases","canonicalAliasEvent","legacy","MediaPreviewAccountSettings","SecurityRoomSettingsTab","forceUpdate","createNewRoom","beforeEncrypted","MEGOLM_ENCRYPTION_ALGORITHM","beforeGuestAccess","shouldCreate","createRoom","beforeHistory","setBlacklistUnverifiedDevices","_error$message","currentlyPublic","_this$props$room$curr","showAdvancedSection","pullContentPropertyFromEvent","hasAliases","stateEncrypted","_this$context$getCryp","_this$context$getCryp2","onStateEvent","isStateEncryptionEnabledInRoom","defaultValue","localAliases","getLocalAliases","renderJoinRule","isPublic","WarningIcon","advanced","toggleAdvancedSection","renderAdvanced","JoinRuleSettings","beforeChange","onBeforeJoinRuleChange","onJoinRuleChangeError","closeSettingsFn","promptUpgrade","renderHistory","RoomHistorySettings","canChangeHistory","displayHistory","StyledRadioGroup","onHistoryRadioToggle","definitions","canSetGuestAccess","onGuestAccessChange","isEncryptionLoading","hasEncryptionPermission","isEncryptionForceDisabled","shouldForceDisableEncryption","canEnableEncryption","encryptionSettings","updateBlacklistDevicesFlag","historySection","onEncryptionChange","Caption","NotificationsSettingsTab","_this$soundUpload$cur","soundUpload","files","uploadedFile","saveSound","ROOM_ACCOUNT","currentSound","roomProps","notificationVolume","Notifications","EchoChamber","forRoom","soundData","currentUploadedFile","onOpenSettingsClick","onRoomNotificationChange","clearSound","chromeFileInputFix","onSoundUploadChanged","accept","triggerUploader","onClickSaveSound","BridgeTile","_content$channel","_content$protocol","channel","bridgebot","network","protocolName","channelName","creator","PillType","UserMention","shouldShowPillAvatar","bot","networkIcon","networkItem","_mediaFromMxc$getSqua","networkName","networkLink","channelLink","BRIDGE_EVENT_TYPES","BRIDGES_LINK","BridgeSettingsTab","renderBridgeCard","getBridgeStateEvents","roomState","typeName","flat","bridgeEvents","ElementCallSwitch","_SdkConfig$get$brand","maySend","_state$getStateEvents","elementCallEnabled","setElementCallEnabled","_content$events","newContent","_newContent$events$Ev","_content$kick","userLevel","moderatorLevel","kick","_newContent$events$Ev2","adminLevel","state_default","disabledMessage","VoipRoomSettingsTab","PollHistoryTab","RoomPermalinkCreator","PollHistory","Timestamp","_roomMember$events$me","origin_server_ts","SeeMoreOrLess","_roomMember$events$me2","seeMore","setSeeMore","shouldTruncate","canKick","onApprove","onDeny","setDisabled","handleDeny","handleApprove","PeopleRoomSettingsTab","getState","FORWARDS","hasSufficientPowerLevelFor","powerLevel","knockMembers","useTypedEventEmitterState","knockMember","RoomSettingsDialog","ViewHomePage","General","dispatcherRef","Name","onRoomName","unregister","getTabs","SettingsIcon","People","GroupIcon","LockIcon","AdminIcon","RolesRoomSettingsTab","NotificationsIcon","NotificationSettingsTab","Bridges","PollsIcon","Advanced","AdvancedSettingsIcon","AdvancedRoomSettingsTab","ErrorBoundary","RoomUpgradeDialog","upgradeRoom","targetVersion","recommended","getRecommendedVersion","buttons","onUpgradeClick","RoomUpgradeWarningDialog","_joinRules$getContent","_this$props$doUpgrade","continue","isInviteOrKnockRoom","inviteUsersToNewRoom","doUpgrade","onProgressCallback","joinRules","currentVersion","inviteToggle","onInviteUsersToggle","bugReports","openBugReportDialog","onContinue","oldVersion","ScrollableBaseModal","cancel","canSubmit","submit","_this$state$cancelLab","renderContent","cancelLabel","SOCIALS","customTitle","showQrCode","ShareQRCode","showSocials","ShareSocial","timeoutIdRef","isCopied","setIsCopied","linkToSpecificEvent","setLinkToSpecificEvent","checkboxLabel","User","newPermalinkCreator","load","forShareableRoom","useTargetValues","newTitle","QRCode","Checkbox","defaultChecked","SocialLinks","social","validator","_this$field$current","htmlFor","busyMessage","UploadConfirmDialog","objectUrl","totalFiles","fileId","mimeType","preview","uploadAllButton","playsInline","controls","FilesIcon","onUploadAllClick","onUploadClick","extraButton","setMessage","actionButton","onActionClick","onBackClick","stateKeyField","validateEventContent","deriveData","fieldData","setFieldData","def","_def$default","setContent","contentField","_contentField$current","_contentField$current2","_originalContent$mNe","_originalContent$mNe2","originalContent","bodyToStartFrom","baseEvent","_mxEvent$getWireConte","_mxEvent$getWireConte2","_baseEvent$replacingE","getWireContent","_children$0$key","_children$","truncateAt","setTruncateAt","filteredChildren","setFilteredChildren","child","_child$key","TruncatedList","getChildren","getChildCount","createOverflowElement","overflowCount","totalCount","num","stateKey","RoomStateHistory","_events$0$unsigned","replaces_state","StateEventButton","trimmed","mx_DevTools_RoomStateExplorer_button_hasSpaces","mx_DevTools_RoomStateExplorer_button_emptyString","RoomStateExplorerEventType","setHistory","showEmptyState","setShowEmptyState","onEmptyStateToggled","_onBack","onHistoryClick","setEventType","FAILED_TO_LOAD","Symbol","getServerVersionFromFederationApi","hsName","capabilities","fetchCapabilities","clientVersions","getVersions","serverVersions","RestoreType","ProgressState","forceRecoveryKey","recoveryKeyValid","isValidRecoveryKey","loading","restoreError","restoreType","Passphrase","recoverInfo","restoreKeyBackupWithPassphrase","passPhrase","showSummary","_this$state$backupInf","RecoveryKey","storeSessionBackupPrivateKey","restoreKeyBackup","loadError","PreFetch","loadBackupStatus","restoreWithSecretStorage","SecretStorage","loadSessionBackupPrivateKeyFromSecretStorage","restoreWithCachedKey","_await$cli$getCrypto$","backupHasPassphrase","auth_data","private_key_salt","private_key_iterations","Fetch","LoadKeys","successes","failures","completed","MatrixClient","RESTORE_BACKUP_ERROR_BAD_KEY","failedToDecrypt","imported","failedCount","sessionCount","onDone","onPassPhraseChange","onPassPhraseNext","primaryIsSubmit","button1","onUseRecoveryKeyClick","button2","onResetRecoveryClick","keyStatus","Filter","getNotificationIcon","NotificationsOffSolidIcon","NotificationsSolidIcon","RoomResultContextMenus","generalMenuPosition","setGeneralMenuPosition","notificationMenuPosition","setNotificationMenuPosition","generalMenu","notificationMenu","SpaceContextMenu","contextMenuBelow","RoomOptionsMenu","OverflowHorizontalIcon","_restProps$ariaLabel","newProps","classnames","mx_AccessibleButton_hasKind","mx_AccessibleButton_disabled","isTriggerInteractive","onOpenChange","BugReportDialogButton","bugReportUrl","CopyTextButton","tooltip","setTooltip","successful","combinedClassName","mx_CopyableText_border","BackspaceSolidIcon","additive","primaryButtonClassName","cancelButtonClass","MenuOption","onMouseEnter","dropdownKey","optClasses","mx_Dropdown_option","mx_Dropdown_option_highlight","ignoreEvent","expanded","highlightedOption","_this$dropdownRootEle","nextKey","nextOption","dropdownRootElement","_this$dropdownRootEle2","prevKey","prevOption","searchQuery","onSearchChange","onRootClick","optionKey","reindexChildren","onDocumentClick","prevProps","_this$props$children","objectHasDiff","childrenByKey","buttonRef","block","behavior","getMenuOptions","setHighlightedOption","onMenuOptionClick","currentValue","menu","searchEnabled","onInputChange","selectedChild","getShortOption","dropdownClasses","mx_Dropdown_disabled","collectRoot","onAccessibleButtonClick","ChevronDownIcon","deleteAllData","componentDidCatch","componentStack","newIssueUrl","bugReportSection","clearCacheButton","newIssueLink","onClearCacheAndReload","overflow","tooltipLabel","tooltipShortcut","faces","pileContents","toggled","useToggled","MemberList","mx_FacePile","mx_FacePile_toggled","AvatarStack","_inputRef","_this$props$onFocus","validateOnFocus","_this$props$onChange","validateOnChange","_this$props$onBlur","validateOnBlur","feedbackVisible","_this$inputRef$curren2","_this$inputRef$curren3","_inputProps$placehold","prefixComponent","tooltipContent","forceValidity","tooltipClassName","usePlaceholderAsHint","forceTooltipVisible","tooltipAlignment","tooltipOpen","inputProps_","callbackRef","fieldInput","prefixContainer","postfixContainer","hasValidationFlag","fieldClasses","mx_Field_labelAlwaysTopLeft","mx_Field_placeholderIsHint","mx_Field_valid","mx_Field_invalid","inputDecoration","normalizeWheelEvent","deltaMode","deltaX","deltaY","deltaZ","WheelEvent","MAX_SCALE","thumbnailInfo","zoom","naturalWidth","imageIsLoaded","animatingLoading","setZoomAndRotation","translationX","translationY","inputRotation","imageWrapper","rotation","imageIsNotFlipped","naturalHeight","zoomX","clientWidth","zoomY","minZoom","maxZoom","zoomDelta","offsetX","offsetY","downloadFunction","cur","contextMenuDisplayed","download","_this$props$mxEvent","_this$props$mxEvent2","moving","previousX","previousY","initX","pageX","initY","pageY","nativeEvent","positionX","positionY","getPanelHeight","documentElement","_this$image$current","onWheel","recalculateZoom","imageLoaded","_this$image$current2","anchorX","anchorY","zoomLevel","oldZoom","newZoom","renderContextMenu","contextMenu","contextMenuButton","onCloseContextMenu","_this$props$mxEvent3","showEventMeta","transitionClassName","rotationDegrees","cursor","_mxEvent$sender$name","_mxEvent$sender","messageTimestamp","MessageTimestamp","onPermalinkClicked","showFullDate","ts","inhibitTooltip","_this$props$mxEvent4","onOpenContextMenu","presentableTextForFile","onZoomOutClick","ZoomOutIcon","onZoomInClick","ZoomInIcon","onRotateCounterClockwiseClick","RotateLeftIcon","onRotateClockwiseClick","RotateRightIcon","DownloadButton","fileName","onDownloadReady","onDownloadFunctionReady","onMouseMove","onMoving","onMouseUp","onEndMoving","onMouseLeave","draggable","onStartMoving","canDownload","useDownloadMedia","DownloadIcon","InfoTooltipKind","InfoTooltip","_this$props$tabIndex","InfoIcon","BaseInlineSpinner","AskToJoinIcon","LabelledCheckbox","byline","ItemRange","topCount","renderCount","bottomCount","expand","amount","topGrow","bottomGrow","totalSize","getDerivedStateFromProps","getVisibleRangeFromProps","intersectRange","overflowMargin","renderRange","overflowItems","itemsAfterTop","visibleItems","paddingTop","renderedItems","elementProps","findRoom","roomIdOrAlias","_client$getRooms$find","getRooms","usePermalinkTargetRoom","parseResult","permalinkRoom","shouldLookUpRoom","RoomMention","EventInSameRoom","EventInOtherRoom","initialRoom","determineInitialRoom","AtRoomMention","targetRoom","setTargetRoom","newRoom","createMemberFromProfile","_profile$displayname","getDirectionalContent","usePermalinkMember","shouldLookUpUser","determineUserId","_event$getSender","userInRoom","determineMember","targetRoomMember","knownProfile","getOnlyKnownProfile","fetchedProfile","fetchOnlyKnownProfile","doProfileLookup","usePermalink","forcedType","resourceId","_parseResult","parsePermalink","primaryEntityId","determineType","usePermalinkEvent","shouldLookUpEvent","eventInRoom","determineInitialEvent","eventData","linkIcon","PillRoomAvatar","PillMemberAvatar","UserSolidIcon","propType","inMessage","customPillText","linkText","mx_AtRoomPill","mx_RoomPill","mx_SpacePill","mx_UserPill","mx_UserPill_me","mx_EventPill","mx_KeywordPill","Keyword","pillText","isAnchor","FocusTarget","creatingInitialState","M_POLL_KIND_DISCLOSED","autoFocusTarget","Topic","PollCreateDialog","checkCanSubmit","newOptions","NewOption","_this$addOptionRef$cu","_this$addOptionRef$cu2","addOptionRef","M_POLL_KIND_UNDISCLOSED","editingMxEvent","isEquivalentTo","answers","ans","editingInitialState","op","createEvent","pollStart","PollStartEvent","pollEvent","doMaybeLocalRoomAction","actualRoomId","_this$props$threadId","tryAgain","onPollTypeChange","onQuestionChange","onOptionRemove","onOptionAdd","CUSTOM_VALUE","PowerSelector","custom","selectValue","powerLevelKey","initStateFromProps","customValue","maxValue","arrayHasDiff","isCustom","picker","onCustomBlur","onCustomKeyDown","onCustomChange","optionsElements","onSelectChange","Infinity","useSmoothAnimation","targetValue","setCurrentValue","currentStepSize","setCurrentStepSize","totalDelta","EPSILON","timeDelta","valueDelta","maxValueDelta","clampedValueDelta","sign","handle","cancelAnimationFrame","useAnimation","animated","defaultOptions","errorCorrectionLevel","dataUri","setUri","cancelled","asFullAlias","validationRules","fullAlias","hasColon","final","getRoomIdForAlias","localpart","hashAlias","domainProps","postfix","maxlength","fieldRef","_this$fieldRef$curren","_this$fieldRef$curren2","secureRandomString","_this$props$roomId","_this$props$roomId2","defaultWatchManager","onSettingChange","_this$props$roomId3","_this$props$roomId4","settingIsOveriddenAtConfigLevel","_this$props$roomId5","_this$props$label","hideIfCannotSet","getDescription","shouldHaveWarning","initialId","descriptionId","InlineField","control","CheckboxInput","Label","HelpMessage","outlined","childrenInLabel","_className","mx_StyledRadioButton_disabled","mx_StyledRadioButton_enabled","mx_StyledRadioButton_checked","mx_StyledRadioButton_outlined","radioButton","_onChange","_d$disabled","highlightAuto","TextWithTooltip","toArray","overflowNode","totalChildren","upperBound","childNodes","hideDescriptionIfValid","memoize","checkRules","derivedData","_rule$skip","skip","ruleValid","memoizeOne","isDataEqual","isDerivedDataEqual","_deriveData","mx_Validation_detail","mx_Validation_valid","mx_Validation_invalid","a1","a2","b1","b2","Header","changeCategoryRelative","changeCategoryAbsolute","categories","findNearestEnabled","cats","visible","_category$ref$current","onAnchorClick","mx_EmojiPicker_anchor_visible","firstVisible","Search","onEnter","_this$context$state$a","rightButton","Preview","unicode","shortcode","Emoji","selectedEmojis","QUICK_REACTIONS","QuickReactions","hover","Toolbar","hexcode","hexEncode","hex","rowIndex","emojis","emojisForRow","_this$props$isEmojiDi","isEmojiDisabled","viewportHeight","EMOJIS_PER_ROW","CATEGORY_HEADER_HEIGHT","EMOJI_HEIGHT","localHeight","localScrollTop","renderEmojiRow","EmojiPicker","_this$scrollRef$curre","updateVisibility","showHighlight","keyboardNavigation","_this$scrollRef$curre2","rect","firstVisibleFound","cat","_cat$ref$current","elemRect","yEnd","_this$scrollRef$curre3","lcFilter","memoizedDataByCategory","recentlyUsed","DATA_BY_CATEGORY","emojiMatchesFilter","indexA","indexB","_emoji$emoticon","emoticon","_this$scrollRef$curre4","btn","previewEmoji","onChoose","recent","hasRecentlyUsed","categoryConfig","isVisible","getRow","rovingNode","_this$getGridcell$par","_this$getGridcell","getGridcell","_rovingNode$parentEle","getRovingNode","gridcellNode","rowElement","columnIndex","refIndex","newRowElement","_newRowElement","newColumnIndex","inline","categoryHeightForEmojiCount","scrollToCategory","onChangeFilter","onEnterFilter","mx_EmojiPicker_body_showHighlight","categoryElement","onClickEmoji","onHoverEmoji","onHoverEmojiEnd","myReactions","canSelfRedact","FocusAComposer","Reaction","addListeners","onReactionsChange","RelationsEvent","Redaction","_this$props$reactions","_this$props$reactions2","myAnnotations","getAnnotationsBySender","_event$getRelation","MapError","isMinimised","mx_MapError_isMinimised","getLocationShareErrorMessage","SvgMap","maskUnits","maskType","mask","MapFallbackImage","LocationMarkerIcon","MapComponent","SmartMarkerComponent","SmartMarker","LocationButtonComponent","LocationButton","LocationViewDialogComponent","LocationViewDialog","JumpToDatePicker","onDatePicked","dateInputDefaultValue","dateValue","setDateValue","refCallback","onJumpToDateSubmit","onInput","DateSeparator","contextMenuPosition","unixTimestamp","inputTimestamp","roomIdForJumpRequest","originServerTs","timestampToEvent","Direction","Forward","currentRoomId","dispatcher","friendlyErrorMessage","submitDebugLogsContent","ConnectionError","dateString","httpStatus","HTTPError","debugLogsLink","onBugReport","setDate","pickDate","setMonth","jumpToDateEnabled","settingWatcherRef","newValAtLevel","newVal","relativeTimeFormat","RelativeTimeFormat","numeric","getLabel","disableRelativeTimestamps","TimelineEnableRelativeDates","forExport","today","yesterday","renderJumpToDateMenu","onContextMenuCloseClick","capitalize","onLastWeekClicked","onLastMonthClicked","onTheBeginningClicked","onContextMenuOpenClick","dateHeaderContent","TimelineSeparator","EncryptionEvent","dmPartner","_room$getMember","EventTileBubble","HiddenMediaPlaceholder","MAX_NON_NARROW_WIDTH","VoiceCallMissedSolidIcon","VideoCallMissedSolidIcon","VideoCallDeclinedSolidIcon","LegacyCallEvent","wrapperElementEntry","entry","wrapperElement","narrow","contentRect","callState","callEventGrouper","onStateChanged","onSilencedChanged","resizeObserver","ResizeObserver","resizeObserverCallback","observe","_this$resizeObserver","renderCallBackButton","callBack","renderSilenceIcon","toggleSilenced","silenceIcon","rejectCall","InviteTimeout","IceFailed","callType","mx_LegacyCallEvent_voice","mx_LegacyCallEvent_video","mx_LegacyCallEvent_narrow","iconState","AudioPlayerViewModel","BaseViewModel","computeSnapshot","mediaName","snapshot","disposables","trackListener","setSnapshot","preparePlayback","setProps","percentComplete","playbackState","playedSeconds","MAudioBody","_content$orgMatrixM","blob","mediaEventHelper","sourceBlob","onMount","_this$state$playback","showFileBody","Pinned","MediaProcessingError","_content$file","contentUrl","AudioPlayer","MFileBody","showGenericPlaceholder","vm","useCreateAutoDisposedViewModel","AudioPlayerView","DOWNLOAD_ICON_URL","computedStyle","cssText","svg","btoa","cacheDownloadIcon","FileDownloader","decryptedBlob","userDidClick","mediaHelper","decryptFile","downloadFile","fileDownloader","getContentUrl","mediaFromContent","_this$props$mediaEven","downloadLabelForFile","autoDownload","imgSrc","imgStyle","dummyLink","_this$props$mediaEven2","_this$content$info$mi","_this$content$info","_this$props$showGener","fileType","mimetype","showDownloadLink","AttachmentIcon","onPlaceholderClick","onLoad","sandbox","downloadProps","_this$props$mediaEven3","blobUrl","tempAnchor","Placeholder","MImageBodyInner","thumbUrl","imgError","imgLoaded","NoImage","mediaVisible","setMediaVisible","httpUrl","isMimeTypeAllowed","cachedValue","clientRect","createReconnectedListener","reconnectedListener","clearBlurhashTimeout","loadedImageDimensions","shouldAutoplay","isAnimated","srcMxc","getThumbUrl","thumbWidth","thumbHeight","hasThumbnail","getThumbnailHttp","devicePixelRatio","isLargerThanThumbnail","downloadImage","_this$props$mediaEven4","_content$info$orgMat","_content$info","_content$info2","sourceUrl","thumbnailUrl","DecryptError","DownloadError","mayBeAnimated","_content$info3","thumbnail_info","loadPromise","onload","crossOrigin","_content$info4","blobIsAnimated","_content$info$mimetyp","_content$info5","thumb","createThumbnail","thumbnail","_this$props$mxEvent$g","BLURHASH_FIELD","Blurhash","sizeWatcher","getBanner","File","messageContent","forcedHeight","_content$info6","_content$info7","infoWidth","infoHeight","infoSvg","imageElement","onImageError","onImageLoad","wrapImage","maxWidth","maxHeight","suggestedImageSize","maxImageHeight","gifLabel","_this$props$mxEvent$g2","getPlaceholder","showPlaceholder","hoverOrFocus","onImageEnter","onImageLeave","banner","sizing","SwitchTransition","mode","CSSTransition","getTooltipProps","aspectRatio","_this$props$mxEvent$g3","blurhash","getFileBody","_this$props$mediaEven5","_content$info$mimetyp2","_content$info8","_content$info9","ImageErrorIcon","_this$props$mxEvent$g4","_this$props$mxEvent$g5","_this$state$thumbUrl","fileBody","setVisible","useMediaVisible","voteRelations","votes","countVotes","collectUserVotes","allVotes","highestScore","bestAnswerIds","answerId","score","bestAnswerTexts","_poll$answers$find$te","_poll$answers$find","isFetchingResponses","isEnded","pollAlreadyHasVotes","relationsList","pollResponseRelations","M_POLL_RESPONSE","pollResposnseAltRelations","RelatedRelations","createVoteRelations","getRelations","launchPollEditor","MPollBody","onRelationsChange","unselectIfNewEventFromMe","pollInitialised","setPollInstance","PollEvent","New","removeListeners","pollId","_this$state$poll","_this$state$poll2","_this$state$poll3","Responses","onResponsesChange","UndecryptableRelations","selectOption","_this$state$poll4","_userVotes$get","userVotes","PollResponseEvent","_this$state$voteRelat","newEvents","seenEventIds","newSelected","newEventIds","totalVotes","collectedVotes","sum","_userVotes$get2","winCount","myVote","disclosed","showResults","totalText","undecryptableRelationsCount","editedSpan","PollIcon","PollsEndIcon","pollLabel","answerVotes","_votes$get","PollOption","optionNumber","isChecked","voteCount","totalVoteCount","displayVoteCount","onOptionSelected","UserVote","userResponseFromPollResponseEvent","answerIds","userResponses","otherResponse","collected","tempResponse","validateAgainst","spoiled","PlaybackQueue","loadClocks","addRoomListener","currentPlaybackId","recentFullPlays","playbackIdOrder","queues","queue","persistClocks","clockStates","unsortedEnqueue","playbacks","onPlaybackStateChange","onPlaybackClock","wasLastPlaying","currentClockState","orderClone","last","nextEv","scanForVoiceMessage","isVoiceMessage","havePlayback","isRecentlyCompleted","lastInstance","clocks","MVoiceMessageBody","LinkWithTooltip","ambiguousLinkTooltipRenderer","anchor","isHtml","domToReact","AT_ROOM_REGEX","getPushRuleGlobRegex","isPreCode","domNode","mentionPillRenderer","hasParentMatching","shouldBePillified","TEXT_NODE","atRoomRule","IsRoomMention","AtRoomNotification","ruleMatchesEvent","reactStringReplace","_match","keywordPillRenderer","keywordRegexpPattern","Spoiler","toggleVisible","spoilerRenderer","ExpandCollapseButton","CollapseIcon","ExpandIcon","CodeBlock","preNode","enableSyntaxHighlightLanguageDetection","showCodeLineNumbers","expandCodeByDefault","setExpanded","expandCollapseButton","getInnerHTML","lineNumbers","ParserElement","mx_EventTile_collapsedCodeBlock","getElementsByTagName","advertisedLang","maybeLang","getLanguage","_code$textContent","_code$textContent2","highlightCode","mx_EventTile_buttonBottom","codeBlockRenderer","pre","useReplacer","_cli$getRoom","replacer","_pushDetails$rule","pushDetails","getPushDetails","ContentSpecific","getPushDetailsKeywordPatternRegexp","combineRenderers","renderers","parameters","_replacer$Node$TEXT_N","parametersWithReplace","Element","_replacer$tagName","renderMentionPills","renderKeywordPills","renderTooltipsForAmbiguousLinks","renderSpoilers","renderCodeBlocks","memo","stripReply","includeDir","enableBigEmoji","isEmote","As","applyReplacerOnString","getSanitizedHtmlBody","textToHtml","wrapInsertion","wrapper","wrapDeletion","diffTreeToDOM","desc","stringAsTextNode","attributes","childDesc","insertBefore","nextSibling","isRouteOfNextSibling","route1","route2","lastD1Idx","adjustRoutes","remainingDiffs","advance","rd","route","string","createTextNode","unescape","renderDifferenceInDOM","originalRootNode","diffMathPatch","refNode","refParentNode","isAddition","_refNode","findRefNodes","delNode","oldValue","insNode","replaceChild","textDiffs","diff_main","diff_cleanupSemantic","modifier","textDiffNode","cloneNode","updatedNode","removeAttribute","ConfirmAndWaitRedactDialog","isRedacting","redact","redactionErrorCode","onParentFinished","getReplacedContent","getOriginalContent","EditHistoryMessage","_event$localRedaction","_room$currentState$ma","sendStatus","getAssociatedStatus","localRedactionEvent","onAssociatedStatusChanged","_event$localRedaction2","renderActionBar","isBaseEvent","contentContainer","RedactedBody","contentElements","previousEdit","editContent","originalBody","editBody","diffActions","DiffDOM","DiffMatchPatch","editBodyDiffToHtml","EventContentBody","isTwelveHour","isSending","mx_EventTile_sending","MessageEditHistoryDialog","_this$state$nextBatch","_this$state$originalE","_result$nextBatch","nextBatch","relations","Replace","locallyRedactEventsIfNeeded","originalEvent","pendingRedaction","pe","RoomRedaction","markLocallyRedacted","loadMoreEdits","renderEdits","lastEvent","allEvents","baseEventId","createEditContent","editedEvent","replyToEvent","containsEmote","stripEmoteCommand","textSerialize","htmlSerializeIfNeeded","useMarkdown","attachMentions","attachRelation","EditMessageComposer","_this$context$room","_this$editorRef$curre","isComposing","sendEdit","cancelEdit","_this$editorRef$curre2","_this$editorRef$curre3","isModified","isCaretAtStart","findEditableEvent","isForward","fromEventId","editState","getEvent","EditEvent","_this$editorRef$curre4","_this$editorRef$curre5","isCaretAtEnd","nextEvent","endEdit","clearPreviousEdit","saveDisabled","messageType","isReply","caret","getCaret","positionForOffset","atNodeEnd","replaceEmoticon","REGEX_EMOTICON","shouldSend","cancelPreviousPendingEdit","isContentModified","isSlashCommand","commandText","getSlashCommand","_editedEvent$getThrea","commandSuccessful","runSlashCommand","CommandCategories","effects","sendAnyway","shouldSendAnyway","sendMessage","_this$editorRef$curre6","composerType","ComposerType","Edit","_this$editorRef$curre7","insertMention","_this$editorRef$curre8","insertQuotedMessage","_this$editorRef$curre9","insertPlaintext","FocusEditMessageComposer","isRestored","createEditorModel","saveStoredEditorState","_this$context$liveTim","liveTimelineEvents","liveTimeline","isInThread","shouldSaveStoredEditorState","restoreStoredEditorState","partCreator","serializedParts","deserializePart","oldContent","QUEUED","_this$editorRef$curre0","sel","getCaretOffsetAndText","setEditorState","CommandPartCreator","hasEditorState","getSerializedParts","restoredParts","parseEvent","shouldEscape","EditorModel","_this$props$editState","_this$props$editState2","BasicMessageComposer","initialCaret","withMatrixClientHOC","LinkPreviewWidget","_src","_p$ogImage","_ImageUtils$thumbHeig","_p$ogTitle$trim","_p$ogTitle","imageMaxHeight","fullWidth","fullHeight","widthMulti","heightMulti","ImageUtils","onImageClick","needsTooltip","fetchPreviews","links","_preview$ogImage","getUrlPreview","LinkPreviewGroup","toggleExpanded","useStateToggle","previews","showPreviews","toggleButton","TextualBody","widgetHidden","linkifyOpts","localHref","starterLink","managers","IntegrationManagers","hasManager","openNoManagerDialog","integrationManager","getPrimaryManager","scalarClient","getScalarClient","completeUrl","getStarterLink","integrationsUrl","uiUrl","features","opener","applyFormatting","calculateUrlPreview","stoppedEditing","messageWasEdited","replacingEventId","urlPreviewChanged","showUrlPreview","shouldComponentUpdate","nextProps","nextState","isSeeingThroughMessageHiddenForModeration","contentRef","findLinks","isLinkPreviewable","_node$getAttribute","_url$match","_node$textContent","_node$textContent2","isPermalinkHost","renderEditedMarker","replacingEventDate","openHistoryDialog","renderPendingModerationMarker","messageVisibility","EditWysiwygComposer","editorStateTransfer","isNotice","Notice","isCaption","willHaveWrapper","getParentEventId","onStarterLinkClick","onBodyLinkClick","onEmoteSenderClick","MVoiceOrAudioBody","MVideoBodyInner","fetchingData","decryptedUrl","decryptedThumbnailUrl","posterLoading","blurhashUrl","hasContentUrl","videoRef","_content$file$url","_this$state$decrypted","_media$srcHttp","thumbnailHttp","loadBlurhash","suggestedVideoSize","pixels","imgData","createImageData","putImageData","downloadVideo","autoplay","inhibitInteraction","spaceFiller","poster","preload","controlsList","muted","autoPlay","onPlay","videoOnPlay","MStickerBodyInner","MLocationBody","idSuffix","mapId","clearError","LocationBodyFallbackContent","LocationBodyContent","_event$getContent2","errorType","locationFallback","isSelfLocation","LocationShareError","MapStyleUrlNotConfigured","markerRoomMember","geoUri","locationEventGeoUri","mapElement","centerGeoUri","MjolnirBody","_this$props$onMessage","onMessageAllowed","onAllowClick","BeaconViewDialogComponent","BeaconViewDialog","MBeaconBody","beaconInfoEvent","useBeacon","LivenessChange","LocationUpdate","isBeaconWaitingToStart","useBeaconState","setId","useUniqueId","isMapDisplayError","MapStyleUrlNotReachable","isOwnBeacon","beaconInfoOwner","useHandleBeaconRedaction","onBeforeBeaconInfoRedaction","_event","redactionEvent","_relations$getRelatio","Reference","locationEvent","initialFocusedBeacon","useMemberColor","mx_MBeaconBody_mapErrorInteractive","MapFallback","OwnBeaconStatus","baseBodyTypes","MImageBody","MVideoBody","baseEvTypes","MStickerBody","M_BEACON_INFO","MessageEvent","_this$body$current","_this$body$current$ge","getEventTileOps","_this$mediaHelper","MediaEventHelper","isEligible","_content$filename","_mime$getType","filename","validateThumbnailMimetype","typeFromExtension","mime","extensionMajorMimetype","parseMajorMimetype","validateAllowedMimetype","contentMimetype","contentMajorMimetype","thumbnailMimetype","allowedMajorMimeTypes","majorMimetype","updateComponentMaps","onDecrypted","_this$mediaHelper2","_this$mediaHelper3","bodyTypes","bodyType","bodyComponent","_this$props$overrideB","overrideBodyTypes","evTypes","evComponent","_this$props$overrideE","overrideEventTypes","getMediaHelper","BodyType","DecryptionFailureBodyWrapper","UnknownBody","validateImageOrVideoMimetype","validateStickerMimetype","Location","userDomain","userBanned","Mjolnir","isUserBanned","serverBanned","isServerBanned","hasCaption","bodyProps","onTileUpdate","CaptionBody","WrappedBodyType","verificationState","LocalDeviceVerificationStateContext","DecryptionFailureBodyViewModel","decryptionFailureCode","decryptionFailureReason","setVerificationState","DecryptionFailureBodyView","SvgSensor","showRelative","receivedTs","dateTime","receivedDate","LateIcon","fullDate","titleText","FileErrorIcon","SvgTrophy","PollOptionContent","isWinner","votesText","TrophyIcon","ActivePollOption","cls","mx_PollOption","mx_PollOption_checked","mx_PollOption_ended","answerPercent","FilterTabGroup","onFilterChange","PollListItem","formattedDate","getWinningAnswers","responseRelations","vote","winningAnswers","answerIndex","PollListItemEnded","setResults","onPollResponses","usePollVotes","LoadingPolls","noResultsYet","mx_PollHistoryList_noResultsYet","LoadMorePolls","loadMorePolls","NoResults","oldestFetchedEventTimestamp","getNoResultsMessage","oldestEventTimestamp","fetchedHistoryDaysCount","PollHistoryList","pollStartEvents","onItemClick","pollStartEvent","PollDetailHeader","onNavigateBack","LeftCaretIcon","PollDetail","requestModalClose","eventIdToLinkTo","endEventId","linkToTimeline","usePollsWithRelations","usePolls","pollsWithRelations","setPollsWithRelations","onPollUpdate","getOldestEventTimestamp","timelineSet","_events$","pagePollHistory","canPageBackward","paginateEventTimeline","getPaginationToken","fetchHistoryUntilTimestamp","filterDefinition","types","useFetchPastPolls","historyPeriodDays","setTimelineSet","setDefinition","filterId","getOrCreateFilter","getOrCreateFilteredTimelineSet","getFilteredTimelineSet","loadTimelineHistory","useTimelineHistory","setIsLoading","setOldestEventTimestamp","setCanPageBackward","endOfHistoryPeriodTimestamp","_timelineSet$getLiveT","Backward","sortEventsByLatest","setFilter","focusedPollId","setFocusedPollId","filterAndSortPolls","filterPolls","isLoadingPollResponses","focusedPoll","closeRightPanel","popCard","BaseCard","closeLabel","ariaLabelledBy","hideHeaderButtons","header","withoutScrollContainer","closeButtonRef","backButton","cardHistory","roomPhaseHistory","_backLabelForPhase","prevCard","backLabelForPhase","IconButton","ChevronLeftIcon","closeButton","shouldRenderHeader","PendingActionSpinner","EncryptionInfo","waitingForOtherParty","waitingForNetwork","onStartVerification","inDialog","isSelfVerification","VerificationQRCode","qrCodeBytes","VerificationPanel","_this$state$reciproca","reciprocateQREvent","reciprocateButtonClicked","_this$state$reciproca2","emojiButtonClicked","startVerification","_this$state$sasEvent","sasEvent","_this$state$sasEvent2","mismatch","verifier","getShowSasCallbacks","getReciprocateQrCodeCallbacks","VerifierEvent","ShowSas","updateVerifierState","ShowReciprocateQr","maybeGetOtherDevice","Phase","Ready","haveFetchedQRCode","generateQRCode","hadVerifier","hasVerifier","_request$verifier","_request$verifier2","_request$verifier3","verify","renderQRPhase","showSAS","otherPartySupportsMethod","showQR","ScanQrCode","noCommonMethodError","qrBlockDialog","sasBlockDialog","startSAS","or","emojiCompare","qrCode","qrBlock","sasBlock","sasLabel","noCommonMethodBlock","_this$props$request","haveCheckedDevice","otherDeviceId","otherDeviceDetails","renderQRReciprocatePhase","onReciprocateYesClick","onReciprocateNoClick","renderVerifiedPhase","renderCancelledPhase","chosenMethod","VerificationShowSas","sas","onSasMismatchesClick","onSasMatchesClick","isSelf","Done","Cancelled","VerificationRequestEvent","Change","onRequestChange","MISMATCHES","verificationRequest","verificationRequestPromise","setRequest","isRequesting","setRequesting","doSetPhase","setPhase","VerificationPhase","requestFromPromise","awaitPromise","isShowingMismatchModal","changeHandler","_request$cancellation","cancellationCode","verificationRequest_","requestVerificationDM","currentCard","EncryptionPanel","pushCard","togglePanel","Requested","initiatedByMe","transactionId","useUserfoHeaderViewModel","showPresence","precenseInfo","lastActiveAgo","enablePresenceByHsUrl","timezoneInfo","useUserTimezone","setTimezone","updateInterval","setUpdateInterval","friendly","setFriendly","setSupported","doesServerSupportExtendedProfiles","_userProfile$ProfileK","userProfile","getExtendedProfile","tz","ProfileKeyTimezone","ProfileKeyMSC4175Timezone","updateTime","toLocaleString","getSeconds","onMemberAvatarClick","useUserInfoVerificationViewModel","userTrust","_cli$getCrypto2","hasUserVerificationStatus","isUserVerified","isMe","canVerify","hasCrossSigningKeys","useHasCrossSigningKeys","userHasCrossSigningKeys","verifySelectedUser","verifyUser","UserInfoHeaderVerificationView","Badge","VerifiedIcon","justify","UserInfoHeaderView","hideVerificationSection","_vm$timezoneInfo$time","_vm$timezoneInfo","_vm$timezoneInfo$frie","_vm$timezoneInfo2","presenceLabel","PresenceLabel","activeAgo","presenceState","coloured","getPowerLevels","_room$currentState","useRoomPermissions","roomPermissions","setRoomPermissions","modifyLevelMax","updateRoomPermissions","_powerLevels$invite","powerLevels","them","_powerLevels$events$E","_powerLevels$events","editPowerLevel","useUserInfoBasicViewModel","useRoomPowerLevels","setPowerLevels","isSynapseAdmin","isSynapseAdministrator","useIsSynapseAdmin","pendingUpdateCount","setPendingUpdateCount","isRoomDMForMember","isMemberSameDomain","showDeactivateButton","startUpdating","stopUpdating","onSynapseDeactivate","deactivateSynapseUser","PowerLevelSection","useUserInfoPowerlevelViewModel","selectedPowerLevel","setSelectedPowerLevel","onPowerChange","powerLevelEvent","myPower","warnSelfDemote","applyPowerChange","setPowerLevel","powerLevelUsersDefault","PowerLevelEditor","IgnoreToggleButton","unignore","ignoredUsers","getIgnoredUsers","setIgnoredUsers","ignore","isIgnored","setIsIgnored","isUserIgnored","accountDataHandler","ignoreButtonClick","useUserInfoIgnoreButtonViewModel","onSelect","BlockIcon","spaceChildFilter","allLabel","specificLabel","noneLabel","warningMessage","spaceChildren","roomsToLeave","setRoomsToLeave","selectedRooms","InfoSolidIcon","SpaceChildrenPicker","useBanButtonViewModel","isUpdating","isBanned","banLabel","onBanOrUnbanClick","commonProps","ConfirmSpaceUserActionDialog","myMember","theirMember","bulkSpaceBehaviour","unban","ban","keepStateEvents","setKeepStateEvents","eventsToRedact","isRedaction","getNeighbouringTimeline","BulkRedactStart","BulkRedactEnd","RoomKickButton","onKickClick","canUserBeKicked","kickLabel","useRoomKickButtonViewModel","RedactMessagesButton","onRedactAllMessagesClick","BulkRedactDialog","useRedactMessagesButtonViewModel","BanToggleButton","ChatProblemIcon","MuteToggleButton","isMuted","powerLevelContent","levelToSend","events_default","muteLabel","isMemberInTheRoom","onMuteButtonClick","_powerLevels$events$m","useMuteButtonViewModel","VisibilityOffIcon","UserInfoAdminToolsContainer","kickButton","banButton","muteButton","banPowerLevel","kickPowerLevel","redactPowerLevel","isCurrentUserInTheRoom","shouldShowKickButton","shouldShowBanButton","shouldShowMuteButton","shouldShowRedactButton","canAffectUser","useUserInfoAdminToolsContainerViewModel","MessageButton","openDMForUser","ChatIcon","UserInfoBasicOptionsView","useUserInfoBasicOptionsViewModel","isSpace","readReceiptButtonDisabled","getEventReadUpTo","showInsertPillButton","showInviteButton","onReadReceiptButton","onInsertPillButton","onInviteUserButton","fallbackRoomId","getCompletionState","errorStringFromInviterUtility","onShareUserClick","onOpenDmForUser","startDmUser","insertPillButton","inviteUserButton","readReceiptButton","MentionIcon","InviteIcon","shareUserButton","directMessageButton","UserInfoBasicView","synapseDeactivateButton","spinner","memberDetails","adminToolsContainer","downloadUncached","userDeviceMap","devicesMap","useDevices","setDevices","create","_devices$i$displayNam","indexList","j","ambiguous","disambiguateDevices","downloadDeviceList","updateDevices","newDevices","onDevicesUpdated","onUserTrustStatusChanged","_userId","trustLevel","CryptoEvent","DevicesUpdated","UserTrustStatusChanged","_useDevices","MemberInfo","cardState","onEncryptionPanelClose","pending","previousCard","ReadPinsEventId","EditableItem","verifyRemove","onActuallyRemove","onDontRemove","EditableItemList","_this$props$onItemAdd","onItemAdded","newItem","_this$props$onItemRem","onItemRemoved","_this$props$onNewItem","onNewItemChanged","renderNewItemField","suggestionsListId","editableItems","editableItemsSection","itemsLabel","noItemsLabel","RoomPublishSetting","setRoomDirectoryVisibility","showError","getRoomDirectoryVisibility","_DirectoryCustomisati","isRoomPublishable","DirectoryCustomisations","requireCanonicalAliasAccessToPublish","onRoomPublishChange","EditableAliasesList","onAliasAdded","localDomain","createAlias","changeCanonicalAlias","deleteAlias","loadLocalAliases","newAltAlias","changeAltAliases","updatingCanonicalAlias","localAliasesLoading","eventContent","getAliases","getLocalNonAltAliases","_mxClient$getRoom","found","canonicalValue","canonicalAliasSection","onCanonicalAliasChange","localAliasesList","onNewAliasChanged","onLocalAliasAdded","onLocalAliasDeleted","hidePublishSetting","onNewAltAliasChanged","onAltAliasAdded","onAltAliasDeleted","onLocalAliasesToggled","ROOM_REGEX","matcherObject","displayedAlias","matchName","RoomProvider","matcherObjects","tombstone","r2","matchedString","canonicalScore","EMOTICON_REGEX","SORTED_EMOJI","EMOJI","group","_orderBy","EmojiProvider","nameMatcher","sorters","trimmedMatch","recentlyUsedAutocomplete","exactMatchEmoji","NotifProvider","mayTriggerNotifOfType","PROVIDERS","Autocompleter","providers","Prov","completionsList","provider","generateCompletionDomId","Autocomplete","hide","selectionOffset","completionList","onCompletionClicked","countCompletions","onConfirm","shouldShowCompletions","forceComplete","autocompleter","applyNewProps","oldQuery","_this$autocompleter","complete","_this$autocompleter2","queryRequested","debounceCompletionsRequest","autocompleteDelay","processCompletions","flatMap","currentSelection","onSelectionChange","moveSelection","completionCount","setSelection","onEscape","_this$completionRefs","selectedCompletion","completionRefs","scrollTo","renderedCompletions","completionResult","componentPosition","refId","HistoryManager","stack","newlyTypedCharCount","changedSinceLastPush","lastCaret","nonWordBoundarySinceLastPush","addedSinceLastPush","removedSinceLastPush","shouldPush","inputType","added","isWordBoundary","pushState","tryPush","ensureLastChangesPushed","canUndo","canRedo","undo","redo","editor","Range","removeAllRanges","selectionRange","createRange","getNodeAndOffsetForPosition","setStart","setEnd","addRange","setDocumentRangeSelection","caretPosition","collapse","existingRange","startOffset","setCaretPosition","lineIndex","nodeIndex","partIndex","lineResult","prevPart","Newline","needsCaretNodeBefore","nextPart","isLastOfLine","needsCaretNodeAfter","findNodeInLineForPart","acceptsCaret","moveOutOfUnselectablePart","getLineAndNodePosition","lineNode","nodeType","ELEMENT_NODE","Formatting","MessageComposerFormatBar","mx_MessageComposerFormatBar_shown","formatBarRef","FormatButton","Bold","BoldIcon","shortcut","shortcuts","bold","Italics","ItalicIcon","italics","Strikethrough","StrikethroughIcon","Code","Quote","quote","InsertLink","insert_link","showAt","selectionRect","_this$formatBarRef$cu","parentRect","halfBarHeight","BAR_HEIGHT","offsetLimit","formatRange","wasInitializedEmpty","expandForwardsWhile","isFormattable","expandBackwardsWhile","selectRangeOfWordAtCaret","toggleInlineFormat","hasBlockFormatting","needsBlockFormatting","_parts$","_parts","fenceLen","longestBacktickSequence","hasInlineFormatting","repeat","plain","newline","rangeStartsAtBeginningOfLine","rangeEndsAtEndOfLine","replaceRangeAndExpandSelection","formatRangeAsCode","formatRangeAsQuote","formatRangeAsLink","newParts","oldLen","addedLen","firstOffset","asOffset","startRange","asPosition","replaceRangeAndMoveCaret","_index","Plain","startsWithPartial","isFirstPart","previousIsNewline","lastPart","endsWithPartial","isLastPart","nextIsNewline","linkRegex","linkDescription","isBlank","isNL","paragraphIndexes","lastNonEmptyPart","lastIndexOf","startIdx","endIdx","base","partWithoutPrefix","deserializedPart","partWithoutSuffix","suffixPartText","hasFormatting","rangeHasFormatting","prefixLength","suffixLength","lastStartingPosition","getLastStartingPosition","relativeOffset","distanceFromEnd","offsetDirection","atEnd","replaceRangeAndAutoAdjustCaret","REGEX_EMOTICON_WHITESPACE","SURROUND_WITH_CHARACTERS","SURROUND_WITH_DOUBLE_CHARACTERS","ctrlShortcutLabel","needsShift","needsAlt","cloneSelection","anchorNode","anchorOffset","focusOffset","isCollapsed","BasicMessageEditor","_this$props$model$aut","renderModel","setLastCaretFromPosition","hidePlaceholder","showVisualBell","historyManager","isTyping","parseCommandString","typingStore","setSelfTyping","isIMEComposing","isSafari","getRangeForSelection","selectedParts","setData","modifiedFlag","onCutCopy","_this$props$onPaste","plainText","partsText","parsePlainTextMessage","onPasteHandler","dataTransfer","lastSelection","refreshLastCaretIfNeeded","_this$formatBarRef$cu2","hasTextSelected","_model$autoComplete","which","surroundWith","navAction","autocompleteAction","accessibilityAction","hasCompletions","confirmCompletion","selectPreviousSelection","selectNextSelection","_this$formatBarRef$cu3","tabCompleteName","onFormatAction","insertText","_this$props$model$aut2","onComponentConfirm","completionIndex","setTransformCallback","showPillAvatar","documentPosition","ua","configureEmoticonAutoReplace","enabledChange","placeholderChanged","regex","PillCandidate","emoticonMatch","EMOTICON_TO_EMOJI","firstMatch","moveStart","moveStartForwards","moveEndBackwards","_this$props$placehold","CSS","textToInsert","_isCaretAtEnd","isAtEnd","clearUndoHistory","isSelectionCollapsed","Command","pillCandidate","startSelection","onBeforeInput","onCompositionStart","onCompositionEnd","useMarkdownHandle","emoticonSettingHandle","shouldShowPillAvatarSettingHandle","surroundWithHandle","_this$editorRef$curre1","_this$editorRef$curre10","_this$editorRef$curre11","configureUseMarkdown","configureShouldShowPillAvatar","surroundWithSettingChanged","setUpdateCallback","updateEditorState","setAutoCompleteCreator","getAutoCompleteCreator","autocompleteRef","getInitialCaretPosition","getPositionAtEnd","_this$autocompleteRef","queryLen","onAutoCompleteConfirm","onAutoCompleteSelectionChange","wrapperClasses","mx_BasicMessageComposer_input_error","mx_BasicMessageComposer_input_shouldShowPillAvatar","mx_BasicMessageComposer_input_disabled","hasAutocomplete","activeDescendant","contentEditable","onCopy","onCut","translate","_this$editorRef$curre12","createMentionParts","insert","quoteParts","isQuotedMessage","plainWithEmoji","crossSigningUserTitles","crossSigningRoomTitles","icons","ShieldIcon","tooltipPlacement","e2eTitle","ExtraTile","isMinimized","ignoreHover","hovered","setHoverState","useHover","mx_ExtraTile","mx_RoomTile","mx_RoomTile_selected","mx_RoomTile_minimized","nameClasses","mx_RoomTile_title","mx_RoomTile_titleHasUnreadEvents","isUnread","nameContainer","TAG_ORDER","Untagged","Conference","ServerNotice","Suggested","ALWAYS_VISIBLE_TAGS","auxButtonContextMenuPosition","TAG_AESTHETICS","sectionLabel","isInvite","defaultHidden","AuxButtonComponent","DmAuxButton","menuDisplayed","openMenu","activeSpace","UPDATE_SELECTED_SPACE","activeSpaceRoom","showCreateRooms","showInviteUsers","shouldShowSpaceInvite","UserAddSolidIcon","CreateChat","UntaggedAuxButton","showCreateRoom","showExploreRooms","ExploreRooms","contextMenuContent","RoomIcon","showAddExistingRooms","CreateRoom","ViewRoomDirectory","LegacyRoomList","updateLists","_SdkContextClass$inst","ViewRoomDelta","viewRoomDeltaPayload","getRoomDelta","unread","show_room_tile","metricsViaKeyboard","listRooms","suggestedRooms","newLists","previousListIds","sublists","newListIds","oldRooms","newRooms","newSublists","objectWithOnly","objectShallowClone","onRoomViewStoreUpdate","UPDATE_SUGGESTED_ROOMS","updateSuggestedRooms","updateProtocolSupport","renderSuggestedRooms","_room$aliases","canonical_alias","_room$aliases2","room_alias","via_servers","oob_data","renderSublists","_this$state$suggested","showSkeleton","every","orderedTagId","extraTiles","alwaysVisible","MetaSpace","Favourites","Orphans","VideoRooms","isMetaSpace","forceExpanded","RoomSublist","forRooms","startAsHidden","sectionLabelRaw","onListCollapse","_this$treeRef$current","_find","treeItems","treeRef","mx_LiveContentSummary_text_active","showCounts","NotificationStateEvents","onNotificationUpdate","countWatcherRef","countPreferenceChanged","showUnsentTooltip","knocked","StatelessNotificationBadge","forceDot","hideBold","hasUnreadCount","isEmptyBadge","formatCount","badgeType","getPrettyPresence","mx_PresenceLabel_online","CurrentRightPanelPhaseContext","currentPhase","isPanelOpen","HEADER_HEIGHT","getLabelId","TouchEvent","UIEvent","changedTouches","targetTouches","touches","scale","roomsLoading","stateUpdates","currentRooms","arrayHasOrderChange","roomIndex","toggleCollapsed","numVisibleTiles","visibleTiles","tilesWithPadding","SHOW_N_BUTTON_HEIGHT","travelDirection","refToElement","heightAtStart","applyHeightChange","tilesToPixelsWithPadding","numTiles","padding","focusRoomTile","defaultVisibleTiles","sublistRef","elements","newAlgorithm","getListOrder","ListAlgorithm","Importance","Natural","setListOrder","setTagSorting","notifState","getForRoom","_this$headerButton$cu","_possibleSticky$paren","_sublist$parentElemen","possibleSticky","sublist","listScrollTop","isAtTop","offsetHeight","isStickyTop","isStickyBottom","_this$headerButton$cu2","RoomListLayoutStore","getLayoutFor","getListState","calculateInitialHeight","requestedVisibleTiles","minVisibleTiles","tileCount","needsShowMore","needsShowLess","_this$props$extraTile","calcNumTiles","nVisible","prevExtraTiles","prevStateNoRooms","objectExcluding","nextStateNoRooms","nextExtraTiles","prevSlicedRooms","nextSlicedRooms","_this$tilesRef$curren","onListsUpdated","LISTS_LOADING_EVENT","onListsLoading","tilesRef","onScrollPrevent","_this$tilesRef$curren2","heightInTiles","pixelsToTiles","renderVisibleTiles","RoomTile","showMessagePreview","isAlphabetical","Alphabetic","isUnreadFirst","otherSections","onCloseMenu","onUnreadFirstChanged","onMessagePreviewChanged","onTagSortChanged","Recent","onOpenMenuClick","renderHeader","onBadgeClick","addRoomButton","mx_RoomSublist_headerContainer","mx_RoomSublist_headerContainer_withAux","badgeContainer","onHeaderKeyDown","onHeaderClick","ChevronRightIcon","_this$props$extraTile2","mx_RoomSublist","mx_RoomSublist_hasMenuOpen","mx_RoomSublist_minimized","mx_RoomSublist_hidden","minTiles","minHeightPadding","minTilesPx","maxTilesPx","showMoreBtnClasses","mx_RoomSublist_showNButton","showNButton","nonPaddedHeight","amountFullyShown","tileHeight","numMissing","showMoreText","onShowAllClick","showLessText","onShowLessClick","handles","bottomLeft","bottomRight","topLeft","topRight","handleWrapperClasses","mx_RoomSublist_resizerHandles","mx_RoomSublist_resizerHandles_showNButton","Resizable","minHeight","onResizeStart","onResizeStop","handleWrapperClass","handleClasses","RoomTileCallSummary","useConnectionState","ConnectionState","Disconnected","Disconnecting","messagePreviewId","RoomTileSubtitle","messagePreview","isThreadReply","property","CachedRoomKey","NotificationVolume","generatePreview","_this$props$room","roomTileRef","clear_search","notificationsMenuPosition","showContextMenu","getCall","_prevProps$room","_this$props$room2","showMessageChanged","minimizedChanged","_prevProps$room2","_this$props$room3","MessagePreviewStore","getPreviewChangedEventName","onRoomPreviewChanged","onRoomNameUpdate","onActiveRoomUpdate","PROPERTY_UPDATED","onRoomPropertyUpdate","onCallChanged","removeRoomListener","_await$MessagePreview","getPreviewForRoom","renderNotificationsMenu","mx_RoomTile_notificationsButton_show","onNotificationsMenuOpenClick","onCloseNotificationsMenu","renderGeneralMenu","onGeneralMenuOpenClick","onCloseGeneralMenu","shouldRenderSubtitle","mx_RoomTile_sticky","mx_RoomTile_hasMenuOpen","titleClasses","mx_RoomTile_titleWithSubtitle","titleContainer","ariaDescribedBy","hasMentions","onTileClick","SendComposer","EditComposer","dynamicImportSendMessage","isHTML","dynamicImportConversionFunctions","richToPlain","plainToRich","DynamicImportSendWysiwygComposer","DynamicImportEditWysiwygComposer","AvatarSettingContextMenu","onUploadSelect","onRemoveSelect","menuOpen","Menu","showTitle","UploadIcon","getFileChanged","_e$target$files","fileInputRef","avatarURL","setAvatarURL","reader","FileReader","readAsDataURL","onFileChanged","uploadAvatar","_fileInputRef$current","setMenuOpen","newOpen","avatarElement","uploadAvatarBtn","uploadButtonClasses","mx_AvatarSetting_uploadButton_active","localRoom","getJoinedMemberCount","numChildRooms","addAllParents","getKnownParents","parentId","ManageRestrictedJoinRuleDialog","setNewSelected","spacesContainingRoom","otherJoinedSpaces","otherEntries","parents","spacePanelSpaces","filteredSpacesContainingRoom","filteredOtherJoinedSpaces","filteredOtherEntries","inviteOnlyWarning","totalResults","disabledOptions","hiddenOptions","recommendedOption","_content$allow","roomSupportsKnock","doesRoomVersionSupport","PreferredRoomVersions","KnockRooms","preferredKnockVersion","roomSupportsRestricted","RestrictedRooms","preferredRestrictionVersion","useLocalEcho","restrictedAllowRoomIds","RestrictedAllowType","RoomMembership","setIsPublicKnockRoom","editRestrictedRoomIds","_selected","roomIds","upgradeRequiredDialog","updateSpacesTotal","inviteUsersTotal","roomUpgraded","roomSynced","inviteUsersProgress","updateSpacesProgress","_progress$inviteUsers","upgradeRequiredPill","withRecommendLabel","shownSpaces","moreText","onRestrictedRoomIdsChange","newAllowRoomIds","onEditRestrictedClick","beforeJoinRule","_restrictedAllowRoomI","_restrictedAllowRoomI2","SettingsSubsectionText","SettingsHeader","hasRecommendedTag","mx_SettingsHeader_recommended","BigIcon","renderHeading","subHeading","mx_SettingsSection_newUi","stretchContent","formWrap","mx_SettingsSubsection_newUi","SettingsSubsectionHeading","mx_SettingsSubsection_contentStretch","mx_SettingsSubsection_noHeading","mx_SettingsSubsection_content_newUi","Separator","oldEventId","oldViaServers","additionalStateChanges","upgraded","replacement_room","upgradeRecommendation","unfederatableSection","roomUpgradeButton","oldRoomLink","needsUpgrade","copy","_room$name2","onOldRoomClicked","AutocompleteInput","renderSuggestion","renderSelection","maxSuggestions","additionalFilter","_editorContainerRef$c","setSuggestions","isFocused","onFocusChangeHandlerFunctions","useFocus","editorContainerRef","focusEditor","_editorRef$current","toggleSelection","newSelection","removeSelection","onClickInputArea","SelectionItem","hasModifiers","SuggestionItem","withContainer","AddPrivilegedUsers","defaultUserLevel","userProvider","selectedUsers","setSelectedUsers","hasLowerOrEqualLevelThanDefaultLevelFilter","hasLowerOrEqualLevelThanDefaultLevel","userIds","getUserIdsFromCompletions","flexGrow","PowerLevelSelector","userLevels","canChangeLevels","currentUserLevel","currentPowerLevel","setCurrentPowerLevel","powerLevelChanged","collator","Collator","userA","userB","powerLevelDiff","compare","toLocaleLowerCase","sortUser","canChange","userLevelsTmp","usersLevels","uL","plEventsToShow","hideForRoom","hideForSpace","parseIntWithDefault","BannedUser","unbanButton","canUnban","onUnbanClick","by","EVENTS_LEVEL_PREFIX","onThisRoomMembership","_plEvent$getContent","plEvent","plContent","_plEvent$getContent2","isReady","populateDefaultPlEvents","eventsSection","stateLevel","eventsLevel","desiredEvent","_room$getMember$power","plEventsToLabels","powerLevelDescriptors","eventsLevels","banLevel","mutedUsersSection","privilegedUsersSection","onUserPowerLevelChanged","banned","bannedUsersSection","canBanUsers","_member$events$member2","banEvent","bannedById","bannedBy","powerSelectors","descriptor","onPowerLevelsChanged","eventPowerSelectors","_plEventsToShow$event","_plEventsToShow$event2","translationKeyForEvent","currentMediaPreview","changeSetting","avatarOnChange","Off","mediaPreviewOnChangeOff","media_previews","mediaPreviewOnChangePrivate","mediaPreviewOnChangeOn","Root","RadioInput","SpaceAvatar","avatarDisabled","setAvatar","avatarUploadRef","setAvatarDataUrl","avatarSection","_avatarUploadRef$curr","_avatarUploadRef$curr2","TakePhotoSolidIcon","_avatarUploadRef$curr3","SpaceBasicSettings","nameDisabled","setName","topicDisabled","setTopic","Target","SpecificChildrenPicker","filteredRooms","All","Specific","createSpace","otherOpts","power_level_content_override","historyVisibility","andView","inlineErrors","spaceNameValidator","nameToLocalpart","SpaceCreateForm","nameFieldRef","aliasFieldRef","setAlias","showAliasField","_cli$getDomain","newName","_aliasFieldRef$curren","SpaceCreateMenu","settingAllowPublicSpaces","AllowCreatingPublicSpaces","setVisibility","spaceNameField","spaceAliasField","supportsSpaceFiltering","setSupportsSpaceFiltering","isVersionSupported","onSpaceCreateClick","onSearchClick","OpenSpotlight","initialFilter","PublicSpaces","SpacePublicShare","copiedText","setCopiedText","detail","PrimaryIcon","overrideWidth","detailContent","isError","mx_Caption_error","cancelling","sasDisplay","sasCaption","SasEmoji","decimal","numberBlocks","otherDevice","deviceName","onMatchClick","onDontMatchClick","BUTTONS","BUTTON_LETTERS","DialPadButtonKind","DialPadButton","Digit","onButtonPress","Dial","digitSubtext","buttonNodes","onDialPress","CurrentRightPanelPhaseContextProvider","sdkContext","getCurrentPhase","rightPanelStore","currentCardForRoom","getIsOpen","isOpenForRoom","setCurrentPhase","useCurrentPhase","ComposedComponent","MainSplitContentType","roomLoading","peekLoading","shouldPeek","membersLoaded","numUnreadMessages","canPeek","showApps","isPeeking","showRightPanel","showTopUnreadMessagesBar","statusBarVisible","resizing","alwaysShowTimestamps","showTwelveHourTimestamps","userTimezone","readMarkerInViewThresholdMs","readMarkerOutOfViewThresholdMs","showReadReceipts","showRedactions","showJoinLeaves","showAvatarChanges","showDisplaynameChanges","matrixClientIsReady","mainSplitContentType","canAskToJoin","promptAskToJoin","viewRoomOpts","SORT_REGEX","MemberListStore","stores","loadMemberList","joined","sensitivity","ignorePunctuation","loadMembers","membersByMembership","filterMembers","sortMembers","loadedRooms","isLazyLoadingEnabled","loadMembersInRoom","isLazyMemberStorageEnabled","loadMembersIfNeeded","markOutOfBandMembersStarted","memberEvents","chunk","getEventMapper","setOutOfBandMembers","allMembers","_this$stores$client","hasLazyLoadMembersEnabled","_enablePresenceByHsUr","matchesName","matchesId","memberA","memberB","convertPresence","presenceIndex","idxA","idxB","getLastActiveTs","canonicalisedName","sortNames","INITIAL_STATE","joinError","subscribingRoomId","initialEventId","initialEventPixelOffset","isInitialEventHighlighted","initialEventScrollIntoView","roomAlias","roomLoadError","replyingToEvent","wasContextSwitch","viewingCall","RoomViewStore","lockedToRoomId","resetDispatcher","emitForRoom","stateChanged","lastRoomId","_this$dis","ActiveRoomChanged","newRoomId","onDispatch","viewRoom","ViewThread","viewThread","ViewRoomError","viewRoomError","JoinRoom","joinRoom","JoinRoomError","joinRoomError","JoinRoomReady","awaitRoomDownSync","numMembers","roomSize","posthogAnalytics","isDM","_payload$event","_this$dis2","isRoomDisplayedInModule","PromptAskToJoin","SubmitAskToJoin","submitAskToJoin","CancelAskToJoin","cancelAskToJoin","RoomLoaded","setViewRoomOpts","_payload$room_alias","_payload$event_id","_payload$highlighted","_payload$scroll_into_","_payload$via_servers","_payload$context_swit","_payload$replyingToEv","_this$state$replyingT","spaceStore","_this$stores$spaceSto","viaKeyboard","getActiveCall","ElementCall","presented","connectionState","prevRoomCall","_payload$view_call","_this$dis3","context_switch","slidingSyncManager","auto_join","_this$dis4","joinPayload","_this$dis6","cachedResult","_payload$view_call2","_this$dis5","thread_id","_payload$opts","joinOpts","acceptSharedHistory","_this$dis7","retry","_this$dis8","_this$dis9","getInvitingUserId","inviteEvent","showJoinRoomError","invitingUserId","_this$dis0","dispatchToken","getInitialEventId","getRoomAlias","isRoomLoading","getRoomLoadError","isJoining","getJoinError","getQuotingEvent","getWasContextSwitch","isViewingCall","knockRoom","leave","getViewRoomOpts","invoke","RoomViewLifecycle","currentSpace","cb","ModuleApi","extras","visibleRoomBySpaceKey","TypingStore","typingStates","_currentTyping","_this$context$client","currentTyping","serverTimer","userTimer","sendTyping","LruCache","capacity","_this$getItem","safeSet","removeItemFromList","head","tail","setHeadTail","cacheSize","UserProfilesStore","profiles","knownProfiles","Membership","onRoomMembershipEvent","getProfile","cachedProfile","fetchProfile","profileLookupErrors","fetchProfileFromApi","isUserIdKnown","flush","_await$this$client$ge","getProfileInfo","OidcClientStore","readyPromise","authenticatedIssuer","getStoredOidcTokenIssuer","getOidcClient","authMetadata","getAuthMetadata","setAccountManagementEndpoint","account_management_uri","issuer","account_management_actions_supported","isUserAuthenticatedWithOidc","endpoint","actionsSupported","idToken","getStoredOidcIdToken","_accountManagementEndpoint","_accountManagementActionsSupported","accountManagementEndpoint","accountManagementActionsSupported","revokeTokens","tryRevokeToken","oidcClient","tokenType","revokeToken","initialisingOidcClientPromise","initOidcClient","_authMetadata$signing","clientId","getStoredOidcClientId","discoverAndValidateOIDCIssuerWellKnown","OidcClient","authority","signingKeys","redirect_uri","client_id","ResizeNotifier","_isResizing","startResizing","stopResizing","noisyMiddlePanel","updateMiddlePanel","throttledMiddlePanel","notifyLeftHandleResized","notifyRightHandleResized","notifyTimelineHeightChanged","notifyWindowResized","MultiRoomViewStore","sdkContextClass","getRoomViewStoreForRoom","removeRoomViewStore","dispose","constructEagerStores","_RoomViewStore","legacyCallHandler","_LegacyCallHandler","_RightPanelStore","roomNotificationStateStore","_RoomNotificationStateStore","widgetLayoutStore","_WidgetLayoutStore","widgetPermissionStore","_WidgetPermissionStore","WidgetPermissionStore","widgetStore","_WidgetStore","_PosthogAnalytics","memberListStore","_MemberListStore","_SpaceStore","_TypingStore","mxTypingStore","_UserProfilesStore","oidcClientStore","_OidcClientStore","_ResizeNotifier","multiRoomViewStore","_MultiRoomViewStore","onLoggedOut","_SdkContextClass","EfficientContext","_this$state","changedKeys","objectKeyChanges","ScopedRoomContext","ScopedRoomContextProvider","_context$state","updatedKeys","updatedKey","DEFAULT_EVENT_POWER_LEVELS","_await$client$getCapa","_await$client$getCapa2","defaultPreset","dmUserId","TrustedPrivateChat","isUrl","invite_3pid","id_server","medium","is_direct","RoomCreateTypeField","JitsiCall","MEMBER_EVENT_TYPE","initial_state","defaultRoomVersion","getCapabilities","room_version","makeSpaceParentEvent","storedRoom","onRoom","emittedRoom","waitTimeMs","hasEncryptionStateEvent","timeoutPromise","timeoutResolve","stateUpdatePromise","stateUpdateResolve","resolution","race","waitForRoomEncryption","enableStateEventEncryption","suggested","justCreatedOpts","canEncryptToAllUsers","_client$getCrypto","usersDeviceMap","existingDMRoom","waitForMember","chatPreset","doesServerForceEncryptionForPreset","doesWellKnownForceDisableEncryption","getForceChatExportParameters","ComponentVisibilityCustomisations","MediaImplementation","prepared","thumbnailMxc","_this$prepared$thumbn","mxcUrlToHttp","dim","downloadSource","parseErrorResponse","thumbnail_url","thumbnail_file","prepEventContentAsMedia","RoomListCustomisations","WidgetPermissionCustomisations","WidgetVariableCustomisations","_ComponentVisibilityC","_ComponentVisibilityC2","invariant","cond","isDispatching","startDispatching","callbacks","isPending","invokeCallback","stopDispatching","lastId","isHandled","waitFor","ids","pendingPayload","sync","_dispatch","mxDispatcher","readyFn","firstPart","UserPill","RoomPill","run","_await$result$promise","errText","LIST_TYPES","currentLength","isListChild","_n$parentNode","parseAtRoomMentions","pc","ATROOM","textPart","atRoomPill","prefixLines","parseChildren","mkListItem","parseNode","_mkListItem","nodeValue","checkIgnored","parseHeader","getPrimaryPermalinkEntity","userPill","roomPill","parseLink","parseImage","_n$firstChild","fence","parseCodeBlock","li","_start","_delims$inline$left","_delims$inline","_delims$display$left","_delims$display","_delims$inline$right","_delims$inline2","_delims$display$right","_delims$display2","delims","latex_maths_delims","delimLeft","delimRight","tex","lines","isRainbow","parseHtmlMessage","textToHtmlRainbow","getSelectionOffsetAndText","selectionNode","characterOffset","childNodeCount","_selectionNode","_selectionNode$textCo","MAX_SAFE_INTEGER","tryReduceSelectionToTextNode","offsetToNode","foundNode","enterNodeCallback","nodeText","isCaretNode","CARET_NODE_CHAR","getTextNodeValue","leaveNodeCallback","_node$nextSibling","rootNode","walkDOMDepthFirst","getTextAndOffsetToNode","offsetWithinNode","DocumentOffset","zwsIdx","focusPosition","anchorPosition","firstDiff","compareLen","diffAtCaret","caretPositionBeforeInput","oldStr","newStr","len","startInCommon","commonStartLen","diffStringsAtEnd","updateCallback","replaceParts","_this$updateCallback","pos","_range$start","_range$end","autoCompletePartIdx","replaceRange","DocumentPosition","autoCompletePartCount","lastPartIndex","_autoComplete","_partCreator","transformCallback","clone","clonedParts","insertPart","activePartIdx","removePart","replacePart","previousValue","firstDiffIdx","diffDeletion","_this$updateCallback2","insertIndex","splitAt","newTextLength","_this$updateCallback3","removedOffsetDecrease","removeText","addText","mergeAdjacentParts","caretOffset","newPosition","canOpenAutoComplete","acPromise","setActivePart","transformAddedLen","getTransformAddedLen","_this$transformCallba","ac","createAutoComplete","onAutoComplete","onPartUpdate","_prevPart$merge","_prevPart","isMerged","replaceWith","createDefaultPart","secondPart","addLen","validateAndInsert","splitPart","newPart","createPartForInput","appendUntilRejected","totalOffset","atPartEnd","currentOffset","partLen","positionA","positionB","startPosition","endPosition","newStartPartIndex","insertIdx","_this$updateCallback4","AutocompleteWrapperModel","getAutocompleterComponent","updateQuery","_this$getAutocomplete","_this$getAutocomplete2","_this$getAutocomplete3","onConfirmCompletion","acComponent","_this$getAutocomplete4","_this$getAutocomplete5","partForCompletion","REGIONAL_EMOJI_SEPARATOR","fromCodePoint","BasePart","_text","acceptsInsertion","chr","acceptsRemoval","splitText","PlainPart","strWithRemoval","charAt","beforeInsert","afterInsert","remaining","PlainBasePart","toDOMNode","updateDOMNode","canUpdateDOMNode","PillPart","textNode","setAvatarVars","initialLetter","avatarTextColor","avatarBackground","avatarLetter","NewlinePart","EmojiPart","RoomPillPart","_this$room","_Avatar$getInitialLet","_this$room2","_this$room$roomId","_this$room3","_this$room$roomId2","_this$room4","_this$room5","AtRoomPillPart","AtRoomPill","UserPillPart","defaultAvatarUrl","_Avatar$getInitialLet2","PillCandidatePart","autoCompleteCreator","_this$autoCompleteCre","_this$autoCompleteCre2","PartCreator","_this$client$getRoom","isRegionalIndicator","_c$codePointAt","codePoint","codePointAt","insertTrailingCharacter","pill","CommandPart","otherPos","iteratePartsBetween","startPos","endPos","forwardsWhile","predicate","backwardsWhile","lastPartIdx","isAtStart","whitespacePredicate","bIsLarger","_end","_lastStart","_initializedEmpty","setWasEmpty","setLastStartingPosition","newLength","oldLength","serializedPart","isFirst","nodeToInsert","createCaretNode","updateCaretNode","removeNextSiblings","removeNode","linesArr","lineContainer","removeChild","_currentNode","caretNode","reconcileLine","foundBR","partNode","reconcileEmptyLine","removeChildren","md","makeGenericPermalink","mdSerialize","orig","patternTypes","patternDefaults","latex","patternName","patternType","_SdkConfig$get","p1","p2","p2e","encode","parserOrig","_model$parts$","hasCommand","hasArgument","caseSensitive","stripPrefix","unescapeMessage","CHAT_EFFECTS","fallbackMessage","maxCount","speed","frameInterval","alpha","gradient","gravity","maxDrift","containsEmoji","EMAIL_ADDRESS_REGEX","looksValid","SETTING_NAME","getRecentEmoji","newEntry","mx_reaction_count","newFormat","count1","date1","count2","date2","migrate","orderBy","CallDuration","SessionDuration","_session$getOldestMem","setNow","createdTs","getOldestMembership","ActiveCallEvent","participatingMembers","buttonKind","buttonDisabledTooltip","onButtonClick","facePileMembers","facePileOverflow","FacePile","ActiveLoadedCallEvent","useParticipatingMembers","latestEvent","RoomPredecessorTile","_predecessor$viaServe","onLinkClicked","prevRoom","guessedLink","guessServerNameFromRoomId","MatrixToPermalinkConstructor","guessLinkForRoomId","ChatSolidIcon","predecessorPermalink","createLinkWithRoom","matrixToPermalinkConstructor","createLinkWithoutRoom","RoomAvatarEvent","onAvatarClick","MKeyVerificationRequest","receiver","userLabelForEventRoom","getNameForEventRoom","MJitsiWidgetEvent","_this$props$mxEvent$s","widgetId","joinCopy","isInContainer","HiddenBody","ViewSourceEvent","mx_ViewSourceEvent_expanded","TextualEventViewModel","setTextFromEvent","SentinelUpdated","MessageEventFactory","CallEventFactory","TextualEventFactory","TextualEventView","VerificationReqFactory","HiddenEventFactory","JitsiEventFactory","JSONEventFactory","EVENT_TILE_TYPES","LegacyCallEventFactory","STATE_EVENT_TILE_TYPES","RoomCreateEventFactory","SINGULAR_STATE_EVENTS","pickFactory","asHiddenEv","_EVENT_TILE_TYPES$get","noEventFactoryFactory","getMessageModerationState","MessageModerationState","HIDDEN_TO_CURRENT_USER","dynamicPredecessorsEnabled","_STATE_EVENT_TILE_TYP","live","isRelation","renderTile","renderType","factory","customComponents","renderMessage","origProps","_origProps$showUrlPre","_origProps$showUrlPre2","renderReplyTile","_origProps$showUrlPre3","messageTypes","isMessageEvent","getHintsForMessage","_matrixClient$getRoom","intent","GroupCallIntent","getShareableLocationEventForBeacon","defaults","textColor","fontFamily","fontWeight","isUp","isLeft","IconRenderer","baseImage","opt","circle","more","clearRect","drawImage","beginPath","fontSize","textAlign","moveTo","lineTo","quadraticCurveTo","arc","PI","closePath","fillText","BadgeOverlayRenderer","contents","toBlob","DEFAULT_FAVICON_SIZE","ff","InstallTrigger","opera","getIcons","lastIcon","ready","_this$readyCb","readyCb","setIcon","setIconSrc","_old$parentNode","old","getLinks","elms","propMember","useOnlyCurrentProfiles","threadContexts","_context$room","currentMember","deps","discard","forRoomId","useCallForWidget","useParticipants","savedHandler","downloader","blobRef","setLoading","setCanDownload","hints","allowDownloadingMedia","downloadBlob","_mediaEventHelper$fil","emitter","eventListener","useEventEmitterAsyncState","running","rerunArgs","NoChange","setFocused","cryptoApi","isEncryptionEnabled","encryptionStateEvent","_roomState$getStateEv","currentFactory","setterFn","errorFn","PRIVATE_JOIN_RULES","mediaPreviewSetting","eventVisibility","roomIsPrivate","explicitEventVisiblity","echoChamber","mapper","savedMapper","excludeDefault","explicit","toggleValue","intervalMs","intervalID","_savedHandler$current2","useExpiringCounter","initialCount","setCount","setSymbol","setLevel","UnreadNotifications","unreadNotifications","evtThreadId","updateNotificationState","LocalEchoUpdated","ScalarAuthClient","apiUrl","scalarToken","termsInteractionCallback","configApiUrl","configUiUrl","isDefaultManager","writeTokenToStore","_this$scalarToken","readTokenFromStore","setTermsInteractionCallback","getScalarToken","tok","hasCredentials","getAccountName","parsedImRestUrl","tokenObject","exchangeForScalarToken","openidTokenObject","scalarRestUrl","headers","scalar_token","getScalarPageTitle","_body$page_title_cach","scalarPageLookupUrl","encodeURIComponent","page_title_cache_item","cached_title","disableWidgetAssets","widgetType","preferred","getScalarInterfaceUrlForRoom","starterLinkUrl","IntegrationManager","errored","connected","Kind","IntegrationManagerInstance","_parsed$host","trimmedApiUrl","integrationId","showDisabledDialog","policyInfo","IntegrationsImpossibleDialog","onAcknowledgeClick","IntegrationsDisabledDialog","manageIntegrations","KIND_PREFERENCE","Account","Homeserver","Config","discoveryResponse","hsManager","primaryManager","compileManagers","startWatching","stopWatching","onAccountData","ClientWellKnown","setupHomeserverManagers","setupConfiguredManager","setupAccountManagers","getIntegrationManagerWidgets","getOrderedManagers","ordered","_a$id","_b$id","mxIntegrationManagers","i18nFolder","substitutionVariablesAndCause","substitutionVariables","errorOptions","normalizeLanguageKey","getLanguagesFromBrowser","availableLanguages","getLangsJson","chosenLanguage","languageData","getLanguageRetry","registerTranslations","setLocale","fallbackLanguageData","testOnlyIgnoreCustomTranslationsCache","doRegisterTranslations","allTranslations","lookupUrl","custom_translations_url","cachedCustomTranslationsExpire","CustomTranslationOptions","lookupFn","cachedCustomTranslations","registerCustomTranslations","getAllLanguagesWithLabels","languageNames","DisplayNames","getAllLanguagesFromJson","langKey","of","labelInTargetLanguage","_navigator$language","languages","getCurrentLanguage","getLocale","langs","currentLang","normalisedLangs","currentLangIndex","closeLangIndex","enIndex","langPath","customTranslations","MapWithDefault","translationKey","translations","translation","getOrCreate","KEY_SEPARATOR","matrixOpaqueIdLinkifyParser","scanner","DOT","NUM","COLON","SYM","EQUALS","HYPHEN","UNDERSCORE","tokens","groups","additionalLocalpartTokens","additionalDomainpartTokens","matrixToken","linkifyjs","isLink","matrixTokenState","matrixTokenWithPort","matrixTokenWithPortState","tt","LOCALPART_STATE","ta","DOMAINPART_STATE_DOT","onUserClick","UserId","_parsePermalink$userI","_parsePermalink","RoomAlias","_parsePermalink$roomI","_parsePermalink2","formatHref","getHttpUriForMxc","_tryTransformEntityTo","tryTransformEntityToPermalink","ignoreTags","decodeURIComponent","registerPlugin","POUND","AT","linkifySupportedProtocols","optionalSlashProtocols","scheme","registerCustomProtocol","MatrixGlob","replaced","globToRegexp","extended","globstar","RECOMMENDATION_BAN","PolicyRecommendation","RECOMMENDATION_BAN_TYPES","recommendationToStable","unstable","ListRule","_glob","_entity","_action","_reason","_kind","isMatch","RULE_USER","PolicyRuleUser","RULE_ROOM","PolicyRuleRoom","RULE_SERVER","PolicyRuleServer","ruleTypeToStable","BanList","_roomId","updateList","serverRules","_rules","userRules","banEntity","unbanEntity","_roomIds","_lists","mjolnirWatchRef","onListsChanged","DoAfterSyncPrepared","deferred_action","getOrCreatePersonalList","personalRoomId","getPersonalList","subscribeToList","unsubscribeFromList","listRoomIds","waitForEvent","pred","customTimeout","wait","isConnected","_callType","CallTypeChanged","_widgetApi","_connectionState","prevValue","_participants","_presented","_room","setDisconnected","widgetUid","WidgetMessagingStoreEvent","StopMessaging","onStopMessaging","_ElementCall$get","_params","messagingStore","startTime","performance","_messaging","recheck","currentMessaging","onStart","WidgetMessagingEvent","Start","onStoreMessaging","StoreMessaging","setConnected","onMyMembership","beforeUnload","performDisconnection","Close","Destroy","updateParticipants","resendDevicesTimer","removeOurDevice","addOurDevice","STUCK_DEVICE_TIMEOUT_MS","TileLayout","SpotlightLayout","reply","onRoomState","onConnectionState","isElementVideoRoom","jitsiWidget","_app$data","isVideoChannel","participantsExpirationTimer","allExpireAt","expiresAt","expires_ts","getDeviceId","localMember","clean","myDevices","deviceMap","device_id","last_seen_ts","devicesSet","JoinCall","onJoin","onHangup","ActiveWidgetStore","ActiveWidgetStoreEvent","Dock","onDock","Undock","onUndock","ElementCallIntent","checkDestroy","appendRoomParams","append","JoinExisting","oldestCallMember","hasCallStarted","JoinExistingDMVoice","JoinExistingDM","StartCallDMVoice","StartCallDM","StartCall","appendAnalyticsParams","accountAnalyticsData","pseudonymousAnalyticsOptIn","project_api_key","sentryConfig","_sentryConfig$environ","dsn","environment","generateWidgetUrl","elementCallUrlOverride","URLSearchParams","perParticipantE2EE","fontScale","FontWatcher","getRootFontSize","getBrowserDefaultFontSize","theme","rageshakeSubmitUrl","replacedUrl","createOrGetCallWidget","ecWidget","CALL","_ecWidget$data","getWidgetData","addVirtualWidget","creatorUserId","waitForIframeLoad","getWidgetIntent","currentData","overwriteData","onCallEncryptionSettingsChange","_this$widget$data","isCallRoom","getConsensusCallIntent","MatrixRTCSessionEvent","MembershipsChanged","onMembershipChanged","MatrixRTCSessionManagerEvents","SessionEnded","hasEcWidget","availableOrCreatedWidget","widgetGenerationParameters","DeviceMute","onDeviceMute","destroyPersistentWidget","removeVirtualWidget","settingsStoreCallEncryptionWatcher","terminationTimer","_participants$get","LOCAL_ROOM_ID_PREFIX","LocalRoomState","NEW","getDefaultRoomName","isNew","isCreated","CREATED","ERROR","stateEvents","ConfigApi","CustomComponentsApi","getModuleMatrixEvent","registerMessageRenderer","eventTypeOrFilter","registeredMessageRenderers","selectRenderer","originalComponent","_originalComponent","moduleEv","roomPreviewBarRenderer","_roomPreviewBarRenderer","registerRoomPreviewBar","WatchableProfile","Watchable","OwnProfileStore","onProfileChange","_OwnProfileStore$inst","_OwnProfileStore$inst2","_OwnProfileStore$inst3","_OwnProfileStore$inst4","_OwnProfileStore$inst5","NavigationApi","toMatrixToLink","navigateToPermalink","_parts$viaServers","openRoom","autoJoin","registerLocationRenderer","path","locationRenderers","OuterDialog","Dialog","openDialog","initialOptions","overwriteAccountAuth","accountInfo","OnLoggedIn","OverwriteLogin","ElementWebBuiltinsApi","setComponents","components","_roomView","roomView","_roomAvatar","roomAvatar","_notificationDecoration","notificationDecoration","getRoomViewComponent","getRoomAvatarComponent","getNotificationDecorationComponent","renderRoomView","renderRoomAvatar","renderNotificationDecoration","sdkRoom","WatchableName","getLastActiveTimestamp","onFirstWatch","onNameUpdate","onLastWatch","AccountDataApi","AccountDataWatchable","deleteAccountData","_cli$getAccountData","ClientApi","ModuleRoom","RoomListStoreApi","moduleLoadPromise","rls","LISTS_LOADED_EVENT","RoomsWatchable","roomListStore","waitForReady","isLoadingRooms","getSortedRooms","onRlsUpdate","StoresApi","roomListStoreApi","legacyCustomisationsFactory","baseCustomisations","used","customisations","ChatExportCustomisations","LifecycleCustomisations","MediaCustomisations","I18nApi","ElementWebExtrasApi","_registerLegacyModule","LegacyModule","registerModule","api","ExtrasApiEvent","setSpacePanelItem","spacekey","spacePanelItems","SpacePanelItemsChanged","getVisibleRoomBySpaceKey","spaceKey","useModuleSpacePanelItems","getItems","setItems","ModuleUiDialog","_this$props$initialOp","_this$props$initialOp2","setOptions","dialogProps","moduleApi","contentProps","additionalContentProps","contentFactory","ProxiedModuleApi","_this$overrideLoginRe","overrideLoginResolve","cachedTranslations","translateString","variables","initialTitleOrOptions","didOkOrSubmit","registerSimpleAccount","username","hsUrl","Matrix","req","initial_device_display_name","getDefaultDeviceDisplayName","inhibit_login","registerRequest","profileClient","setDisplayName","awaitNewLogin","navigatePermalink","andJoin","_parts$viaServers2","getConfigValue","namespace","maybeObj","getAppAvatarUrl","isAppInContainer","moveAppToContainer","AppModule","TextInputField","renderFactory","ModuleSpinner","ExtensionsManager","cryptoSetupExtension","DefaultCryptoSetupExtensions","experimentalExtension","DefaultExperimentalExtensions","experimental","addExtensions","_runtimeModule$extens","_runtimeModule$extens3","runtimeModule","hasDefaultCryptoSetupExtension","moduleName","_runtimeModule$extens2","hasDefaultExperimentalExtension","_runtimeModule$extens4","extensionsManager","modules","merged","strings","appModule","lifecycleEvent","_ModuleRunner","consoleFunctionsToLevels","ConsoleLogger","monkeyPatch","consoleObj","fnName","originalFn","originalFunctions","bypassRageshake","_this$originalFunctio","_this$originalFunctio2","getCircularReplacer","seen","WeakSet","logs","keepLogs","logsToFlush","IndexedDBLogStore","indexedDB","onsuccess","db","_req$error","onupgradeneeded","logObjStore","createObjectStore","keyPath","createIndex","unique","generateLogEntry","generateLastModifiedTime","flushPromise","flushAgainPromise","txn","transaction","objStore","objectStore","oncomplete","_txn$error","consume","allLogIds","fetchLogIds","removeLogIds","instanceId","truncated","fetchLogs","deleteLogs","keyRange","resultMapper","openCursor","_query$error3","selectQuery","sizeSoFar","IDBKeyRange","only","_query$error","_cursor$value$ts","newLines","logBatchTimestamp","shouldTruncateAfterLogBatch","openKeyCursor","primaryKey","_query$error2","setUpPersistence","mx_rage_initPromise","mx_rage_logger","tryInitStorage","mx_rage_initStoragePromise","mx_rage_store","cleanup","getLogsForReport","collectBugReport","gzipLogs","FormData","_window$navigator$use","_window$navigator","installedPWA","matchesMediaQuery","touchInput","customApp","customFields","collectBaseInformation","_await$cryptoApi$getC","ownDeviceKeys","curve25519","getCrossSigningKeyId","collectCryptoInfo","sessionBackupKeyFromCache","collectRecoveryInfo","http","Method","Get","getUrl","collectSynapseSpecific","collectClientInfo","collectLabels","enabledLabs","getFeatureSettingNames","exportForRageshake","collectSettings","storage","persisted","hasStorageAccess","estimate","quota","usage","usageDetails","collectStorageStatInfo","missingFeatures","collectMissingFeatures","pako","rageshake","TextEncoder","gzip","collectLogs","matchMedia","bugReportEndpoint","submitReport","loadBugReport","Tar","metadata","tape","TextDecoder","readAsArrayBuffer","dl","out","fromCharCode","uint8ToString","extraData","_PlatformPeg$get$getH","_PlatformPeg$get3","_MatrixClientPeg$get$","bugReportEndpointUrl","_AbortSignal$timeout","_AbortSignal","signal","AbortSignal","policy_url","report_url","getStorageContext","getUserContext","enabled_labs","getEnabledLabs","low_bandwidth","getCryptoContext","crypto_version","device_keys","cross_signing_ready","cross_signing_key","cross_signing_privkey_in_secret_storage","cross_signing_master_privkey_cached","cross_signing_user_signing_privkey_cached","secret_storage_ready","secret_storage_key_in_account","session_backup_key_in_secret_storage","session_backup_key_cached","session_backup_key_well_formed","getDeviceContext","_client$deviceId","mx_local_settings","getContexts","captureContext","contexts","user_text","issue_url","Sentry","setSentryUser","sentry","initSentry","integrations","onunhandledrejection","release","process","defaultIntegrations","tracesSampleRate","mxSendSentryReport","ThemeController","SettingController","getValueOverride","calculatedValue","calculatedAtLevel","enumerateThemes","DEFAULT_THEME","FontSizeController","CONFIG","MigrateBaseFontSize","UpdateFontSizeDelta","SystemFontController","UpdateSystemFont","useBundledEmojiFont","useSystemFont","UIFeatureController","uiFeatureName","ReducedMotionController","prefersReducedMotion","IncompatibleController","incompatibleValue","incompatibleSetting","SlidingSyncController","ServerSupportUnstableFeatureController","watchers","unstableFeatureGroups","stableVersion","newDisabledValue","firstSupportedLevel","settingValue","notifyUpdate","initMatrixClient","featureGroup","feature","isFeatureSupported","AnalyticsController","interactionName","_level","_newValue","FallbackIceServerController","wellKnown","_wellKnown$ioElement","newClient","oldClient","checkWellKnown","getClientWellKnown","setFallbackICEServerAllowed","MediaPreviewConfigController","getValidSettingData","mediaPreviews","inviteAvatars","validMediaPreviews","_source$getAccountDat","_source$getAccountDat2","_calculatedConfig$inv2","_calculatedConfig$med2","calculatedConfig","_calculatedConfig$inv","_calculatedConfig$med","globalConfig","INVITE_RULES_ACCOUNT_DATA_TYPE","MSC4380_INVITE_RULES_ACCOUNT_DATA_TYPE","InviteRulesConfigController","_expectedConfig$block","allBlocked","blocked_users","featureSupported","_this$client$getAccou","_this$client$getAccou2","_existingContent$bloc","_newContent$blocked_u","existingContent","inRoomId","roomWatchers","LEVELS_ROOM_SETTINGS","LEVELS_ROOM_OR_ACCOUNT","LEVELS_ROOM_SETTINGS_WITH_ROOM","LEVELS_ACCOUNT_SETTINGS","LEVELS_DEVICE_ONLY_SETTINGS","LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG","LEVELS_DEVICE_ONLY_SETTINGS_WITH_CONFIG_PRIORITISED","LEVELS_UI_FEATURE","LabGroup","Features","labGroupNames","Messaging","Profile","Spaces","Widgets","Threads","VoiceAndVideo","Moderation","Analytics","Themes","Encryption","Experimental","Developer","Ui","isFeature","labsGroup","supportedLevels","ReloadOnChangeController","betaInfo","NotificationSettings2","supportedLevelsAreOrdered","shouldExportToRageshake","default_action","newDefault","DeviceIsolationModeController","shouldWarn","DEFAULT_DELTA","invertedSettingName","UNSTABLE_MSC4133_EXTENDED_PROFILES","STABLE_MSC4133_EXTENDED_PROFILES","AdvancedEncryption","NotificationsEnabledController","NotificationBodyEnabledController","deny","SortingAlgorithm","Recency","ImageSize","ReleaseAnnouncement","LocationSharing","Feedback","Registration","PasswordReset","Deactivate","ThirdPartyID","PLATFORM","AbstractLocalStorageSettingsHandler","SettingsHandler","itemCache","objectCache","storageListenerBound","onStorageEvent","getBoolean","setBoolean","setObject","_AbstractLocalStorageSettingsHandler","DefaultSettingsHandler","invertedDefaults","ALLOWED_WIDGETS_EVENT_TYPE","DEFAULT_SETTINGS_EVENT_TYPE","RoomAccountSettingsHandler","prevEvent","_prevEvent$getContent","changedSettings","getSettings","BREADCRUMBS_LEGACY_EVENT_TYPE","BREADCRUMBS_EVENT_TYPE","BREADCRUMBS_EVENT_TYPES","RECENT_EMOJI_EVENT_TYPE","INTEG_PROVISIONING_EVENT_TYPE","AccountSettingsHandler","notifyBreadcrumbsUpdate","preferredValue","legacyEventType","_content","newType","RoomSettingsHandler","ConfigSettingsHandler","featureNames","isNullOrUndefined","settingsConfig","LocalEchoWrapper","cacheRoomId","bySetting","_this$handler$watcher","handlerPromise","_this$handler$watcher2","PlatformSettingsHandler","initialised","_setting$supportedLev","_PlatformPeg$get$supp2","defaultSettings","invertedDefaultSettings","LEVEL_HANDLERS","readFeature","writeFeature","read","getKey","DEFAULT","getLevelOrder","callbackFn","_setting$invertedSett","finalSettingName","watcherId","watcherCount","localizedCallback","_SettingsStore$getVal","doesSettingSupportLevel","watcherReference","monitors","registerWatcher","_SETTINGS$settingName","_SETTINGS$settingName2","_betaInfo$requiresRef","getLabGroup","_SETTINGS$settingName3","levelOrder","minIndex","getHandlers","getFinalValue","getDefaultValue","resultingValue","actualValue","_setting$controller","getHandler","_setting$controller2","levelOrders","configIndex","levelIndex","configVal","migrateURLPreviewsE2EE","isFreshLogin","MIGRATION_DONE_FLAG","isInitialSyncComplete","roomAccounthandler","migrateShowImagesToSettings","migrateMediaControlsToSetting","showImages","runMigrations","debugSetting","realSettingName","doChecks","handlerName","settingMap","mxSettingsStore","OnlySignedDevicesIsolationMode","AllDevicesIsolationMode","_matrixClient","_instance$initMatrixC","masterRule","getNotifier","SIZE_LARGE","SIZE_NORMAL_LANDSCAPE","SIZE_NORMAL_PORTRAIT","suggestedSize","contentSize","portrait","maxSize","Large","constrainedSize","migrateBaseFontSize","setRootFontSize","setSystemFont","updateFont","DEFAULT_SIZE","toPx","fontString","BUNDLED_EMOJI_FONT","FONT_FAMILY_CUSTOM_PROPERTY","EMOJI_FONT_FAMILY_CUSTOM_PROPERTY","migrateBaseFontV1toFontSizeDelta","migrateBaseFontV2toFontSizeDelta","legacyBaseFontSize","baseFontSizeV2","computeBaseFontSizeV1toV2","computeFontSizeDeltaFromV2BaseFontSize","legacyBaseFontV2Size","ThemeWatcherEvent","RecheckTheme","forceTheme","preferDark","preferLight","preferHighContrast","currentTheme","themeWatchRef","systemThemeWatchRef","oldTheme","themeBasedOnSystem","themeExplicit","newTheme","hcTheme","findHighContrastTheme","isSystemThemeSupported","eventDiff","isMemberEvent","isMembershipChanged","isJoin","isPart","isJoinToJoin","isDisplaynameChange","isAvatarChange","memberEventDiff","SlashCommandHelpDialog","colSpan","successSync","canAffectPowerlevels","singleMxcUpload","fileSelector","onchange","_target$files","shouldContinue","isCurrentLocalRoom","admin","_opts$runFn","runFn","_isEnabled","getCommandWithArgs","_this$renderingTypes","getUsage","_this$_isEnabled","_this$_isEnabled2","updatePowerLevelHelper","updatePowerLevel","deop","isPermalink","parsedUrl","permalinkParts","_openRoom","goto","_openRoom2","_threadId","parsedArgs","additionalCreators","parseUpgradeRoomArgs","_room$getLiveTimeline","runUpgradeRoomCommand","_cli","upgraderoom","inputDate","setAvatarUrl","splitAtFirstSpace","prom","useDefault","targetRoomId","_rooms$find","leaveRoomBehaviour","AddIntegrations","widgetUrl","_embed$childNodes","embed","canUserModifyWidgets","nowMs","CUSTOM","jitsiData","parsePreferredConferenceUrl","getLocalJitsiWrapperUrl","setRoomWidget","forceDiscardSession","_cli$getRoom2","isPhoneNumber","sendTextMessage","effect","trimmedInput","trimStart","withoutSlash","trimmedArgs","onRoomStateEvents","getWidgetPersistence","setWidgetPersistence","stopMessagingByUid","calcWidgetUid","isPersisted","persistentWidgetId","persistentRoomId","Persistence","getPersistentWidgetId","getPersistentRoomId","dockWidget","_this$dockedWidgetsBy","refs","dockedWidgetsByUid","undockWidget","isDocked","_this$dockedWidgetsBy2","mxActiveWidgetStore","AsyncStore","initialState","AwaitLock","storeState","updateState","lock","acquireAsync","freeze","quiet","AsyncStoreWithClient","asyncStore","readyStore","ReadyWatchingStore","_this$matrixClient","onReady","onNotReady","BreadcrumbsStore","settingValueRaw","meetsRoomRequirement","waitingRoom","waitingRooms","addedTs","appendRoom","updateRooms","_this$matrixClient2","updated","getRoomUpgradeHistory","existingIdx","_BreadcrumbsStore","updateRoom","setMaxListeners","fetchTransports","_this$matrixClient$ge","configuredMatrixRTCTransports","_unstable_getRTCTransports","waitForClientWellKnown","foci","TransportsUpdated","SessionStarted","onRTCSessionStart","onWidgets","uncleanlyDisconnectedRoomIds","_this$getCall","uncleanlyDisconnectedRoomId","listenerMap","callListeners","_connectedCalls","inUpdateRoom","onDestroy","_this$calls$get","getConfiguredRTCTransports","NonUrgentToastStore","toasts","addToast","removeToast","OwnBeaconStoreEvent","CREATED_BEACONS_KEY","getLocallyCreatedBeaconEventIds","_window$localStorage$","OwnBeaconStore","getLiveBeaconIds","beaconHasLocationPublishError","beaconId","counts","beaconLocationPublishErrorCounts","incrementBeaconLocationPublishErrorCount","publishCurrentLocationToBeacons","liveBeaconIds","_this$beaconsByRoomId","beaconsByRoomId","beacons","_beacon$beaconInfo","beaconIdentifier","updateBeaconEvent","removeLocallyCreateBeaconEventId","beaconInfoId","addBeacon","checkLiveness","monitorLiveness","stopBeacon","_this$beaconsByRoomId2","removeBeacon","clearBeacons","initialiseBeaconState","locallyCreatedBeaconEventIds","prevLiveBeaconIds","sortBeaconsByLatestCreation","arrayDiff","isMonitoringLiveLocation","togglePollingLocation","beaconInfoContent","existingLiveBeaconIdsForRoom","unstable_createLiveBeacon","storeLocallyCreateBeaconEventId","startPollingLocation","stopPollingLocation","clearPositionWatch","watchPosition","onWatchedPosition","onGeolocationError","locationInterval","lastPublishedPositionTimestamp","MonitoringLivePosition","timedGeoPosition","mapGeolocationPositionToTimedGeo","debouncedPublishLocationToBeacons","publishLocationToBeacons","GeolocationError","Unavailable","PermissionDenied","getCurrentPosition","assetType","updateContent","unstable_setLiveBeacon","beaconUpdateErrors","BeaconUpdateError","healthyLiveBeaconIds","sendLocationToBeacon","hadError","_this$beaconLocationP","LocationPublishError","onBeaconLiveness","onNewBeacon","onUpdateBeacon","onDestroyBeacon","onRoomStateMembers","dynamicWatcherRef","reinitialiseBeaconState","_OwnBeaconStore","KEY_DISPLAY_NAME","KEY_AVATAR_URL","profileInfo","fetchedAt","onProfileUpdate","isProfileInfoFetched","avatarMxc","getHttpAvatarUrl","monitoredUser","DisplayName","AvatarUrl","onStateEvents","_OwnProfileStore","onDispatcherAction","Prepared","useUnitTestClient","mxToastStore","newToast","toast","getToasts","windowEntry","trackedElementName","trackedUiElements","uiElementDimensions","innerWidth","innerHeight","getElementDimensions","trackElementDimensions","stopTrackingElementDimensions","trackedElement","unobserve","isTrackingElementDimensions","mxUIStore","WidgetEchoStore","roomWidgetEcho","getEchoedRoomWidgets","currentRoomWidgets","echoedWidgets","roomEchoState","roomHasPendingWidgetsOfType","roomHasPendingWidgets","setRoomWidgetEcho","removeRoomWidgetEcho","singletonWidgetEchoStore","isAppWidget","initRoom","loadRoomWidgets","_this$matrixClient$ge2","onWidgetEchoStoreUpdate","roomMap","widgetMap","generateApps","getRoomWidgets","makeAppConfig","edited","existingApp","initIfNeeded","roomApps","mxWidgetStore","ContextTransactionState","EchoContext","Whenable","NotStarted","AllSuccessful","transactions","TransactionStatus","didPreviouslyFail","PendingErrors","Pending","_state","notifyCondition","_transactions","firstFailedTime","failedTxn","disownTransaction","checkTransactions","beginTransaction","auditName","EchoTransaction","whenAnything","when","Success","RoomEchoContext","ServerOfflineDialog","EchoStore","onEchosUpdated","renderTimeline","NonUrgentEchoFailureToast","OfflineIcon","roomContextKey","caches","getOrCreateChamberForRoom","checkContexts","echo","RoomEchoChamber","setClient","hasOrHadError","toastRef","didFail","_status","setStatus","implicitlyReverted","GenericEchoChamber","onClientChanged","cacheVal","decacheKey","markEchoReceived","targetVal","revertFn","ctxn","PushRules","updateNotificationVolume","Muted","NotificationState","watcherReferences","_symbol","_count","_muted","_knocked","_invited","emitIfUpdated","isDifferentFrom","NotificationStateSnapshot","isInvitation","before","is","after","ListNotificationState","byTileCount","getRoomFn","calculateTotalState","setRooms","onRoomNotificationStateUpdate","RoomNotificationState","readReceiptChangeIsFor","MARKED_UNREAD_TYPE_STABLE","MARKED_UNREAD_TYPE_UNSTABLE","handleReadReceipt","handleMembershipUpdate","handleLocalEchoUpdated","handleRoomEventUpdate","handleRoomAccountDataUpdate","handleNotificationCountUpdate","handleAccountDataUpdate","isMention","isUnsentMessage","isActivityNotification","hasAnyNotificationOrActivity","isNotification","RoomNotifs","SummarizedNotificationState","numUnreadStates","totalStatesWithUnread","includeSymbol","UPDATE_STATUS_INDICATOR","emitUpdateIfStateChanged","forceEmit","globalState","numFavourites","VisibilityProvider","isRoomVisible","_globalState","testInstance","listMap","useTileCount","onSync","convertToStorePanel","cacheRoom","storeHistory","panelState","_panelState$state","_state$threadHeadEven","_state$memberInfoEven","_state$initialEvent","_state$member","threadHeadEventId","threadHeadEvent","memberInfoEventId","memberInfoEvent","memberId","convertCardToStore","convertToStatePanel","storeRoom","stateHistory","panelStateStore","_panelStateStore$stat","stateStored","convertStoreToCard","_this$currentCard","pendingRequest","pendingVerificationRequestForUser","emitAndUpdateSettings","byRoom","viewedRoomId","VerificationRequestReceived","onVerificationRequestUpdate","loadCacheFromSettings","changePayload","handleViewedRoomChange","FocusMessageSearch","RoomSummary","focusRoomSearch","_this$byRoom$isOpen","_this$byRoom","_this$viewedRoomId","_this$byRoom$roomId$i","_this$byRoom$roomId","_this$byRoom$history","_this$byRoom2","_this$viewedRoomId2","hist","_this$byRoom$roomId$h","_this$byRoom$roomId2","allowClose","_redirect$phase","_redirect$state","_card$state","_this$currentCardForR","_this$currentCardForR2","rId","redirect","getVerificationRedirect","targetPhase","isPhaseValid","_this$byRoom$rId$hist","_this$byRoom$rId","generateHistoryForPhase","setCards","cards","_c$state","_redirect$phase2","_redirect$state2","pState","roomCache","_ref5","removedCard","_ref6","_ref7","_ref8","showOrHidePhase","isCardStateValid","ThreadPanel","ThreePidMemberInfo","getPhasesForPhase","_this$mxClient","_ref9","_this$global","_ref0","_this$byRoom$this$vie","filterValidCards","storePanelGlobal","panelThisRoom","storePanelThisRoom","rightPanelForRoom","_card$state2","_card$state3","_card$state4","_card$state5","_card$state6","_card$state7","_card$state8","_card$state9","ThreadView","Widget","_this$currentCard2","_this$currentCard3","_this$viewedRoomId3","mxRightPanelStore","selfUserId","shouldPrefixMessagesIn","PollStartEventPreview","getTextFor","isThread","sanitizeForTranslation","InvalidEventError","PREVIEWS","previewer","_eventContent","_eventContent$msgtype","_event$getWireContent","hasHtml","sanitised","emote","stickerName","relatedEvent","generatePreviewForEvent","TAG_ANY","_thread$rootEvent","mkMessagePreview","inTagId","_previews$get","_previewDef$previewer","previewDef","changed","_map$get","anyPreviewText","tagsToGenerate","genTagId","realTagId","_map$get2","_map$get3","isHistoricalEvent","onLocalEchoUpdated","_MessagePreviewStore","ListLayout","serialized","_n","_previews","_collapsed","paddingPx","tilesToPixels","px","ensureLayoutExists","layoutMap","resetLayouts","mxRoomListLayoutStore","FILTER_CHANGED","ALGORITHM_INSTANCES","RecentAlgorithm","getOrderProp","sortRoomsWithAlgorithm","getSortingAlgorithmInstance","OrderingAlgorithm","initialSortingAlgorithm","setSortAlgorithm","orderedRooms","cachedOrderedRooms","isMutedToBottom","sortingAlgorithm","getRoomIndex","roomIdx","CATEGORY_ORDER","ImportanceAlgorithm","categorizeRooms","_map$category","getRoomCategory","categorized","notificationColor","roomsToOrder","newlyOrganized","newIndices","indices","getCategoryIndex","categoryIndex","handleSplice","RoomUpdateCause","NewRoom","alterCategoryPositionBy","sortCategory","RoomRemoved","oldCategory","getCategoryFromIndices","handleRoomUpdate","ReadReceipt","PossibleMuteChange","moveRoomIndexes","nextCategoryStartIdx","numSort","sorted","isLast","nRooms","fromCategory","toCategory","nextOrderIndex","nextCategory","lastCat","lastCatIndex","thisCat","thisCatIndex","NaturalAlgorithm","defaultRooms","mutedRooms","cachedCategorizedOrderedRooms","buildCachedOrderedRooms","isSplice","isInPlace","getRoomIsMuted","removeRoom","onPossibleMuteChange","defaultIndex","mutedIndex","ALGORITHM_FACTORIES","initSort","getListAlgorithmInstance","LIST_UPDATED_EVENT","CAUSES_REQUIRING_ROOM","Algorithm","recalculateStickyRoom","recalculateActiveCallRooms","updatesInhibited","onConnectedCalls","stickyRoom","_stickyRoom","hasTagSortingMap","sortAlgorithms","cachedRooms","_cachedRooms","setStickyRoom","updateStickyRoom","algorithms","getListOrdering","listAlgorithms","setListOrdering","doUpdateStickyRoom","_lastStickyRoom","_val","_this$roomIdsToTags$v","roomIdsToTags","getOrderedRoomsWithoutSticky","wasSticky","lastStickyRoom","stickyRoomMightBeModified","initCachedStickyRooms","_cachedStickyRooms","updatedTag","sticky","activeRoomIds","activeRooms","inactiveRooms","populateTags","tagSortingMap","listOrderingMap","setKnownRooms","getOrderedRooms","oldStickyRoom","newTags","generateFreshTags","splitRoomsByMembership","getTagsOfJoinedRoom","inTag","updateTagsFromCache","getEffectiveMembershipTag","newMap","updatedTagMap","_this$_stickyRoom","isSticky","_this$_lastStickyRoom","isForLastSticky","hasTags","PossibleTagChange","knownRoomRef","didTagChange","oldTags","rmTag","SpaceFilterCondition","beforeRoomIds","getSpaceFilteredRoomIds","beforeUserIds","getSpaceFilteredUserIds","beforeShowPeopleInSpace","showPeopleInSpace","setHasDiff","isRoomInSpace","updateSpace","onStoreUpdate","SpaceWatcher","allRoomsInHome","neededFilter","needsFilter","addFilter","removeFilter","onSelectedSpaceUpdated","UPDATE_HOME_BEHAVIOUR","onHomeBehaviourUpdated","RoomListStoreEvent","ListsUpdate","ListsLoading","RoomListStoreClass","updateFn","recalculatePrefiltering","msc3946SettingWatcherRef","_settingName","_newValAtLevel","regenerateAllLists","setupWatchers","resetStore","prefilterConditions","initialListsGenerated","onAlgorithmListUpdated","makeReady","forcedClient","handleRVSUpdate","onAlgorithmFilterUpdated","updateAlgorithmInstances","activeRoomId","activeRoom","TEST_MODE","onDispatchAsync","roomPayload","eventPayload","tryUpdate","updatedRoom","dmMap","onDispatchMyMembership","possibleMuteChangeRoomIds","getChangedOverrideRoomMutePushRules","membershipPayload","newMembership","roomUpgradeHistory","predecessors","getPlausibleRooms","currentSticky","stickyIsStillPresent","setAndPersistTagSorting","getStoredTagSorting","calculateTagSorting","definedSort","storedSort","tagSort","setAndPersistListOrder","getStoredListOrder","calculateListOrder","defaultOrder","definedOrder","storedOrder","listOrder","sorts","orders","allTags","OrderedDefaultTagIDs","onPrefilterUpdated","algorithmTags","getCount","manualRoomUpdate","mxRoomListStore","shouldCauseReorder","tsCache","_tsCache$a$roomId","_tsCache$b$roomId","roomALastTs","getLastTs","roomBLastTs","mainTimelineLastTs","_r$timeline$0$getTs","_r$timeline$","bumpStamp","getBumpStamp","membershipEvent","Unread","threadLastEventTimestamps","_thread$replyToEvent","_event$getTs","isVisibleFn","actionPayload","_actionPayload$event","roomPushRules","prevRoomPushRules","SpaceNotificationState","getFirstRoomWithNotifications","_Object$values$find","midPointsBetweenStrings","maxLen","alphabet","DEFAULT_ALPHABET","padN","padA","alphabetPad","padB","baseA","stringToBase","baseB","BigInt","baseToString","reorderLexicographically","fromIndex","toIndex","_newOrder","_newOrder2","_newOrder$order","_newOrder4","_newOrder$order2","_newOrder5","ordersWithIndices","newOrder","moveElement","orderToLeftUndefined","leftBoundIdx","rightBoundIdx","canMoveLeft","nextBase","MAX_VALUE","_newOrder$i","firstOrderBase","bigToIndex","canDisplaceRight","canMoveRight","_newOrder3","_newOrder$rightBoundI","prevBase","MIN_VALUE","_newOrder$i2","leftDiff","rightDiff","traverseSpaceDescendants","spaceDescendantMap","spaceId","flatSpace","descendentSpaces","descendantSpaceId","flattenSpaceHierarchy","spaceEntityMap","flattenedSpaceIds","flattenedRooms","flattenSpaceHierarchyWithCache","useCache","ACTIVE_SPACE_LS_KEY","metaSpaceOrder","getSpaceContextKey","partitionSpacesAndRooms","validOrder","charCode","getChildOrder","_validOrder","NaN","SpaceStoreClass","EnhancedMap","roomIdsBySpace","userIdsBySpace","getRoomHierarchy","viaMap","children_state","_ev$content$via","room_type","includeDescendantSpaces","_msc3946ProcessDynamicPredecessor","getAggregatedRoomIdsBySpace","childSpacesBySpace","getAggregatedUserIdsBySpace","_aggregatedSpaceCache","rootSpace","unseen","joinedSpaces","unseenSpaces","subspace","rootSpaces","detachedNodes","markTreeChildren","detachedNode","visibleSpaces","invitedSpaces","findRootSpaces","oldRootSpaces","sortRootSpaces","onRoomsUpdate","UPDATE_TOP_LEVEL_SPACES","enabledMetaSpaces","oldInvitedSpaces","_invitedSpaces","UPDATE_INVITED_SPACES","parentMap","showInHomeSpace","switchSpaceIfNeeded","rebuildHomeSpace","orphans","_this$parentMap$get","dmBadgeSpace","flattenedRoomsForSpace","getNotificationState","notificationStateMap","_this$parentMap$get2","inSpace","isInSpace","_this$userIdsBySpace$","_this$userIdsBySpace$2","affectedParentSpaceIds","prevRoomsBySpace","prevUsersBySpace","prevChildSpacesBySpace","rebuildParentMap","rebuildMetaSpaces","hiddenChildren","getParents","traverseSpace","parentPath","_hiddenChildren$get","childSpaces","childRooms","newPath","childSpace","expandedRoomIds","roomDiff","mapDiff","userDiff","spaceDiff","roomsChanged","usersChanged","spacesChanged","changeSet","changedId","notificationStatesToUpdate","updateNotificationStates","_this$matrixClient3","switchToRelatedSpace","_this$getCanonicalPar","getCanonicalParent","_this$rootSpaces$find","setActiveSpace","goToFirstSpace","roomMembership","_this$parentMap$get3","rebuildSpaceHierarchy","numSuggestedRooms","_suggestedRooms","_this$matrixClient4","loadSuggestedRooms","_this$matrixClient5","getDMRoomsForUserId","onMemberUpdate","lastEv","SpaceOrder","_ev$getContent","_lastEv$getContent","spaceOrderLocalEchoMap","notifyIfOrderChanged","Tag","_lastEv$getContent2","_ev$getContent2","onRoomFavouriteChange","prevEv","_prevEv$getContent","previousRooms","setDiff","_this$matrixClient6","onRoomDmChange","_space$getAccountData","storeReadyPromise","_storeReadyDeferred","_enabledMetaSpaces","_activeSpace","_this$matrixClient7","_allRoomsInHome","setActiveRoomInSpace","_this$matrixClient8","tagLoop","contextSwitch","cliSpace","_cliSpace","_cliSpace2","getLastSelectedRoomIdForSpace","_this$matrixClient9","fetchSuggestedRooms","_this$matrixClient0","childEvents","_ev$getContent3","canonicalOnly","_this$matrixClient1","canonical","_sortBy","includeAncestors","_this$getSpaceFiltere","_this$getSpaceFiltere2","_this$matrixClient10","_this$roomIdsBySpace$","_this$roomIdsBySpace$2","_this$roomIdsBySpace$3","homeRooms","_this$roomIdsBySpace$4","_this$roomIdsBySpace$5","onRoomAccountData","oldMetaSpaces","sendUserProperties","lastSpaceId","_this$enabledMetaSpac","_this$spacePanelSpace","_payload$justCreatedO","_payload$room_id","AfterLeaveRoom","SwitchSpace","numMetaSpaces","hadPeopleOrHomeEnabled","hasPeopleOrHomeEnabled","includeRooms","getSpaceTagOrdering","setRootSpaceOrder","_this$matrixClient11","moveRootSpace","currentOrders","mxSpaceStore","getMetaSpaceName","ElementWidgetCapabilities","MAX_PINNED","recalculateRoom","updateAllRooms","_atLevel","_newVal","emissionForRoom","emitFor","updateRoomFromState","pinnedRef","updateFromSettings","layoutRef","dynamicRef","updateFromWidgetStore","_layoutEv$getContent","roomContainers","beforeChanges","recursiveMapToObject","layoutEv","legacyPinned","userLayout","overrides","roomLayout","topWidgets","rightWidgets","centerWidgets","_roomLayout$widgets","_userLayout","stateContainer","manualContainer","isLegacyPinned","defaultContainer","Center","targetContainer","runoff","_roomLayout$widgets2","_roomLayout$widgets3","_userLayout2","_userLayout3","layoutA","layoutB","userLayoutA","userLayoutB","defaultA","MIN_SAFE_INTEGER","defaultB","orderA","defaultNumber","orderB","widths","doAutobalance","_roomLayout$widgets4","_userLayout4","widgetLayout","userWidgetLayout","normalized","defRoomHeight","difference","toReclaim","largeIndices","newRoomContainers","distributions","getContainerWidgets","_this$byRoom$get","canAddToContainer","getResizerDistributions","_this$byRoom$get2","setResizerDistributions","numbers","localLayout","_this$byRoom$get3","updateUserLayout","getContainerHeight","_this$byRoom$get$get$","_this$byRoom$get4","setContainerHeight","_this$byRoom$get5","moveWithinContainer","_this$byRoom$get6","_this$byRoom$get7","currentIdx","newIdx","toContainer","getAllWidgets","newLayout","hasPinnedWidgets","canCopyLayoutToRoom","copyLayoutToRoom","allWidgets","evContent","_this$byRoom$get8","_this$byRoom$get9","containers","ret","containerValue","_this$byRoom$get0","_this$byRoom$get1","mxWidgetLayoutStore","WidgetOpenIDPermissionsDialog","onPermissionSelection","rememberSelection","allowed","setOIDCState","widgetKind","OIDCState","Allowed","Denied","templateUrl","onAllow","onRememberSelectionChange","GENERIC_WIDGET_KIND","CapabilityText","bylineFor","eventCap","EventKind","keyStr","capability","simpleCaps","textForKind","primary","isTimelineCapability","isTimelineCapabilityFor","Symbols","AnyRoom","getTimelineRoomIDFromCapability","_room$getCanonicalAli","WidgetEventCapability","findEventCapabilities","Event","forRoomMessageCap","evSendRecv","stateSendRecvCaps","nonStateSendRecvCaps","textForDirection","WidgetKind","EventDirection","Send","MatrixCapabilities","AlwaysOnScreen","StickerSending","CanChangeViewedRoom","MSC2931Navigate","Receive","WidgetCapabilitiesPromptDialog","newStates","booleanStates","closeAndTryRemember","cap","requestedCapabilities","eventPermissionsMap","raw","approved","remember","checkboxRows","capA","capB","isTimelineA","lexicographicCompare","onReject","normalizeTurnServer","credential","uris","ElementWidgetDriver","WidgetDriver","forWidget","forWidgetKind","virtual","allowedCapabilities","Screenshots","RequiresClient","STICKERPICKER","stickerSendingCap","forRoomEvent","MSC3846TurnServers","MSC4157SendDelayedEvent","MSC4157UpdateDelayedEvent","MSC4407SendStickyEvent","MSC4407ReceiveStickyEvent","forStateEvent","clientUserId","clientDeviceId","sendRoomEvents","CallNotify","sendRecvRoomEvents","RTCMembership","sendRecvToDevice","CallCandidates","CallNegotiate","CallSDPStreamMetadataChanged","CallSDPStreamMetadataChangedPrefix","CallReplaces","CallEncryptionKeysPrefix","forToDeviceEvent","validateCapabilities","missing","allowedSoFar","preapproveCapabilities","approvedCapabilities","WidgetLifecycle","CapabilitiesRequest","rememberApproved","_result$approved","allAllowed","arrayIntersection","iterableIntersection","caps","setRememberedCapabilitiesForWidget","getSendEventTarget","_content$mRelates_to","THREAD_RELATION_TYPE","sendStickyEvent","stickyDurationMs","_unstable_sendStickyEvent","getSendDelayedEventOpts","delay","parentDelayId","parent_delay_id","sendDelayedEvent","delayOpts","_unstable_sendDelayedStateEvent","_unstable_sendDelayedEvent","delayId","delay_id","sendDelayedStickyEvent","_unstable_sendStickyDelayedEvent","cancelScheduledDelayedEvent","_unstable_cancelScheduledDelayedEvent","restartScheduledDelayedEvent","_unstable_restartScheduledDelayedEvent","sendScheduledDelayedEvent","_unstable_sendScheduledDelayedEvent","sendToDevice","contentMap","invertedContentMap","userContentMap","stringifiedContent","recipients","batch","encryptToDeviceMessages","queueToDevice","readRoomTimelineIterator","since","resultCount","getEffectiveEvent","readRoomTimeline","readRoomState","askOpenID","observer","IdentityRequest","OpenIDRequestState","oidcState","getOIDCState","getToken","Blocked","PendingUserConfirmation","navigate","pollingTurnServers","setTurnServer","onTurnServers","onTurnServersError","TurnServers","TurnServersError","initialTurnServer","readEventRelations","prevBatch","limited","getMediaConfig","uploadFile","contentUri","getKnownRooms","processError","matrix_api_error","asWidgetApiErrorData","ELEMENT_CLIENT_ID","ModalWidgetDialog","disabledButtonIds","widgetDefinition","_this$state$messaging","themeWatcher","onThemeChange","sendWidgetConfig","WidgetApiFromWidgetAction","CloseModalWidget","onWidgetClose","SetModalButtonEnabled","onButtonEnableToggle","_this$state$messaging2","updateTheme","_this$state$messaging4","_this$state$messaging3","BuiltInModalButtonID","possibleButtons","buttonIds","tempSet","ElementWidget","sourceWidgetId","driver","ClientWidgetApi","appFrame","_this$widget$name","templated","getCompleteUrl","widgetRoomId","userDisplayName","userHttpAvatarUrl","clientTheme","clientLanguage","ModalButtonKind","Primary","Secondary","Danger","isDisabled","_this$state$messaging5","notifyModalWidgetButtonClicked","widgetDomain","ModalWidgetStore","modalInstance","requestData","sourceWidget","openSourceWidgetId","openSourceWidgetRoomId","closeModalWidget","sourceMessaging","getMessaging","notifyModalWidgetClose","_ModalWidgetStore","mxModalWidgetStore","rawDefinition","_super$rawData","forLocalRender","rawData","popoutTemplateUrl","_super$rawData2","conferenceId","customTheme","getCustomTheme","is_dark","asPopout","runTemplate","WidgetMessaging","_options$room","_this$widgetApi","_this$widgetApi2","_this$widgetApi3","canOpenModalWidget","openModalWidget","setViewedRoomId","feedEvent","feedStateUpdate","encryptionInfo","_this$widgetApi4","feedToDevice","userWidget","stickyPromise","embedUrl","runUrlTemplate","popoutUrl","_WidgetVariableCustom","_WidgetVariableCustom2","_this$client$getDevic","fromCustomisation","provideVariables","_SdkContextClass$inst2","OpenModalWidget","onOpenModal","_this$widgetApi6","_this$widgetApi5","_this$widgetApi7","hasCapability","roomEvent","readUpToMap","onStateUpdate","ReceivedToDeviceMessage","onToDeviceMessage","UpdateAlwaysOnScreen","_this$widgetApi8","_this$roomId","SendSticker","_this$widgetApi9","OpenIntegrationManager","_this$widgetApi0","_IntegrationManagers$","integType","integId","_ev$detail$data","_this$widgetApi1","errorMessage","_WidgetVariableCustom3","_WidgetVariableCustom4","isScalarUrl","defaultManager","scalar","forceDestroy","_this$roomId2","_this$widgetApi10","_this$widgetApi11","Stop","stopMessaging","relatesToUnknown","isFromInvite","advanceReadUpToMarker","evId","upToEventId","eventsToFeed","storeMessaging","_WidgetMessagingStore","packSettingKey","_settings$deny","_settings$allow","settingsKey","Unknown","currentValues","HIGH_CONTRAST_THEMES","light","findNonHighContrastTheme","isHighContrastTheme","BUILTIN_THEMES","customThemes","customThemeNames","getOrderedThemes","themes","builtInThemes","allowedFontFaceProps","COMPOUND_TOKEN","normalizeHexColour","hexColor","setHexAlpha","normalizedHexColor","setCustomThemeVars","setCSSColorVariable","doPct","baseAlpha","parseAlpha","colors","fonts","css","face","_face$src","srcElement","local","prop","general","monospace","compound","generateCustomCompoundCSS","themeName","knownNames","setTheme","_document$querySelect","_document$querySelect2","inlineStyleProps","clearCustomTheme","stylesheetName","styleElements","mxTheme","styleSheet","compoundThemeClassName","switchTheme","bodyStyles","backgroundColor","isStyleSheetLoaded","styleSheets","_styleSheet","waitForStyleSheetLoading","onAccept","getLocalNotificationAccountDataEventType","is_silenced","showToast","fromMessageSend","hideToast","REPOS","parseVersion","commit","checkVersion","ChangelogDialog","fetchChanges","repo","statusText","commits","newCommits","elementsForCommit","sha","html_url","releaseNotes","acceptLabel","_matrixClient$getAcco","_matrixClient$getAcco2","setMDirectFromContent","userToRooms","roomToUser","hasSentOutPatchDirectAccountDataPatch","mDirectRawContent","makeShared","setShared","inst","populateRoomToUser","patchUpSelfDMs","selfRoomIds","guessedUserIdsThatChanged","guessDMUserId","getUserToRooms","getDMRoomForIdentifiers","commonRooms","userRooms","getDMInviter","hasTwoMembers","getInvitedAndJoinedMemberCount","getRoomIds","prevRoomIds","selfDMs","neededPatching","responseData","_info$mimetype$split$","_info$mimetype","dataArray","getBlobSafeMimeType","_ModuleApi$instance$c","allowEditingEvent","canEditOwnEvent","maxIdx","inc","beginIdx","foundFromEventId","msc3531Enabled","VISIBLE_FOR_ALL","SEE_THROUGH_FOR_CURRENT_USER","EVENT_VISIBILITY_CHANGE_TYPE","fetchInitialEvent","_initialEvent","supportsThreads","_room$findEventById","createThread","canCancel","ENCRYPTING","hasThreadSummary","_event$getThread","DEFAULT_STYLES","managedIframe","onLoadPromise","iframeFn","_this$iframeFn","_iframe$contentWindow","contentWindow","auto","withSize","standard","fallbackText","shortened","_content$body","extension","byteCount","filesize","compactFormatter","NumberFormat","notation","formatter","formatCountLong","getUserNameColorClass","itemLimit","includeCount","_items$","ListFormat","joinedItems","jsxJoin","Items","base_url","fullUrl","_terms","arrayBufferRead","arrayBufferReadInt","DataView","getUint32","arrayBufferReadStr","decoder","ImageDecoder","tracks","track","flags","dv","globalColorTable","getUint8","globalColorTableSize","pow","extensionIntroducer","graphicsControlLabel","delayTime","getUint16","onMarkCallback","marked","_this$onMarkCallback","LazyValue","getFn","present","thumbnailBlob","_content$info$thumbna","prepareSourceUrl","prepareThumbnailUrl","fetchSource","fetchThumbnail","canHide","InviteProgressDialog","InviteState","USER_ALREADY_JOINED","USER_ALREADY_INVITED","USER_BANNED","_fatal","openInviteProgressDialog","completionStates","errors","doInvite","handleUnknownProfileUsers","_closeDialog","_this$errors$addr$err","_this$errors$addr","inviteToRoom","ignoreProfile","addrType","inviteByEmail","ourMember","shareEncryptedHistory","_this$options$progres","_this$options","inviteUnknowns","isPinnable","isUnpinnable","PINNABLE_EVENT_TYPES","pinnedEvent","userHasPinOrUnpinPermission","_room$getLiveTimeline2","_room$getLiveTimeline3","pinnedIds","roomAccountDataPromise","_room$getAccountData","event_ids","unpinAllEvents","roomVer","featureVer","array","joiner","allowVulnerableTags","exclusiveFilter","frame","shouldDisplayReply","inReplyTo","is_falling_back","addReplyToMessageContent","mixin","makeReplyMixIn","checkForRoomFn","handleError","updateSpaces","awaitRoom","inhibitInviteProgressDialog","_spinnerModal","spinnerModal","toInvite","parentsToRelink","inviteOptions","inviteUsersToRoom","currentEv","shieldStatusForRoom","getEncryptionTargetMembers","inDMMap","verified","unverified","devicesByUser","asyncSome","ClientStoppedError","keyMap","SingleflightContext","forgetAll","forget","fallbackKey","fallbackWarnings","toJSON","_activityScores$a$use","_activityScores$a$use2","_memberScores$a$userI","_memberScores$a$userI2","_memberScores$a$userI3","_memberScores$a$userI4","_activityScores$b$use","_activityScores$b$use2","_memberScores$b$userI","_memberScores$b$userI2","_memberScores$b$userI3","_memberScores$b$userI4","aScore","aNumRooms","bScore","bNumRooms","joinedRooms","earliestAgeConsidered","takeRight","senderEvents","groupBy","mapValues","maxBy","distanceFromNow","inverseTime","lastSpoke","memberPeerEntries","userMeta","roomMemberships","maximumPeers","totalPeers","sumBy","minBy","getIDBFactory","_self","self","idb","idbInit","idbTransaction","table","idbClear","SYNC_STORE_NAME","LEGACY_CRYPTO_STORE_NAME","RUST_CRYPTO_STORE_NAME","tryPersistStorage","persist","requestStorageAccess","checkConsistency","dataInLocalStorage","dataInCryptoStore","cryptoInited","healthy","exists","IndexedDBStore","checkSyncStore","rustDbExists","IndexedDBCryptoStore","legacyIdbExists","existsAndIsNotMigrated","checkCryptoStore","setCryptoInitialised","elapsed","startTs","setNotStarted","timerHandle","onTimeout","changeTimeout","isSmallerTimeout","unabbreviateUrl","longUrl","E2EE_WK_KEY","E2EE_WK_KEY_DEPRECATED","TILE_SERVER_WK_KEY","EMBEDDED_PAGES_WK_PROPERTY","getCallBehaviourWellKnown","clientWellKnown","getE2EEWellKnown","getTileServerWellKnown","tileServerFromWellKnown","_clientWellKnown$TILE","getEmbeddedPagesWellKnown","condition","listeners","whenAnyOf","testUrlString","testUrl","scalarUrls","integrations_widgets_urls","scalarUrl","_testUrl$pathname","waitForUserWidget","eventInIntendedState","waitForRoomWidget","eventsInIntendedState","evList","widgetPresent","setUserWidget","widgetData","userWidgets","getUserWidgets","addingWidget","widgetAvatarUrl","setRoomWidgetContent","appsStateEvents","getUserWidgetsArray","getStickerpickerWidgets","_widget$content","_w$content","removeStickerpickerWidgets","oobRoomName","_await$Jitsi$getInsta","preferredDomain","getJitsiAuth","confId","base32","pad","secureRandomStringFrom","LOWERCASE","isAudioOnly","appId","senderUserId","queryStringParts","queryString","getWidgetName","_app$name","getWidgetDataTitle","editWidget","isManagedByManager","useWidgets","apps","setApps","updateApps","points","everyNth","spreadFactor","arrayUnion","arrays","concatenatedSoFar","toBeConcatenated","concatenated","asyncSomeParallel","any","AggregateError","asyncFilter","_room$currentState$be","getBeaconInfoIdentifier","latestLocationEvent","msUntilExpiry","startTimestamp","sortBeaconsByLatestExpiry","GeolocationOptions","maximumAge","mapGeolocationError","isGeolocationPositionError","Default","PERMISSION_DENIED","POSITION_UNAVAILABLE","PositionUnavailable","TIMEOUT","Timeout","getGeolocation","geolocation","genericPositionFromGeolocation","geoPosition","latitude","longitude","altitude","accuracy","coords","getGeoUri","genericPosition","onWatchPosition","onWatchPositionError","watchId","clearWatch","setBeacon","beaconInstance","beaconInstanceEventId","setStoppingInProgress","resetLocationPublishError","getBeaconById","ALLOWED_BLOB_MIMETYPES","frequency","hue","chroma","cos","sin","generateAB","green","blue","adjustXYZ","z","adjustRGB","labToRGB","corrected","gammaCorrection","storeOpts","useAuthorizationHeader","dbName","workerFactory","indexeddbWorkerFactory","cryptoStore","LocalStorageCryptoStore","MemoryCryptoStore","_deviceMap$get","getUserDeviceIds","_deviceMap$get$keys","_deviceMap$get2","e2eeWellKnown","isDehydrationSupported","startDehydration","concatenateNameAndVersion","UAParser","getBrowser","operatingSystem","getOS","getDeviceType","_operatingSystem$name","Mobile","shouldIgnoreOSVersion","deviceOperatingSystem","deviceModel","vendor","customDeviceModel","customDeviceOS","deviceInfoSegments","checkForCustomValues","showSpinner","existingRoom","_DMRoomMap$shared$get","createRoomOptions","determineCreateRoomEncryptionOption","roomOptions","lookupThreePidProfiles","threePids","lookedUpThreePids","bulkLookupThreePids","threepids","_threePidType","threePidId","lookupThreePids","resolvedTargets","threePidMembers","lookedUpProfiles","_lookedUpProfile$prof","_lookedUpProfile$prof2","lookedUpProfile","resolveThreePids","_findDMForUser","findDMRoom","makeTxnId","KNOWN_SAFE_ROOM_VERSION","_target$getMxcAvatarU","_target$getMxcAvatarU2","updateMyMembership","addLiveEvents","addToState","setStateEvents","createDmLocalRoom","createRoomFromLocalRoom","CREATING","waitForRoomReadyAndApplyAfterCreateCallbacks","Member","userDirResult","filteredRoomIds","extractSuitableRoom","findRoomWithThirdpartyInvites","suitableRooms","functionalUsers","getFunctionalMembers","joinedMembers","isJoinedOrNearlyJoined","thirdPartyInvites","r1","suitableRoomForUserId","allRoomIds","BlurhashEncoder","getBlurhash","imageData","_BlurhashEncoder","inputWidth","inputHeight","calculateBlurhash","thumbnailPromise","targetWidth","targetHeight","OffscreenCanvas","convertToBlob","getImageData","LeaveSpaceDialog","roomSet","rejoinWarning","onlyAdminWarning","isOnlyAdmin","_spinnerModal2","leavingAllVersions","SENDING","leaveRoomChain","limitExceededError","_limitExceededError$d","roomErr","isRoomReady","_localRoom$targets","roomEncryptionEvents","isActualRoomIdDefined","afterCreateCallbacks","applyAfterCreateCallbacks","finish","checkRoomStateIntervalHandle","stopgapTimeoutHandle","stopgapFinish","afterCreateCallback","roomOrID","WebGLNotEnabled","findMapStyleUrl","_getTileServerWellKno","_getTileServerWellKno2","mapStyleUrl","map_style_url","locationContent","_asset$type","asset","M_ASSET","findIn","LocationAssetType","Self","_loc$uri","loc","parseGeoUri","parseFloat","uncertainty","param","geoCoords","altitudeAccuracy","makeMapSiteLink","mLocation","positionFailureMessage","aKeys","bKeys","keyDiff","previousMembership","isKicked","effective","_client$getRoom$getMe","__","NewMember","userLevelValues","maxUserLevel","editedContent","mentions","userMentions","roomMention","newMentions","user_ids","prevMentions","MarkedUnread","deviceNotificationSettingsKeys","LOCAL_NOTIFICATION_SETTINGS_PREFIX","isSilenced","_event$getContent$is_","getLastLiveEvent","receiptType","Read","sendReadReceipt","setUnreadNotificationCount","setThreadUnreadNotificationCount","clearAllNotifications","receiptPromises","_room$getAccountData2","currentStateStable","currentStateUnstable","notificationLevelToIndicator","getThreadNotificationLevel","threadsAggregateNotificationType","tempMap","existingProps","propertyCloner","newObj","possibleChanges","objectDiff","clientIdStorageKey","tokenIssuerStorageKey","idTokenStorageKey","persistOidcAuthenticatedSettings","_localStorage$getItem","getStoredOidcIdTokenClaims","decodeIdToken","idTokenClaims","_localStorage$getItem2","baseUrlPattern","PermalinkConstructor","serverCandidates","encodeServerCandidates","forUser","forEntity","entityId","testHost","matchAll","PermalinkParts","eventIdAndQuery","ElementPermalinkConstructor","elementUrl","parseAppRoute","lastPartMaybeWithQuery","entityType","MatrixSchemePermalinkConstructor","encodeEntity","entityNoSigil","sigil","ANY_REGEX","shouldThrottle","fullUpdate","highestPlUserId","getServerName","serversByPopulation","populationMap","_getHostnameFromMatri","getHostnameFromMatrixServerName","isHostnameIpAddress","isHostInRegex","bannedHostsRegexps","allowedHostsRegexps","_serverCandidates","started","getPermalinkConstructor","updateAllowedServers","updateHighestPlUser","updatePopulationMap","updateServerCandidates","allowedEntries","_getHostnameFromMatri2","maxEntry","_this$room6","aclEvent","getRegex","denied","isPill","_permalinkParts$viaSe","eventIdPart","pl","matrixtoBaseUrl","_permalinkParts$viaSe2","entityInfo","elementPrefix","decodedUrl","matrixToBaseUrlPattern","regexps","isIP","_permalinkCreator$ser","localUri","timeoutValue","timeoutId","lastErr","receipt","isSupportedReceiptType","functionalUsersStateEvent","UNSTABLE_ELEMENT_FUNCTIONAL_USERS","service_members","functionalMembers","CreateSubspaceDialog","onAddExistingSpaceClick","setParentSpace","spaceJoinRule","defaultJoinRule","setJoinRule","onCreateSubspaceClick","joinRuleMicrocopy","AddExistingSubspaceDialog","OpenSpaceSettings","OpenAddToExistingSpaceDialog","showAddExistingSubspace","UpdateSpaceHierarchy","OpenSpacePreferences","_navigator","clipboard","writeText","textArea","selectNode","execCommand","selectNodeContents","copyNode","Segmenter","iterator","pixelValue","GenericExpiringToast","dismissLabel","onDismiss","numSeconds","rejectLabel","thumbnailSize","Tabs","ExistingSource","thumbnailClasses","mx_desktopCapturerSourcePicker_source_thumbnail","mx_desktopCapturerSourcePicker_source_thumbnail_selected","thumbnailURL","DesktopCapturerSourcePicker","selectedSource","selectedTab","Screens","sources","interval","getTab","_this$state$selectedS","Windows","onShare","BaseEventIndexManager","supportsEventIndexing","initEventIndex","addEventToIndex","deleteEvent","isEventIndexEmpty","isRoomIndexed","getStats","getUserVersion","setUserVersion","commitLiveEvents","searchEventIndex","searchArgs","addHistoricEvents","checkpoint","oldCheckpoint","addCrawlerCheckpoint","removeCrawlerCheckpoint","loadCheckpoints","loadFileEvents","closeEventIndex","deleteEventIndex","IPCManager","sendChannel","recvChannel","_ev","pendingIpcCalls","onIpcReply","ipcCallId","nextIpcCallId","SeshatIndexManager","ipc","searchConfig","SSO_ID_KEY","ElectronPlatform","releaseName","showUpdateToast","Downloading","NotAvailable","getUpdateCheckStatus","_MatrixClientPeg$get3","onUpdateDownloaded","clientStartedPromiseWithResolvers","uniqueId","onBreadcrumbsUpdate","initialise","ClientStarted","supportedSettings","supportsBadgeOverlay","badgeOverlayRenderer","_this$supportedSettin","feedUrl","platformName","eventIndexManager","_web_base_url","checkSessionLockFree","getSessionLock","_onNewInstance","SESSION_LOCK_CONSTANTS","onNewInstance","sessionIdentifier","uuidv4","prefixedLogger","lockServicer","checkLock","claimant","lastPingTime","lockHolder","timeAgo","serviceLock","onPagehideEvent","onStorageUpdate","storageUpdatePromise","sleepPromise","winner","StorageEvent","claimingSession","releaseLock","getNormalizedAppVersion","WebPlatform","_event$data","_event$data2","responseKey","showUpdate","showNoUpdate","getMostRecentVersion","mostRecentVersion","VERSION","registerServiceWorkerPromise","registerServiceWorker","handleServiceWorkerRegistrationError","registration","serviceWorker","onServiceWorkerPostMessage","requestPermission","pollForUpdate","parseQs","appName","osName","SessionLock","PWAPlatform","setAppBadge","mxSendRageshake","withLogs","rageshakePromise","initRageshake","preparePlatform","setupLogStorage","loadConfig","platformConfig","loadLanguage","prefLang","languageHandler","loadTheme","loadApp","fragParams","matrixChat","ErrorView","showIncompatibleBrowser","UnsupportedBrowserView","loadModules","INSTALLED_MODULES","InstalledModule","loadPlugins","moduleLoader","ModuleLoader","mxModuleLoader","import","existingRequest","findVerificationRequestDMInProgress","getDecryptionReasonFromCode","DecryptionFailureCode","HISTORICAL_MESSAGE_BACKUP_UNCONFIGURED","DecryptionFailureReason","HISTORICAL_MESSAGE_NO_KEY_BACKUP","HISTORICAL_MESSAGE_USER_NOT_JOINED","MEGOLM_KEY_WITHHELD_FOR_UNVERIFIED_DEVICE","SENDER_IDENTITY_PREVIOUSLY_VERIFIED","UNSIGNED_SENDER_DEVICE","UNABLE_TO_DECRYPT","isLocalDeviceVerified","_DecryptionFailureBodyViewModel","defaultClassNames","_discoveryResponse$JI","wkJitsiConfig","wkPreferredDomain","_useFor1To1Calls","getWidgetBuildUrl","widget_build_url","widget_build_url_ignore_dm","ignore_dm","widgetBuildUrl","widget_id","widgetContent","installedWidget","isManagedHybridWidget","fromString","knownMatch","_WidgetType","zh","_isDisposed","isDisposed","throwIfDisposed","Bh","Fh","k8","subs","subscribe","getSnapshot","R8","Cf","globalThis","g","Nf","__esModule","prototype","Lc","si","Lh","$h","Uh","Gh","gap","wrap","Hc","Hr","Jn","Uc","$$typeof","jsx","jsxs","Xh","xf","nm","zf","rm","im","Bf","Pe","am","sm","Ce","Et","TypeError","Ks","ur","RangeError","Jd","ke","qe","lr","kn","St","configurable","writable","cm","Qa","toStringTag","zn","Ao","Ff","Ze","Kc","Df","qf","Gc","br","so","Bt","vt","ar","qt","Io","Xa","trunc","$r","Lf","ut","se","jo","Hf","es","gt","Kf","Uf","$f","_r","K0","Jt","D0","q0","ns","U0","Te","rs","$0","Gf","H0","L0","je","os","Vc","Rn","an","ct","Le","Vf","co","lt","ss","cs","gr","mr","isoYear","Ve","ze","Be","isoHour","dt","_e","isoDay","isoNanosecond","jg","Ig","Qt","Lt","Xe","Oo","Yc","Oe","Bn","isoMonth","isoMinute","isoSecond","isoMillisecond","xe","Ot","isoMicrosecond","jr","ls","lo","ap","Yf","valueOf","setUTCHours","setUTCFullYear","Fn","Po","rc","Zo","getUTCFullYear","getUTCMonth","getUTCDate","getUTCHours","getUTCMinutes","getUTCSeconds","getUTCMilliseconds","us","fs","Wf","Zf","Ct","Jf","ds","Qf","Xf","getUTCDay","ed","Gn","Ut","kg","fm","Pg","era","eraYear","qd","ko","un","Dn","td","Wc","ec","te","wp","Ro","pt","Ep","qg","qn","_p","kr","Pr","gs","Mo","Co","go","ps","oc","nd","hs","od","sr","hi","No","Rg","ys","La","Sg","Xd","Gs","Gt","dg","It","branding","cc","epochNanoseconds","Je","Xt","calendar","Qe","Vn","Tg","jt","Rr","tc","fr","ic","uo","ht","sc","gp","be","lc","Vt","Js","vs","ad","Zc","we","bs","oe","_s","Kn","sd","cd","wr","ws","Ht","fo","Yo","ld","ud","Ag","wm","Hn","Bo","xo","pr","Mn","Sm","Em","Tm","Xs","zo","fd","$g","Qs","Lo","weeks","Jc","Es","Er","mn","Qc","Hg","Lg","Ss","Xc","po","tl","dd","pd","nl","Am","rl","hd","ci","dn","Re","vd","Ts","rn","years","months","Ye","gd","Wo","Gg","useGrouping","Im","offsetNanoseconds","Ln","ag","Sr","sg","ig","$t","il","bd","ug","al","sl","Is","Fo","ll","dr","Ps","Ee","ul","yd","$e","Do","js","qo","Os","Zm","Jm","fl","relativeTo","Vo","lg","Eg","El","isSafeInteger","cg","mp","km","ro","pn","Ns","Ne","ks","Yt","wd","Ed","Rs","bt","_d","Bs","$","Go","Sd","Qg","Td","Ad","Ho","Ms","Zg","Cs","Jg","ey","og","Pn","xs","zs","ty","padEnd","$n","Fs","iy","rp","oy","rg","resolvedOptions","ry","Id","jd","Od","Un","Ds","Pd","hl","$o","ml","Ko","Rd","gl","Md","yl","kd","vl","bl","qs","Cd","Nd","Uo","np","xd","zd","Ls","Hs","ay","tg","Tr","ho","$s","Bd","Fa","pp","Dd","Fd","vg","cn","Qm","Xm","e0","WeakMap","Og","Ld","hp","normalize","relatedYear","mo","hr","Hd","no","wl","Ur","_l","Kr","$d","Ar","tp","Ud","sy","t0","Wt","kt","lp","Ir","He","V0","G0","Sl","dp","Qd","hc","Kd","J0","Z0","X0","Q0","eg","Gr","monthCode","er","ng","ep","ui","fi","Gd","Qo","q","Vd","Yd","Wd","hn","Zt","Zd","Ny","x0","hg","Ft","Us","di","Da","Xn","Tl","qa","fg","pi","Cn","nanosecond","microsecond","millisecond","week","Pt","Ha","mg","sp","cp","$a","gg","Vs","Ys","Ws","Or","Zs","up","yg","fp","gregory","japanese","meiji","taisho","showa","heisei","reiwa","ethiopic","ethioaa","coptic","roc","buddhist","islamic","ah","indian","saka","persian","bce","ce","era0","era1","broc","minguo","chinese","dangi","hebrew","bg","wg","nc","yp","Ua","vp","mi","bp","constrain","Mg","compatible","earlier","later","Cg","use","prefer","Ng","never","critical","always","xg","zg","Bg","halfFloor","halfCeil","halfTrunc","halfExpand","halfEven","Fg","previous","Dg","Ug","Kg","Yg","Vg","nn","tn","uc","oo","Sp","fc","dc","Wg","Tp","Jo","Xg","ny","Ap","inLeapYear","monthsInYear","daysInMonth","daysInYear","dayOfYear","dayOfWeek","daysInWeek","ly","uy","weekOfYear","yearOfWeek","fy","py","hy","my","Dt","Mr","Ip","mc","gc","yc","vc","gy","yy","vy","_y","bc","wy","Ey","_c","Cr","wc","Sy","Ty","Ay","Iy","jy","Oy","Py","ky","Ry","My","Cy","jp","Op","xy","Pp","kp","Rp","Mp","Cp","en","jl","defineProperties","Me","Yn","Nr","Np","Xo","Ec","De","qm","ve","c0","Fm","tr","Mm","Nt","s0","Bm","Sc","wn","r0","Nm","Al","a0","zm","En","i0","xm","Sn","o0","Tn","n0","Cm","Il","Ka","An","Rm","zy","vo","Dy","getOwnPropertyDescriptors","By","Fy","Ky","pg","yo","xp","Tc","zp","qy","Ac","Ly","Hy","xr","calendarId","$y","Ic","Bp","epochMilliseconds","Uy","de","blank","with","m0","negated","Om","subtract","ie","jm","hm","DurationFormat","Hm","Instant","PlainDateTime","PlainDate","PlainTime","PlainYearMonth","PlainMonthDay","Gy","Vy","Yy","Wy","Zy","Jy","Qy","Xy","zt","h0","until","equals","Wm","ot","u0","withCalendar","withPlainTime","B0","ym","Km","toZonedDateTime","Ie","I0","toPlainDate","toPlainTime","tv","Ga","p0","Ym","M0","nv","ir","d0","Vm","R0","rv","f0","Gm","plainTime","j0","toPlainDateTime","O0","toPlainYearMonth","P0","toPlainMonthDay","k0","ov","timeZoneId","hoursInDay","bm","l0","withTimeZone","F0","z0","gm","startOfDay","_m","Um","toInstant","xt","A0","getTimeZoneTransition","dm","mm","$m","toZonedDateTimeISO","T0","fromEpochMilliseconds","C0","fromEpochNanoseconds","N0","av","instant","zonedDateTimeISO","plainDateTimeISO","plainDateISO","plainTimeISO","sv","ZonedDateTime","Duration","Now","cv","lv","Ol","smallestUnit","largestUnit","uv","Fp","fv","et","Function","Ue","Dp","pv","nr","gv","Pl","gn","hv","yv","Tt","ei","qp","At","kl","Rl","Lp","wv","Sv","Tv","Ev","Kt","Av","Iv","jv","Ov","Cl","Hp","gi","Nl","IE_PROTO","zv","yn","Fv","Dv","qv","Lv","Hv","$v","Uv","Nv","vn","Kv","Va","Wv","Jv","bo","Qv","enumerable","Xv","Zv","n2","$p","jc","i2","Up","xl","Kp","Gp","l2","Vp","zl","Yp","d2","propertyIsEnumerable","Wp","Zp","Bl","Fl","Buffer","_o","isBuffer","re","Oc","Jp","cr","yi","Nn","Dl","isTypedArray","Qp","U2","Xp","u2","e1","K2","V2","W2","Y2","Q2","X2","Z2","eb","tb","nb","yr","fb","ln","ti","__data__","yb","Rt","vr","ni","Sb","Mt","Pc","Cache","Rb","Mb","Cb","kb","kc","rb","Nb","t1","Rc","ql","isConcatSpreadable","zb","Fb","Bb","n1","getPrototypeOf","Lb","Hb","$b","Ub","wt","Jb","o1","Ll","Hl","i1","allocUnsafe","r_","$l","getOwnPropertySymbols","t_","i_","s1","Ul","c1","Ya","Wa","Za","Kl","Gl","Vl","Yl","Wl","s_","c_","l_","u_","f_","Ge","ArrayBuffer","p_","wo","Mc","g_","Zl","Jl","D_","byteOffset","m_","b_","y_","v_","Ql","isMap","H_","Xl","isSet","K_","l1","u1","f1","ee","io","h_","e_","e2","Eo","vw","bw","d1","Ew","Sw","eu","vi","qw","tu","nu","Vr","ru","Uw","Bw","Lw","bi","Gw","Vw","Yw","maxWait","Zw","xb","Gb","Xw","e7","Ww","t7","Kb","i7","Gv","s2","Db","n7","l7","u7","s7","C8","onSeekbarChange","_i","N8","h1","h7","m1","g1","y1","ou","Yr","b7","v1","_7","wi","iu","Ti","au","Ai","su","Ii","cu","ji","lu","Oi","uu","Pi","fu","ki","du","Ri","pu","Mi","hu","Ci","mu","Ni","gu","xi","yu","zi","vu","Bi","bu","Fi","_u","Di","wu","qi","Eu","Li","Su","Hi","Tu","$i","Au","Iu","Ki","ju","Gi","Ou","Vi","Pu","Yi","ku","Wi","Ru","Zi","Mu","Ji","Cu","Qi","Nu","Xi","xu","ea","zu","Bu","na","Fu","ra","Du","oa","qu","ia","Lu","aa","Hu","sa","$u","ca","Uu","la","Ku","Gu","fa","Vu","da","Yu","pa","Wu","ha","Zu","Ei","Si","getOwnPropertyNames","getOwnPropertyDescriptor","ri","_1","E7","S7","EvalError","T7","A7","ReferenceError","w1","SyntaxError","zr","I7","URIError","j7","O7","P7","k7","R7","M7","C7","N7","x7","Wn","oi","defineProperty","E1","Reflect","S1","Br","B7","Cc","Nc","T1","xc","D7","__proto__","zc","A1","I1","z7","Atomics","BigInt64Array","BigUint64Array","decodeURI","eval","Float16Array","Float32Array","Float64Array","FinalizationRegistry","Int8Array","Int16Array","Int32Array","Proxy","SharedArrayBuffer","Uint8ClampedArray","Uint16Array","Uint32Array","WeakRef","ue","ne","le","he","ge","Ke","ye","bn","Zn","Dr","qr","Lr","Fr","q7","callee","isLegacyArguments","H7","toPrimitive","L7","$7","G7","K7","V7","Y7","ga","Ju","ya","Qu","va","Xu","ba","ef","tf","_a","nf","wa","rf","Ea","af","ma","W7","Z7","hasArrayLengthDefineBug","J7","X7","Q7","j1","e3","t3","U7","working","isArgumentsObject","isGeneratorFunction","isPromise","isArrayBufferView","isView","isUint8Array","isUint8ClampedArray","isUint16Array","isUint32Array","isInt8Array","isInt16Array","isInt32Array","isFloat32Array","isFloat64Array","isBigInt64Array","isBigUint64Array","isWeakMap","isWeakSet","isArrayBuffer","isDataView","isSharedArrayBuffer","isAsyncFunction","isMapIterator","isSetIterator","isGeneratorObject","isWebAssemblyCompiledModule","isNumberObject","isStringObject","isBooleanObject","isBigIntObject","isSymbolObject","isBoxedPrimitive","isAnyArrayBuffer","sf","cf","Wr","lf","deprecate","noDeprecation","throwDeprecation","traceDeprecation","env","NODE_DEBUG","stylize","showHidden","_extend","customInspect","styles","inspect","toUTCString","pid","italic","underline","inverse","white","grey","black","cyan","magenta","yellow","special","boolean","null","regexp","isBoolean","isNull","isNumber","isString","isSymbol","isUndefined","isRegExp","isDate","isNativeError","isFunction","isPrimitive","readUInt8","getHours","getMinutes","inherits","super_","promisify","setPrototypeOf","callbackify","nextTick","uf","Sa","Ta","df","Aa","pf","Ia","hf","ja","mf","Oa","gf","Pa","yf","ka","vf","Ra","bf","Zr","i3","ownKeys","_events","_eventsCount","_maxListeners","defaultMaxListeners","newListener","warned","fired","wrapFn","getMaxListeners","prependListener","prependOnceListener","rawListeners","listenerCount","eventNames","s3","a3","O1","__locale","abbreviated_days","abbreviated_months","pm","l3","getTimezoneOffset","p3","w7","not_string","not_json","modulo","key_access","index_access","toExponential","toPrecision","sprintf","vsprintf","_registry","interpolate","fallbackLocales","interpolations","normalizedKeys","separator","keepTrailingDot","keyTransformer","generateMissingEntry","counterpart","pluralize","long","short","datetime","getFallbackLocale","setFallbackLocale","getAvailableLocales","availableLocales","setAvailableLocales","getSeparator","setSeparator","setInterpolate","getInterpolate","setKeyTransformer","getKeyTransformer","setMissingEntryGenerator","getMissingEntryGenerator","registerInterpolations","onLocaleChange","addLocaleChangeListener","offLocaleChange","removeLocaleChangeListener","onTranslationNotFound","addTranslationNotFoundListener","offTranslationNotFound","removeTranslationNotFoundListener","addErrorListener","offError","removeErrorListener","substr","fallbackLocale","_normalizeKeys","_fallback","_pluralize","_interpolate","localize","withLocale","withScope","withSeparator","_normalizeKey","_resolve","Instance","Translator","d3","We","P1","h3","m3","z8","B8","_f","Bc","translated","isFallback","g3","R1","M1","F8","D8","q8","wf","v3","rr","_3","translated_descriptions","Jr","H8","w3","Ma","$8","U8","C1","P3","N1","Ef","x1","z1","B1","F1","D1","q1","L1","k3","H1","$1","U1","R3","K1","M3","G1","C3","V1","N3","Y1","x3","W1","z3","Z1","B3","J1","F3","Q1","D3","X1","q3","eh","L3","th","H3","nh","rh","oh","$3","ih","Fc","U3","sh","Sf","ch","lh","uh","K3","fh","G3","dh","ph","hh","V3","mh","Y3","gh","W3","yh","Z3","vh","J3","So","tE","K8","rE","nE","G8","formattedSenders","iE","V8","Tf","Y8","Ja","uE","Ca","W8","fE","nt","ConnectionLost","NeedsConsent","ResourceLimited","UnsentMessages","LocalRoomFailed","Z8","onDeleteAllClick","onResendAllClick","onRetryRoomCreationClick","onTermsAndConditionsClicked","consentUri","adminContactHref","monthly_active_user","hs_disabled","resourceLimit","isResending","Na","J8","colorClass","displayIdentifier","emphasizeDisplayName","mx_DisambiguatedProfile_displayName","Q8","jn","X8","IE","humanizeTime","Qr","e5","listRef","nextElementSibling","previousElementSibling","RE","CE","NE","activeSortOption","isMessagePreviewEnabled","toggleMessagePreview","zE","BE","canInviteInSpace","canAccessSpaceSettings","openSpaceHome","hideChevron","inviteInSpace","openSpacePreferences","openSpaceSettings","FE","canCreateRoom","canCreateVideoRoom","createChatRoom","createVideoRoom","xa","t5","displaySpaceMenu","displayComposeMenu","Xr","n5","displayExploreButton","displayDialButton","searchShortcut","iconOnly","onDialPadClick","onExploreClick","za","QE","filterIds","activeFilterId","onToggleFilter","isWrapping","wrappingIndex","offsetLeft","GE","VE","JE","e8","t8","ao","a8","eo","s8","c8","bh","canMarkAsRead","onMarkAsRead","canMarkAsUnread","onMarkAsUnread","isFavourite","onToggleFavorite","onToggleLowPriority","onInvite","canCopyRoomLink","onCopyRoomLink","onLeaveRoom","Ae","l8","roomNotifState","onSetRoomNotifState","rt","b8","showMoreOptionsMenu","showNotificationMenu","_8","hasAccessibleAlternative","E8","roomCount","renderAvatar","preventScroll","w8","isBold","mx_RoomListItemView_selected","onOpenRoom","In","T8","getItemComponent","isItemFocusable","getItemKey","rangeChanged","S8","endIndex","tabIndexKey","scrollerRef","overscan","itemContent","A8","roomListState","activeRoomIndex","updateVisibleRooms","getRoomItemViewModel","filterKeys","Jw","scrollIntoViewOnChange","initialTopMostItemIndex","fixedItemHeight","increaseViewportBy","r5","isRoomListEmpty","Ba","o5","flex","shrink","grow","i5","showStreamAudioStreamButton","showEditButton","showSnapshotButton","showDeleteButton","showRevokeButton","showMoveButtons","isMenuOpened","onStreamAudioClick","onSnapshotClick","onDeleteClick","onRevokeClick","onMoveButton","inert","side","I8","a5","s5","c5","l5","u5","f5"],"sourceRoot":""}