Knock Requests List Screen (#3533)

* created the basic navigation and files

* updated the logic

so that the buttons that do not have permissions won't show

* added the empty state

* progress in making the list UI

* update tests

* UI improvements

* fixed an issue with media provider

* update button style

* fixed a navigation bug

* pr suggestions

* pr suggestions
This commit is contained in:
Mauro
2024-11-21 20:14:05 +01:00
committed by GitHub
parent 7e1476d973
commit e315451448
85 changed files with 701 additions and 145 deletions
+28
View File
@@ -30,6 +30,7 @@
024E70451A7CD9E4E034D8A9 /* VoiceMessageRoomTimelineItem.swift in Sources */ = {isa = PBXBuildFile; fileRef = D529B976F8B2AA654D923422 /* VoiceMessageRoomTimelineItem.swift */; }; 024E70451A7CD9E4E034D8A9 /* VoiceMessageRoomTimelineItem.swift in Sources */ = {isa = PBXBuildFile; fileRef = D529B976F8B2AA654D923422 /* VoiceMessageRoomTimelineItem.swift */; };
02A92F8F4538CECDFB4F2607 /* RoomDirectorySearchScreenCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1562EAF6231151A675BED7A9 /* RoomDirectorySearchScreenCoordinator.swift */; }; 02A92F8F4538CECDFB4F2607 /* RoomDirectorySearchScreenCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1562EAF6231151A675BED7A9 /* RoomDirectorySearchScreenCoordinator.swift */; };
02D8DF8EB7537EB4E9019DDB /* EventBasedTimelineItemProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 218AB05B4E3889731959C5F1 /* EventBasedTimelineItemProtocol.swift */; }; 02D8DF8EB7537EB4E9019DDB /* EventBasedTimelineItemProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 218AB05B4E3889731959C5F1 /* EventBasedTimelineItemProtocol.swift */; };
0307469D99B5FE6C7043AE39 /* KnockRequestsListScreenCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = C9E8A8EC299E12490588B07C /* KnockRequestsListScreenCoordinator.swift */; };
037006FB6DF1374F94E4058D /* Dictionary.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFDCAC6CAAD65A2C24EA9C4B /* Dictionary.swift */; }; 037006FB6DF1374F94E4058D /* Dictionary.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFDCAC6CAAD65A2C24EA9C4B /* Dictionary.swift */; };
038AB2E86960FD240231D4C2 /* GeneratedPreviewTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 95A2E4BD7C0CAD25EF924A4C /* GeneratedPreviewTests.swift */; }; 038AB2E86960FD240231D4C2 /* GeneratedPreviewTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 95A2E4BD7C0CAD25EF924A4C /* GeneratedPreviewTests.swift */; };
03BD83E8BDD23AE059802E0D /* UITestsScreenIdentifier.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6CEBE5EA91E8691EDF364EC2 /* UITestsScreenIdentifier.swift */; }; 03BD83E8BDD23AE059802E0D /* UITestsScreenIdentifier.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6CEBE5EA91E8691EDF364EC2 /* UITestsScreenIdentifier.swift */; };
@@ -548,6 +549,7 @@
755727E0B756430DFFEC4732 /* SessionVerificationViewModelTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = DF05DA24F71B455E8EFEBC3B /* SessionVerificationViewModelTests.swift */; }; 755727E0B756430DFFEC4732 /* SessionVerificationViewModelTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = DF05DA24F71B455E8EFEBC3B /* SessionVerificationViewModelTests.swift */; };
756EA0D663261889EF64E6D4 /* VoiceMessageRecordingView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5E9CBF577B9711CFBB4FA40D /* VoiceMessageRecordingView.swift */; }; 756EA0D663261889EF64E6D4 /* VoiceMessageRecordingView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5E9CBF577B9711CFBB4FA40D /* VoiceMessageRecordingView.swift */; };
7573D682F089205F7F1D96CF /* SessionDirectories.swift in Sources */ = {isa = PBXBuildFile; fileRef = 43C2067FF58B4996323EB40C /* SessionDirectories.swift */; }; 7573D682F089205F7F1D96CF /* SessionDirectories.swift in Sources */ = {isa = PBXBuildFile; fileRef = 43C2067FF58B4996323EB40C /* SessionDirectories.swift */; };
75ED4B73983228BB6922CE3C /* KnockRequestsListScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6A5C217DD0749EC709EED028 /* KnockRequestsListScreenViewModelProtocol.swift */; };
762DAF94846C7AC8550F1CC1 /* MediaPlayerProviderProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = F5E23D8EE6CBACF32F1EC874 /* MediaPlayerProviderProtocol.swift */; }; 762DAF94846C7AC8550F1CC1 /* MediaPlayerProviderProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = F5E23D8EE6CBACF32F1EC874 /* MediaPlayerProviderProtocol.swift */; };
762DB0973865293F0C3D3D7B /* SessionVerificationScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = A7D452AF7B5F7E3A0A7DB54C /* SessionVerificationScreenViewModelProtocol.swift */; }; 762DB0973865293F0C3D3D7B /* SessionVerificationScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = A7D452AF7B5F7E3A0A7DB54C /* SessionVerificationScreenViewModelProtocol.swift */; };
763D69741D58D2B650BC1FC9 /* CallScreenCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = F37FA1A5D55633E1942B153B /* CallScreenCoordinator.swift */; }; 763D69741D58D2B650BC1FC9 /* CallScreenCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = F37FA1A5D55633E1942B153B /* CallScreenCoordinator.swift */; };
@@ -755,6 +757,7 @@
9DE801D278AC34737467F937 /* VoiceMessageMediaManagerProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 889DEDD63C68ABDA8AD29812 /* VoiceMessageMediaManagerProtocol.swift */; }; 9DE801D278AC34737467F937 /* VoiceMessageMediaManagerProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 889DEDD63C68ABDA8AD29812 /* VoiceMessageMediaManagerProtocol.swift */; };
9E838A62918E47BC72D6640D /* UserIndicatorPresenter.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6AB54B4F94686CCF0289B72F /* UserIndicatorPresenter.swift */; }; 9E838A62918E47BC72D6640D /* UserIndicatorPresenter.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6AB54B4F94686CCF0289B72F /* UserIndicatorPresenter.swift */; };
9EBDC79CAC9B63A0D626E333 /* LegalInformationScreenCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5EB2CAA266B921D128C35710 /* LegalInformationScreenCoordinator.swift */; }; 9EBDC79CAC9B63A0D626E333 /* LegalInformationScreenCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5EB2CAA266B921D128C35710 /* LegalInformationScreenCoordinator.swift */; };
9EE71509E6E7519A2B2388B3 /* KnockRequestsListScreenModels.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8BD9C9A31D9AB3B6D8128E69 /* KnockRequestsListScreenModels.swift */; };
9EF9773DBE3F6497A25CE236 /* test_apple_image.heic in Resources */ = {isa = PBXBuildFile; fileRef = F6B676B4866F5B383DE819B2 /* test_apple_image.heic */; }; 9EF9773DBE3F6497A25CE236 /* test_apple_image.heic in Resources */ = {isa = PBXBuildFile; fileRef = F6B676B4866F5B383DE819B2 /* test_apple_image.heic */; };
9F11B9F347F9E2D236799FB3 /* ElementCallServiceConstants.swift in Sources */ = {isa = PBXBuildFile; fileRef = 406C90AF8C3E98DF5D4E5430 /* ElementCallServiceConstants.swift */; }; 9F11B9F347F9E2D236799FB3 /* ElementCallServiceConstants.swift in Sources */ = {isa = PBXBuildFile; fileRef = 406C90AF8C3E98DF5D4E5430 /* ElementCallServiceConstants.swift */; };
9F11E743EA01482E78A438B0 /* GlobalSearchScreenCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 22DB19219E6CC4D002E15D48 /* GlobalSearchScreenCell.swift */; }; 9F11E743EA01482E78A438B0 /* GlobalSearchScreenCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 22DB19219E6CC4D002E15D48 /* GlobalSearchScreenCell.swift */; };
@@ -765,6 +768,7 @@
A009BDFB0A6816D4C392ADCB /* SettingsScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2AF715D4FD4710EBB637D661 /* SettingsScreenViewModelProtocol.swift */; }; A009BDFB0A6816D4C392ADCB /* SettingsScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 2AF715D4FD4710EBB637D661 /* SettingsScreenViewModelProtocol.swift */; };
A021827B528F1EDC9101CA58 /* AppCoordinatorProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = FBC776F301D374A3298C69DA /* AppCoordinatorProtocol.swift */; }; A021827B528F1EDC9101CA58 /* AppCoordinatorProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = FBC776F301D374A3298C69DA /* AppCoordinatorProtocol.swift */; };
A0601810597769B81C2358AF /* EncryptionResetPasswordScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4A2B5274C1D3D2999D643786 /* EncryptionResetPasswordScreenViewModelProtocol.swift */; }; A0601810597769B81C2358AF /* EncryptionResetPasswordScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4A2B5274C1D3D2999D643786 /* EncryptionResetPasswordScreenViewModelProtocol.swift */; };
A0861B727B273B5B3DD7FBF6 /* KnockRequestsListScreenViewModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = D09227E671DB30795C43FFFD /* KnockRequestsListScreenViewModel.swift */; };
A0868BDE84D2140A885BE3C9 /* EncryptionResetScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7E8562F4D7DE073BC32902AB /* EncryptionResetScreenViewModelProtocol.swift */; }; A0868BDE84D2140A885BE3C9 /* EncryptionResetScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7E8562F4D7DE073BC32902AB /* EncryptionResetScreenViewModelProtocol.swift */; };
A0D7E5BD0298A97DCBDCE40B /* Emojibase in Frameworks */ = {isa = PBXBuildFile; productRef = C05729B1684C331F5FFE9232 /* Emojibase */; }; A0D7E5BD0298A97DCBDCE40B /* Emojibase in Frameworks */ = {isa = PBXBuildFile; productRef = C05729B1684C331F5FFE9232 /* Emojibase */; };
A10D6CCDE2010C09EEA1A593 /* HomeScreenRoomList.swift in Sources */ = {isa = PBXBuildFile; fileRef = C7661EFFCAA307A97D71132A /* HomeScreenRoomList.swift */; }; A10D6CCDE2010C09EEA1A593 /* HomeScreenRoomList.swift in Sources */ = {isa = PBXBuildFile; fileRef = C7661EFFCAA307A97D71132A /* HomeScreenRoomList.swift */; };
@@ -802,6 +806,7 @@
A6F345328CCC5C9B0DAE2257 /* LogViewerScreenViewModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0BB05221D7D941CC82DC8480 /* LogViewerScreenViewModel.swift */; }; A6F345328CCC5C9B0DAE2257 /* LogViewerScreenViewModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0BB05221D7D941CC82DC8480 /* LogViewerScreenViewModel.swift */; };
A722F426FD81FC67706BB1E0 /* CustomLayoutLabelStyle.swift in Sources */ = {isa = PBXBuildFile; fileRef = 42236480CF0431535EBE8387 /* CustomLayoutLabelStyle.swift */; }; A722F426FD81FC67706BB1E0 /* CustomLayoutLabelStyle.swift in Sources */ = {isa = PBXBuildFile; fileRef = 42236480CF0431535EBE8387 /* CustomLayoutLabelStyle.swift */; };
A74438ED16F8683A4B793E6A /* AnalyticsSettingsScreenViewModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0BCE3FAF40932AC7C7639AC4 /* AnalyticsSettingsScreenViewModel.swift */; }; A74438ED16F8683A4B793E6A /* AnalyticsSettingsScreenViewModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0BCE3FAF40932AC7C7639AC4 /* AnalyticsSettingsScreenViewModel.swift */; };
A756F17A2CEDFF9700128047 /* KnockRequestsListEmptyStateView.swift in Sources */ = {isa = PBXBuildFile; fileRef = A756F1792CEDFF7300128047 /* KnockRequestsListEmptyStateView.swift */; };
A7D48E44D485B143AADDB77D /* Strings+Untranslated.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1A18F6CE4D694D21E4EA9B25 /* Strings+Untranslated.swift */; }; A7D48E44D485B143AADDB77D /* Strings+Untranslated.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1A18F6CE4D694D21E4EA9B25 /* Strings+Untranslated.swift */; };
A808DC3F72D15C6C5A52317E /* TimelineItemDebugView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BCDA016D05107DED3B9495CB /* TimelineItemDebugView.swift */; }; A808DC3F72D15C6C5A52317E /* TimelineItemDebugView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BCDA016D05107DED3B9495CB /* TimelineItemDebugView.swift */; };
A816F7087C495D85048AC50E /* RoomMemberDetailsScreenModels.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1B6E30BB748F3F480F077969 /* RoomMemberDetailsScreenModels.swift */; }; A816F7087C495D85048AC50E /* RoomMemberDetailsScreenModels.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1B6E30BB748F3F480F077969 /* RoomMemberDetailsScreenModels.swift */; };
@@ -816,6 +821,7 @@
AA050DF4AEE54A641BA7CA22 /* RoomSummaryProviderProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 10CC626F97AD70FF0420C115 /* RoomSummaryProviderProtocol.swift */; }; AA050DF4AEE54A641BA7CA22 /* RoomSummaryProviderProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 10CC626F97AD70FF0420C115 /* RoomSummaryProviderProtocol.swift */; };
AA5924D3B67F7ACD98BBEFDC /* OrientationManagerProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = C4756240773D26AB74C22668 /* OrientationManagerProtocol.swift */; }; AA5924D3B67F7ACD98BBEFDC /* OrientationManagerProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = C4756240773D26AB74C22668 /* OrientationManagerProtocol.swift */; };
AA93B3F9B5DD097DEF79F981 /* NotificationSettingsEditScreen.swift in Sources */ = {isa = PBXBuildFile; fileRef = FBB0328F2887BF0A65BC5D49 /* NotificationSettingsEditScreen.swift */; }; AA93B3F9B5DD097DEF79F981 /* NotificationSettingsEditScreen.swift in Sources */ = {isa = PBXBuildFile; fileRef = FBB0328F2887BF0A65BC5D49 /* NotificationSettingsEditScreen.swift */; };
AAA551AD8768309024D4907B /* KnockRequestsListScreen.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1511B1DCECC0DC75EB267328 /* KnockRequestsListScreen.swift */; };
AADE7C2497A7B55D8BED7BD6 /* IdentityConfirmedScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8319173DD66C07F45DC48848 /* IdentityConfirmedScreenViewModelProtocol.swift */; }; AADE7C2497A7B55D8BED7BD6 /* IdentityConfirmedScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8319173DD66C07F45DC48848 /* IdentityConfirmedScreenViewModelProtocol.swift */; };
AAF0BBED840DF4A53EE85E77 /* MatrixRustSDK in Frameworks */ = {isa = PBXBuildFile; productRef = C2C69B8BA5A9702E7A8BC08F /* MatrixRustSDK */; }; AAF0BBED840DF4A53EE85E77 /* MatrixRustSDK in Frameworks */ = {isa = PBXBuildFile; productRef = C2C69B8BA5A9702E7A8BC08F /* MatrixRustSDK */; };
ABD29E06DD1224812E750AF8 /* ReadReceiptCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 3D75941CBD7D336F831924EC /* ReadReceiptCell.swift */; }; ABD29E06DD1224812E750AF8 /* ReadReceiptCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 3D75941CBD7D336F831924EC /* ReadReceiptCell.swift */; };
@@ -880,6 +886,7 @@
B9CB30FED3E29D2036EA3FCC /* DeveloperOptionsScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 54C4E7B46099462F12000C91 /* DeveloperOptionsScreenViewModelProtocol.swift */; }; B9CB30FED3E29D2036EA3FCC /* DeveloperOptionsScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 54C4E7B46099462F12000C91 /* DeveloperOptionsScreenViewModelProtocol.swift */; };
BA31448FBD9697F8CB9A83CD /* ImageCache.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4E2245243369B99216C7D84E /* ImageCache.swift */; }; BA31448FBD9697F8CB9A83CD /* ImageCache.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4E2245243369B99216C7D84E /* ImageCache.swift */; };
BA43D782BE85C7F5F20C624A /* AttributedStringBuilderProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72F37B5DA798C9AE436F2C2C /* AttributedStringBuilderProtocol.swift */; }; BA43D782BE85C7F5F20C624A /* AttributedStringBuilderProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 72F37B5DA798C9AE436F2C2C /* AttributedStringBuilderProtocol.swift */; };
BA48D6AFF6421D199148C0A1 /* KnockRequestsListScreenViewModelTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = C9AC2CC94FA06F728883B694 /* KnockRequestsListScreenViewModelTests.swift */; };
BA4C9049BC96DED3A2F3B82E /* RoomNotificationSettingsScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 03DD998E523D4EC93C7ED703 /* RoomNotificationSettingsScreenViewModelProtocol.swift */; }; BA4C9049BC96DED3A2F3B82E /* RoomNotificationSettingsScreenViewModelProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 03DD998E523D4EC93C7ED703 /* RoomNotificationSettingsScreenViewModelProtocol.swift */; };
BAC845780F17CCFBC5A9CA37 /* AppLockUITests.swift in Sources */ = {isa = PBXBuildFile; fileRef = F733F135E6D67BBBEB76CC30 /* AppLockUITests.swift */; }; BAC845780F17CCFBC5A9CA37 /* AppLockUITests.swift in Sources */ = {isa = PBXBuildFile; fileRef = F733F135E6D67BBBEB76CC30 /* AppLockUITests.swift */; };
BB04B1D8E7401C90506D401E /* QRCodeLoginServiceProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 536C0E2178949B290776EA4E /* QRCodeLoginServiceProtocol.swift */; }; BB04B1D8E7401C90506D401E /* QRCodeLoginServiceProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 536C0E2178949B290776EA4E /* QRCodeLoginServiceProtocol.swift */; };
@@ -1358,6 +1365,7 @@
13BE9781699FB510E9263192 /* AppSettingsHook.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppSettingsHook.swift; sourceTree = "<group>"; }; 13BE9781699FB510E9263192 /* AppSettingsHook.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppSettingsHook.swift; sourceTree = "<group>"; };
1423AB065857FA546444DB15 /* NotificationManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NotificationManager.swift; sourceTree = "<group>"; }; 1423AB065857FA546444DB15 /* NotificationManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NotificationManager.swift; sourceTree = "<group>"; };
1454CF3AABD242F55C8A2615 /* InviteUsersScreenModels.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = InviteUsersScreenModels.swift; sourceTree = "<group>"; }; 1454CF3AABD242F55C8A2615 /* InviteUsersScreenModels.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = InviteUsersScreenModels.swift; sourceTree = "<group>"; };
1511B1DCECC0DC75EB267328 /* KnockRequestsListScreen.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KnockRequestsListScreen.swift; sourceTree = "<group>"; };
1562EAF6231151A675BED7A9 /* RoomDirectorySearchScreenCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RoomDirectorySearchScreenCoordinator.swift; sourceTree = "<group>"; }; 1562EAF6231151A675BED7A9 /* RoomDirectorySearchScreenCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RoomDirectorySearchScreenCoordinator.swift; sourceTree = "<group>"; };
15748C254911E3654C93B0ED /* MentionBuilder.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MentionBuilder.swift; sourceTree = "<group>"; }; 15748C254911E3654C93B0ED /* MentionBuilder.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MentionBuilder.swift; sourceTree = "<group>"; };
1575947B7A6FE08C57FE5EE4 /* NetworkMonitorProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NetworkMonitorProtocol.swift; sourceTree = "<group>"; }; 1575947B7A6FE08C57FE5EE4 /* NetworkMonitorProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NetworkMonitorProtocol.swift; sourceTree = "<group>"; };
@@ -1747,6 +1755,7 @@
69CB8242D69B7E4D0B32E18D /* AggregatedReactionMock.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AggregatedReactionMock.swift; sourceTree = "<group>"; }; 69CB8242D69B7E4D0B32E18D /* AggregatedReactionMock.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AggregatedReactionMock.swift; sourceTree = "<group>"; };
69D42EE0102D2857933625DD /* CreateRoomViewModelTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CreateRoomViewModelTests.swift; sourceTree = "<group>"; }; 69D42EE0102D2857933625DD /* CreateRoomViewModelTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CreateRoomViewModelTests.swift; sourceTree = "<group>"; };
6A580295A56B55A856CC4084 /* InfoPlistReader.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = InfoPlistReader.swift; sourceTree = "<group>"; }; 6A580295A56B55A856CC4084 /* InfoPlistReader.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = InfoPlistReader.swift; sourceTree = "<group>"; };
6A5C217DD0749EC709EED028 /* KnockRequestsListScreenViewModelProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KnockRequestsListScreenViewModelProtocol.swift; sourceTree = "<group>"; };
6A8E19C4645D3F5F9FB02355 /* UnitTestsAppCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UnitTestsAppCoordinator.swift; sourceTree = "<group>"; }; 6A8E19C4645D3F5F9FB02355 /* UnitTestsAppCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UnitTestsAppCoordinator.swift; sourceTree = "<group>"; };
6AB54B4F94686CCF0289B72F /* UserIndicatorPresenter.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UserIndicatorPresenter.swift; sourceTree = "<group>"; }; 6AB54B4F94686CCF0289B72F /* UserIndicatorPresenter.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UserIndicatorPresenter.swift; sourceTree = "<group>"; };
6AD1A853D605C2146B0DC028 /* MatrixEntityRegex.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MatrixEntityRegex.swift; sourceTree = "<group>"; }; 6AD1A853D605C2146B0DC028 /* MatrixEntityRegex.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MatrixEntityRegex.swift; sourceTree = "<group>"; };
@@ -1893,6 +1902,7 @@
8AE78FA0011E07920AE83135 /* PlainMentionBuilder.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PlainMentionBuilder.swift; sourceTree = "<group>"; }; 8AE78FA0011E07920AE83135 /* PlainMentionBuilder.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PlainMentionBuilder.swift; sourceTree = "<group>"; };
8AFCE895ECFFA53FEE64D62B /* MediaLoader.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MediaLoader.swift; sourceTree = "<group>"; }; 8AFCE895ECFFA53FEE64D62B /* MediaLoader.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MediaLoader.swift; sourceTree = "<group>"; };
8BCCE3D12B0A9C6E559B5B5A /* EmojiProviderProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = EmojiProviderProtocol.swift; sourceTree = "<group>"; }; 8BCCE3D12B0A9C6E559B5B5A /* EmojiProviderProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = EmojiProviderProtocol.swift; sourceTree = "<group>"; };
8BD9C9A31D9AB3B6D8128E69 /* KnockRequestsListScreenModels.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KnockRequestsListScreenModels.swift; sourceTree = "<group>"; };
8BEBF0E59F25E842EDB6FD11 /* LocationSharingScreenModels.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LocationSharingScreenModels.swift; sourceTree = "<group>"; }; 8BEBF0E59F25E842EDB6FD11 /* LocationSharingScreenModels.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LocationSharingScreenModels.swift; sourceTree = "<group>"; };
8C44BBC892499BE45B074F89 /* AppLockScreenCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppLockScreenCoordinator.swift; sourceTree = "<group>"; }; 8C44BBC892499BE45B074F89 /* AppLockScreenCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppLockScreenCoordinator.swift; sourceTree = "<group>"; };
8C8616254EE40CA8BA5E9BC2 /* VideoRoomTimelineItemContent.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = VideoRoomTimelineItemContent.swift; sourceTree = "<group>"; }; 8C8616254EE40CA8BA5E9BC2 /* VideoRoomTimelineItemContent.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = VideoRoomTimelineItemContent.swift; sourceTree = "<group>"; };
@@ -2007,6 +2017,7 @@
A6C11AD9813045E44F950410 /* ElementCallWidgetDriverProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ElementCallWidgetDriverProtocol.swift; sourceTree = "<group>"; }; A6C11AD9813045E44F950410 /* ElementCallWidgetDriverProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ElementCallWidgetDriverProtocol.swift; sourceTree = "<group>"; };
A6EA0D8B0BBD8805F7D5A133 /* TextBasedRoomTimelineViewProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TextBasedRoomTimelineViewProtocol.swift; sourceTree = "<group>"; }; A6EA0D8B0BBD8805F7D5A133 /* TextBasedRoomTimelineViewProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TextBasedRoomTimelineViewProtocol.swift; sourceTree = "<group>"; };
A73A07BAEDD74C48795A996A /* AsyncSequence.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AsyncSequence.swift; sourceTree = "<group>"; }; A73A07BAEDD74C48795A996A /* AsyncSequence.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AsyncSequence.swift; sourceTree = "<group>"; };
A756F1792CEDFF7300128047 /* KnockRequestsListEmptyStateView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KnockRequestsListEmptyStateView.swift; sourceTree = "<group>"; };
A7978C9EFBDD7DE39BD86726 /* RestorationTokenTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RestorationTokenTests.swift; sourceTree = "<group>"; }; A7978C9EFBDD7DE39BD86726 /* RestorationTokenTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RestorationTokenTests.swift; sourceTree = "<group>"; };
A7C4EA55DA62F9D0F984A2AE /* CollapsibleTimelineItem.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CollapsibleTimelineItem.swift; sourceTree = "<group>"; }; A7C4EA55DA62F9D0F984A2AE /* CollapsibleTimelineItem.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CollapsibleTimelineItem.swift; sourceTree = "<group>"; };
A7D452AF7B5F7E3A0A7DB54C /* SessionVerificationScreenViewModelProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SessionVerificationScreenViewModelProtocol.swift; sourceTree = "<group>"; }; A7D452AF7B5F7E3A0A7DB54C /* SessionVerificationScreenViewModelProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SessionVerificationScreenViewModelProtocol.swift; sourceTree = "<group>"; };
@@ -2177,7 +2188,9 @@
C95ADE8D9527523572532219 /* hu */ = {isa = PBXFileReference; lastKnownFileType = text.plist.stringsdict; name = hu; path = hu.lproj/Localizable.stringsdict; sourceTree = "<group>"; }; C95ADE8D9527523572532219 /* hu */ = {isa = PBXFileReference; lastKnownFileType = text.plist.stringsdict; name = hu; path = hu.lproj/Localizable.stringsdict; sourceTree = "<group>"; };
C97F8963B14EB0AF3940DDBF /* NotificationSettingsEditScreenRoomCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NotificationSettingsEditScreenRoomCell.swift; sourceTree = "<group>"; }; C97F8963B14EB0AF3940DDBF /* NotificationSettingsEditScreenRoomCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NotificationSettingsEditScreenRoomCell.swift; sourceTree = "<group>"; };
C99FDEEB71173C4C6FA2734C /* UserSessionFlowCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UserSessionFlowCoordinator.swift; sourceTree = "<group>"; }; C99FDEEB71173C4C6FA2734C /* UserSessionFlowCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UserSessionFlowCoordinator.swift; sourceTree = "<group>"; };
C9AC2CC94FA06F728883B694 /* KnockRequestsListScreenViewModelTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KnockRequestsListScreenViewModelTests.swift; sourceTree = "<group>"; };
C9E535B3388755B65C34CD10 /* UnsupportedRoomTimelineView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UnsupportedRoomTimelineView.swift; sourceTree = "<group>"; }; C9E535B3388755B65C34CD10 /* UnsupportedRoomTimelineView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UnsupportedRoomTimelineView.swift; sourceTree = "<group>"; };
C9E8A8EC299E12490588B07C /* KnockRequestsListScreenCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KnockRequestsListScreenCoordinator.swift; sourceTree = "<group>"; };
C9F893F4A111CB7BA5C96949 /* AppLockSetupBiometricsScreenViewModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppLockSetupBiometricsScreenViewModel.swift; sourceTree = "<group>"; }; C9F893F4A111CB7BA5C96949 /* AppLockSetupBiometricsScreenViewModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppLockSetupBiometricsScreenViewModel.swift; sourceTree = "<group>"; };
CA28F29C9F93E93CC3C2C715 /* NavigationRootCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NavigationRootCoordinator.swift; sourceTree = "<group>"; }; CA28F29C9F93E93CC3C2C715 /* NavigationRootCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NavigationRootCoordinator.swift; sourceTree = "<group>"; };
CA29952595B804DA221A0C1D /* ComposerToolbarViewModelTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ComposerToolbarViewModelTests.swift; sourceTree = "<group>"; }; CA29952595B804DA221A0C1D /* ComposerToolbarViewModelTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ComposerToolbarViewModelTests.swift; sourceTree = "<group>"; };
@@ -2205,6 +2218,7 @@
D01FD1171FF40E34D707FD00 /* BigIcon.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = BigIcon.swift; sourceTree = "<group>"; }; D01FD1171FF40E34D707FD00 /* BigIcon.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = BigIcon.swift; sourceTree = "<group>"; };
D071F86CD47582B9196C9D16 /* UserDiscoverySection.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UserDiscoverySection.swift; sourceTree = "<group>"; }; D071F86CD47582B9196C9D16 /* UserDiscoverySection.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UserDiscoverySection.swift; sourceTree = "<group>"; };
D086854995173E897F993C26 /* AdvancedSettingsScreenViewModelProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AdvancedSettingsScreenViewModelProtocol.swift; sourceTree = "<group>"; }; D086854995173E897F993C26 /* AdvancedSettingsScreenViewModelProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AdvancedSettingsScreenViewModelProtocol.swift; sourceTree = "<group>"; };
D09227E671DB30795C43FFFD /* KnockRequestsListScreenViewModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KnockRequestsListScreenViewModel.swift; sourceTree = "<group>"; };
D09A267106B9585D3D0CFC0D /* ClientError.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ClientError.swift; sourceTree = "<group>"; }; D09A267106B9585D3D0CFC0D /* ClientError.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ClientError.swift; sourceTree = "<group>"; };
D0C2D52E36AD614B3C003EF6 /* RoomTimelineItemViewState.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RoomTimelineItemViewState.swift; sourceTree = "<group>"; }; D0C2D52E36AD614B3C003EF6 /* RoomTimelineItemViewState.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RoomTimelineItemViewState.swift; sourceTree = "<group>"; };
D1896F6288D80E1F3EFB3DF8 /* ka */ = {isa = PBXFileReference; lastKnownFileType = text.plist.stringsdict; name = ka; path = ka.lproj/Localizable.stringsdict; sourceTree = "<group>"; }; D1896F6288D80E1F3EFB3DF8 /* ka */ = {isa = PBXFileReference; lastKnownFileType = text.plist.stringsdict; name = ka; path = ka.lproj/Localizable.stringsdict; sourceTree = "<group>"; };
@@ -3990,6 +4004,7 @@
845DDBDE5A0887E73D38B826 /* InviteUsersViewModelTests.swift */, 845DDBDE5A0887E73D38B826 /* InviteUsersViewModelTests.swift */,
DE5127D6EA05B2E45D0A7D59 /* JoinRoomScreenViewModelTests.swift */, DE5127D6EA05B2E45D0A7D59 /* JoinRoomScreenViewModelTests.swift */,
FDB9C37196A4C79F24CE80C6 /* KeychainControllerTests.swift */, FDB9C37196A4C79F24CE80C6 /* KeychainControllerTests.swift */,
C9AC2CC94FA06F728883B694 /* KnockRequestsListScreenViewModelTests.swift */,
6E5725BC6C63604CB769145B /* LegalInformationScreenViewModelTests.swift */, 6E5725BC6C63604CB769145B /* LegalInformationScreenViewModelTests.swift */,
C070FD43DC6BF4E50217965A /* LocalizationTests.swift */, C070FD43DC6BF4E50217965A /* LocalizationTests.swift */,
3DC1943ADE6A62ED5129D7C8 /* LoggingTests.swift */, 3DC1943ADE6A62ED5129D7C8 /* LoggingTests.swift */,
@@ -5034,6 +5049,10 @@
BF0415BE807CA2BCFC210008 /* KnockRequestsListScreen */ = { BF0415BE807CA2BCFC210008 /* KnockRequestsListScreen */ = {
isa = PBXGroup; isa = PBXGroup;
children = ( children = (
C9E8A8EC299E12490588B07C /* KnockRequestsListScreenCoordinator.swift */,
8BD9C9A31D9AB3B6D8128E69 /* KnockRequestsListScreenModels.swift */,
D09227E671DB30795C43FFFD /* KnockRequestsListScreenViewModel.swift */,
6A5C217DD0749EC709EED028 /* KnockRequestsListScreenViewModelProtocol.swift */,
F2BBD71E8BF13D2DD2A19064 /* View */, F2BBD71E8BF13D2DD2A19064 /* View */,
); );
path = KnockRequestsListScreen; path = KnockRequestsListScreen;
@@ -5595,7 +5614,9 @@
F2BBD71E8BF13D2DD2A19064 /* View */ = { F2BBD71E8BF13D2DD2A19064 /* View */ = {
isa = PBXGroup; isa = PBXGroup;
children = ( children = (
A756F1792CEDFF7300128047 /* KnockRequestsListEmptyStateView.swift */,
44B71F6D9062E8EB8929BB97 /* KnockRequestCell.swift */, 44B71F6D9062E8EB8929BB97 /* KnockRequestCell.swift */,
1511B1DCECC0DC75EB267328 /* KnockRequestsListScreen.swift */,
); );
path = View; path = View;
sourceTree = "<group>"; sourceTree = "<group>";
@@ -6386,6 +6407,7 @@
A216C83ADCF32BA5EF8A6FBC /* InviteUsersViewModelTests.swift in Sources */, A216C83ADCF32BA5EF8A6FBC /* InviteUsersViewModelTests.swift in Sources */,
7C0E29E0279866C62EC67A28 /* JoinRoomScreenViewModelTests.swift in Sources */, 7C0E29E0279866C62EC67A28 /* JoinRoomScreenViewModelTests.swift in Sources */,
EEC40663922856C65D1E0DF5 /* KeychainControllerTests.swift in Sources */, EEC40663922856C65D1E0DF5 /* KeychainControllerTests.swift in Sources */,
BA48D6AFF6421D199148C0A1 /* KnockRequestsListScreenViewModelTests.swift in Sources */,
CC961529F9F1854BEC3272C9 /* LayoutMocks.swift in Sources */, CC961529F9F1854BEC3272C9 /* LayoutMocks.swift in Sources */,
8AC256AF0EC54658321C9241 /* LegalInformationScreenViewModelTests.swift in Sources */, 8AC256AF0EC54658321C9241 /* LegalInformationScreenViewModelTests.swift in Sources */,
0033481EE363E4914295F188 /* LocalizationTests.swift in Sources */, 0033481EE363E4914295F188 /* LocalizationTests.swift in Sources */,
@@ -6733,6 +6755,7 @@
36926D795D6D19177C7812F8 /* EncryptionResetPasswordScreenCoordinator.swift in Sources */, 36926D795D6D19177C7812F8 /* EncryptionResetPasswordScreenCoordinator.swift in Sources */,
B1B255CE0E4306DD6E09D936 /* EncryptionResetPasswordScreenModels.swift in Sources */, B1B255CE0E4306DD6E09D936 /* EncryptionResetPasswordScreenModels.swift in Sources */,
D6152E21036B88C44ECB22E7 /* EncryptionResetPasswordScreenViewModel.swift in Sources */, D6152E21036B88C44ECB22E7 /* EncryptionResetPasswordScreenViewModel.swift in Sources */,
A756F17A2CEDFF9700128047 /* KnockRequestsListEmptyStateView.swift in Sources */,
A0601810597769B81C2358AF /* EncryptionResetPasswordScreenViewModelProtocol.swift in Sources */, A0601810597769B81C2358AF /* EncryptionResetPasswordScreenViewModelProtocol.swift in Sources */,
F3F9D61C53C348043D3D6F51 /* EncryptionResetScreen.swift in Sources */, F3F9D61C53C348043D3D6F51 /* EncryptionResetScreen.swift in Sources */,
3041EBA2660F28FFB7BDA339 /* EncryptionResetScreenCoordinator.swift in Sources */, 3041EBA2660F28FFB7BDA339 /* EncryptionResetScreenCoordinator.swift in Sources */,
@@ -6817,6 +6840,11 @@
CB99B0FA38A4AC596F38CC13 /* KeychainControllerProtocol.swift in Sources */, CB99B0FA38A4AC596F38CC13 /* KeychainControllerProtocol.swift in Sources */,
2748E5574A1031DD05E54FDA /* KnockRequestCell.swift in Sources */, 2748E5574A1031DD05E54FDA /* KnockRequestCell.swift in Sources */,
D5E8EE8A288EFCCF646860EA /* KnockRequestsBannerView.swift in Sources */, D5E8EE8A288EFCCF646860EA /* KnockRequestsBannerView.swift in Sources */,
AAA551AD8768309024D4907B /* KnockRequestsListScreen.swift in Sources */,
0307469D99B5FE6C7043AE39 /* KnockRequestsListScreenCoordinator.swift in Sources */,
9EE71509E6E7519A2B2388B3 /* KnockRequestsListScreenModels.swift in Sources */,
A0861B727B273B5B3DD7FBF6 /* KnockRequestsListScreenViewModel.swift in Sources */,
75ED4B73983228BB6922CE3C /* KnockRequestsListScreenViewModelProtocol.swift in Sources */,
C969A62F3D9F14318481A33B /* KnockedRoomProxy.swift in Sources */, C969A62F3D9F14318481A33B /* KnockedRoomProxy.swift in Sources */,
6681D6D3ADF69EBD2625F29A /* KnockedRoomProxyMock.swift in Sources */, 6681D6D3ADF69EBD2625F29A /* KnockedRoomProxyMock.swift in Sources */,
454F8DDC4442C0DE54094902 /* LABiometryType.swift in Sources */, 454F8DDC4442C0DE54094902 /* LABiometryType.swift in Sources */,
@@ -370,7 +370,11 @@
"screen_join_room_knock_message_description" = "Message (optional)"; "screen_join_room_knock_message_description" = "Message (optional)";
"screen_join_room_knock_sent_description" = "You will receive an invite to join the room if your request is accepted."; "screen_join_room_knock_sent_description" = "You will receive an invite to join the room if your request is accepted.";
"screen_join_room_knock_sent_title" = "Request to join sent"; "screen_join_room_knock_sent_title" = "Request to join sent";
"screen_knock_requests_list_accept_all_button_title" = "Accept all";
"screen_knock_requests_list_decline_and_ban_action_title" = "Decline and ban"; "screen_knock_requests_list_decline_and_ban_action_title" = "Decline and ban";
"screen_knock_requests_list_empty_state_description" = "When somebody will ask to join the room, you’ll be able to see their request here.";
"screen_knock_requests_list_empty_state_title" = "No pending request to join";
"screen_knock_requests_list_title" = "Requests to join";
"screen_pinned_timeline_empty_state_description" = "Press on a message and choose “%1$@” to include here."; "screen_pinned_timeline_empty_state_description" = "Press on a message and choose “%1$@” to include here.";
"screen_pinned_timeline_empty_state_headline" = "Pin important messages so that they can be easily discovered"; "screen_pinned_timeline_empty_state_headline" = "Pin important messages so that they can be easily discovered";
"screen_reset_encryption_password_error" = "An unknown error happened. Please check your account password is correct and try again."; "screen_reset_encryption_password_error" = "An unknown error happened. Please check your account password is correct and try again.";
@@ -413,6 +413,11 @@ class RoomFlowCoordinator: FlowCoordinatorProtocol {
return .presentingChild(childRoomID: roomID, previousState: fromState) return .presentingChild(childRoomID: roomID, previousState: fromState)
case (.presentingChild(_, let previousState), .dismissChildFlow): case (.presentingChild(_, let previousState), .dismissChildFlow):
return previousState return previousState
case (.roomDetails, .presentKnockRequestsListScreen):
return .knockRequestsList
case (.knockRequestsList, .dismissKnockRequestsListScreen):
return .roomDetails(isRoot: false)
default: default:
return nil return nil
@@ -565,6 +570,11 @@ class RoomFlowCoordinator: FlowCoordinatorProtocol {
presentResolveSendFailure(failure: failure, sendHandle: sendHandle) presentResolveSendFailure(failure: failure, sendHandle: sendHandle)
case (.resolveSendFailure, .dismissResolveSendFailure, .room): case (.resolveSendFailure, .dismissResolveSendFailure, .room):
break break
case (.roomDetails, .presentKnockRequestsListScreen, .knockRequestsList):
presentKnockRequestsList()
case (.knockRequestsList, .dismissKnockRequestsListScreen, .roomDetails):
break
// Child flow // Child flow
case (_, .startChildFlow(let roomID, let via, let entryPoint), .presentingChild): case (_, .startChildFlow(let roomID, let via, let entryPoint), .presentingChild):
@@ -837,6 +847,8 @@ class RoomFlowCoordinator: FlowCoordinatorProtocol {
actionsSubject.send(.presentCallScreen(roomProxy: roomProxy)) actionsSubject.send(.presentCallScreen(roomProxy: roomProxy))
case .presentPinnedEventsTimeline: case .presentPinnedEventsTimeline:
stateMachine.tryEvent(.presentPinnedEventsTimeline) stateMachine.tryEvent(.presentPinnedEventsTimeline)
case .presentKnockingRequestsListScreen:
stateMachine.tryEvent(.presentKnockRequestsListScreen)
} }
} }
.store(in: &cancellables) .store(in: &cancellables)
@@ -883,6 +895,20 @@ class RoomFlowCoordinator: FlowCoordinatorProtocol {
} }
} }
private func presentKnockRequestsList() {
let parameters = KnockRequestsListScreenCoordinatorParameters(roomProxy: roomProxy, mediaProvider: userSession.mediaProvider)
let coordinator = KnockRequestsListScreenCoordinator(parameters: parameters)
coordinator.actionsPublisher
.sink { [weak self] _ in
}
.store(in: &cancellables)
navigationStackCoordinator.push(coordinator) { [weak self] in
self?.stateMachine.tryEvent(.dismissKnockRequestsListScreen)
}
}
private func presentRoomDetailsEditScreen() { private func presentRoomDetailsEditScreen() {
let stackCoordinator = NavigationStackCoordinator() let stackCoordinator = NavigationStackCoordinator()
@@ -1546,6 +1572,7 @@ private extension RoomFlowCoordinator {
case rolesAndPermissions case rolesAndPermissions
case pinnedEventsTimeline(previousState: PinnedEventsTimelineSource) case pinnedEventsTimeline(previousState: PinnedEventsTimelineSource)
case resolveSendFailure case resolveSendFailure
case knockRequestsList
/// A child flow is in progress. /// A child flow is in progress.
case presentingChild(childRoomID: String, previousState: State) case presentingChild(childRoomID: String, previousState: State)
@@ -1624,6 +1651,9 @@ private extension RoomFlowCoordinator {
// Child room flow events // Child room flow events
case startChildFlow(roomID: String, via: [String], entryPoint: RoomFlowCoordinatorEntryPoint) case startChildFlow(roomID: String, via: [String], entryPoint: RoomFlowCoordinatorEntryPoint)
case dismissChildFlow case dismissChildFlow
case presentKnockRequestsListScreen
case dismissKnockRequestsListScreen
} }
} }
+8
View File
@@ -1298,8 +1298,16 @@ internal enum L10n {
} }
/// Are you sure you want to turn off key storage and delete it? /// Are you sure you want to turn off key storage and delete it?
internal static var screenKeyBackupDisableTitle: String { return L10n.tr("Localizable", "screen_key_backup_disable_title") } internal static var screenKeyBackupDisableTitle: String { return L10n.tr("Localizable", "screen_key_backup_disable_title") }
/// Accept all
internal static var screenKnockRequestsListAcceptAllButtonTitle: String { return L10n.tr("Localizable", "screen_knock_requests_list_accept_all_button_title") }
/// Decline and ban /// Decline and ban
internal static var screenKnockRequestsListDeclineAndBanActionTitle: String { return L10n.tr("Localizable", "screen_knock_requests_list_decline_and_ban_action_title") } internal static var screenKnockRequestsListDeclineAndBanActionTitle: String { return L10n.tr("Localizable", "screen_knock_requests_list_decline_and_ban_action_title") }
/// When somebody will ask to join the room, you’ll be able to see their request here.
internal static var screenKnockRequestsListEmptyStateDescription: String { return L10n.tr("Localizable", "screen_knock_requests_list_empty_state_description") }
/// No pending request to join
internal static var screenKnockRequestsListEmptyStateTitle: String { return L10n.tr("Localizable", "screen_knock_requests_list_empty_state_title") }
/// Requests to join
internal static var screenKnockRequestsListTitle: String { return L10n.tr("Localizable", "screen_knock_requests_list_title") }
/// This account has been deactivated. /// This account has been deactivated.
internal static var screenLoginErrorDeactivatedAccount: String { return L10n.tr("Localizable", "screen_login_error_deactivated_account") } internal static var screenLoginErrorDeactivatedAccount: String { return L10n.tr("Localizable", "screen_login_error_deactivated_account") }
/// Incorrect username and/or password /// Incorrect username and/or password
@@ -0,0 +1,45 @@
//
// Copyright 2022-2024 New Vector Ltd.
//
// SPDX-License-Identifier: AGPL-3.0-only
// Please see LICENSE in the repository root for full details.
//
// periphery:ignore:all - this is just a knockRequestsList remove this comment once generating the final file
import Combine
import SwiftUI
struct KnockRequestsListScreenCoordinatorParameters {
let roomProxy: JoinedRoomProxyProtocol
let mediaProvider: MediaProviderProtocol
}
enum KnockRequestsListScreenCoordinatorAction { }
final class KnockRequestsListScreenCoordinator: CoordinatorProtocol {
private let viewModel: KnockRequestsListScreenViewModelProtocol
private var cancellables = Set<AnyCancellable>()
private let actionsSubject: PassthroughSubject<KnockRequestsListScreenCoordinatorAction, Never> = .init()
var actionsPublisher: AnyPublisher<KnockRequestsListScreenCoordinatorAction, Never> {
actionsSubject.eraseToAnyPublisher()
}
init(parameters: KnockRequestsListScreenCoordinatorParameters) {
viewModel = KnockRequestsListScreenViewModel(roomProxy: parameters.roomProxy,
mediaProvider: parameters.mediaProvider)
}
func start() {
viewModel.actionsPublisher.sink { [weak self] action in
MXLog.info("Coordinator: received view model action: \(action)")
}
.store(in: &cancellables)
}
func toPresentable() -> AnyView {
AnyView(KnockRequestsListScreen(context: viewModel.context))
}
}
@@ -0,0 +1,24 @@
//
// Copyright 2022-2024 New Vector Ltd.
//
// SPDX-License-Identifier: AGPL-3.0-only
// Please see LICENSE in the repository root for full details.
//
import Foundation
enum KnockRequestsListScreenViewModelAction { }
struct KnockRequestsListScreenViewState: BindableState {
var requests: [KnockRequestCellInfo] = []
var canAccept = false
var canDecline = false
var canBan = false
}
enum KnockRequestsListScreenViewAction {
case acceptAllRequests
case acceptRequest(userID: String)
case declineRequest(userID: String)
case ban(userID: String)
}
@@ -0,0 +1,75 @@
//
// Copyright 2022-2024 New Vector Ltd.
//
// SPDX-License-Identifier: AGPL-3.0-only
// Please see LICENSE in the repository root for full details.
//
import Combine
import SwiftUI
typealias KnockRequestsListScreenViewModelType = StateStoreViewModel<KnockRequestsListScreenViewState, KnockRequestsListScreenViewAction>
class KnockRequestsListScreenViewModel: KnockRequestsListScreenViewModelType, KnockRequestsListScreenViewModelProtocol {
private let roomProxy: JoinedRoomProxyProtocol
private let actionsSubject: PassthroughSubject<KnockRequestsListScreenViewModelAction, Never> = .init()
var actionsPublisher: AnyPublisher<KnockRequestsListScreenViewModelAction, Never> {
actionsSubject.eraseToAnyPublisher()
}
init(roomProxy: JoinedRoomProxyProtocol, mediaProvider: MediaProviderProtocol) {
self.roomProxy = roomProxy
super.init(initialViewState: KnockRequestsListScreenViewState(), mediaProvider: mediaProvider)
Task {
await updatePermissions()
}
setupSubscriptions()
}
// MARK: - Public
override func process(viewAction: KnockRequestsListScreenViewAction) {
switch viewAction {
case .acceptAllRequests:
break
case .acceptRequest(let userID):
break
case .declineRequest(let userID):
break
case .ban(let userID):
break
}
}
// MARK: - Private
private func setupSubscriptions() {
roomProxy.infoPublisher
.throttle(for: .milliseconds(200), scheduler: DispatchQueue.main, latest: true)
.sink { [weak self] _ in
Task { await self?.updatePermissions() }
}
.store(in: &cancellables)
}
private func updatePermissions() async {
state.canAccept = await (try? roomProxy.canUserInvite(userID: roomProxy.ownUserID).get()) == true
state.canDecline = await (try? roomProxy.canUserKick(userID: roomProxy.ownUserID).get()) == true
state.canBan = await (try? roomProxy.canUserBan(userID: roomProxy.ownUserID).get()) == true
}
// For testing purposes
private init(initialViewState: KnockRequestsListScreenViewState) {
roomProxy = JoinedRoomProxyMock(.init())
super.init(initialViewState: initialViewState)
}
}
extension KnockRequestsListScreenViewModel {
static func mockWithInitialState(_ initialViewState: KnockRequestsListScreenViewState) -> KnockRequestsListScreenViewModel {
.init(initialViewState: initialViewState)
}
}
@@ -0,0 +1,14 @@
//
// Copyright 2022-2024 New Vector Ltd.
//
// SPDX-License-Identifier: AGPL-3.0-only
// Please see LICENSE in the repository root for full details.
//
import Combine
@MainActor
protocol KnockRequestsListScreenViewModelProtocol {
var actionsPublisher: AnyPublisher<KnockRequestsListScreenViewModelAction, Never> { get }
var context: KnockRequestsListScreenViewModelType.Context { get }
}
@@ -15,8 +15,9 @@
import Compound import Compound
import SwiftUI import SwiftUI
struct KnockRequestCellInfo { struct KnockRequestCellInfo: Identifiable {
let userID: String /// user identifier of the usee that sent the request
let id: String
let displayName: String? let displayName: String?
let avatarUrl: URL? let avatarUrl: URL?
let timestamp: String? let timestamp: String?
@@ -26,67 +27,92 @@ struct KnockRequestCellInfo {
struct KnockRequestCell: View { struct KnockRequestCell: View {
let cellInfo: KnockRequestCellInfo let cellInfo: KnockRequestCellInfo
var mediaProvider: MediaProviderProtocol? var mediaProvider: MediaProviderProtocol?
let onAccept: (String) -> Void let onAccept: ((String) -> Void)?
let onDecline: (String) -> Void let onDecline: ((String) -> Void)?
let onDeclineAndBan: (String) -> Void let onDeclineAndBan: ((String) -> Void)?
var body: some View { var body: some View {
VStack(spacing: 0) { HStack(alignment: .top, spacing: 16) {
HStack(alignment: .top, spacing: 16) { LoadableAvatarImage(url: cellInfo.avatarUrl,
LoadableAvatarImage(url: cellInfo.avatarUrl, name: cellInfo.displayName,
name: cellInfo.displayName, contentID: cellInfo.id,
contentID: cellInfo.userID, avatarSize: .user(on: .knockingUserList),
avatarSize: .user(on: .knockingUserList), mediaProvider: mediaProvider)
mediaProvider: mediaProvider) VStack(alignment: .leading, spacing: 12) {
VStack(alignment: .leading, spacing: 12) { header
VStack(alignment: .leading, spacing: 0) { if let reason = cellInfo.reason {
HStack(alignment: .top, spacing: 0) { DisclosableText(text: reason)
Text(cellInfo.displayName ?? cellInfo.userID) }
.font(.compound.bodyLGSemibold) actions
.foregroundStyle(.compound.textPrimary) }
.frame(maxWidth: .infinity, alignment: .leading) .padding(.trailing, 16)
if let timestamp = cellInfo.timestamp { .overlay(alignment: .bottom) {
Text(timestamp) // Custom separator that uses the same color from the compound one
.font(.compound.bodySM) Color.compound._borderInteractiveSecondaryAlpha
.foregroundStyle(.compound.textSecondary) .frame(height: 0.5)
} }
} }
if cellInfo.displayName != nil { .padding(.top, 16)
Text(cellInfo.userID) .padding(.leading, 16)
.font(.compound.bodyMD) .background(.compound.bgCanvasDefault)
.foregroundStyle(.compound.textSecondary) }
}
} private var header: some View {
if let reason = cellInfo.reason { VStack(alignment: .leading, spacing: 0) {
DisclosableText(text: reason) HStack(alignment: .top, spacing: 0) {
} Text(cellInfo.displayName ?? cellInfo.id)
actions .font(.compound.bodyLGSemibold)
.foregroundStyle(.compound.textPrimary)
.frame(maxWidth: .infinity, alignment: .leading)
if let timestamp = cellInfo.timestamp {
Text(timestamp)
.font(.compound.bodySM)
.foregroundStyle(.compound.textSecondary)
} }
} }
.padding(16) if cellInfo.displayName != nil {
Divider() Text(cellInfo.id)
.font(.compound.bodyMD)
.foregroundStyle(.compound.textSecondary)
}
} }
} }
@ViewBuilder @ViewBuilder
private var actions: some View { private var actions: some View {
HStack(spacing: 16) { VStack(spacing: 0) {
Button(L10n.actionDecline) { if onDecline != nil || onAccept != nil {
onDecline(cellInfo.userID) HStack(spacing: 16) {
if let onDecline {
Button(L10n.actionDecline) {
onDecline(cellInfo.id)
}
.buttonStyle(.compound(.secondary, size: .medium))
}
if let onAccept {
Button(L10n.actionAccept) {
onAccept(cellInfo.id)
}
.buttonStyle(.compound(.primary, size: .medium))
}
}
} }
.buttonStyle(.compound(.secondary))
Button(L10n.actionAccept) { if let onDeclineAndBan {
onAccept(cellInfo.userID) Button(role: .destructive) {
onDeclineAndBan(cellInfo.id)
} label: {
Text(L10n.screenKnockRequestsListDeclineAndBanActionTitle)
.padding(.top, 8)
.padding(.bottom, 4)
}
.frame(maxWidth: .infinity)
.buttonStyle(.compound(.plain))
.padding(.top, 16)
} }
.buttonStyle(.compound(.primary))
} }
Button(L10n.screenKnockRequestsListDeclineAndBanActionTitle, role: .destructive) { .padding(.bottom, 16)
onDeclineAndBan(cellInfo.userID)
}
.buttonStyle(.compound(.plain))
.frame(maxWidth: .infinity)
.padding(.top, 12)
.padding(.bottom, 4)
} }
} }
@@ -130,9 +156,10 @@ private struct DisclosableText: View {
} }
} label: { } label: {
CompoundIcon(\.chevronDown, size: .medium, relativeTo: .compound.bodyMD) CompoundIcon(\.chevronDown, size: .medium, relativeTo: .compound.bodyMD)
.foregroundStyle(.compound.iconTertiary)
.rotationEffect(.degrees(isExpanded ? 180 : 0))
} }
.rotationEffect(.degrees(isExpanded ? 180 : 0)) .buttonStyle(.plain)
.foregroundStyle(.compound.iconTertiary)
.opacity(collapsedHeight < expandedHeight ? 1 : 0) .opacity(collapsedHeight < expandedHeight ? 1 : 0)
.disabled(collapsedHeight >= expandedHeight) .disabled(collapsedHeight >= expandedHeight)
} }
@@ -141,13 +168,13 @@ private struct DisclosableText: View {
struct KnockRequestCell_Previews: PreviewProvider, TestablePreview { struct KnockRequestCell_Previews: PreviewProvider, TestablePreview {
// swiftlint:disable:next line_length // swiftlint:disable:next line_length
static let aliceWithLongReason = KnockRequestCellInfo(userID: "@alice:matrix.org", displayName: "Alice", avatarUrl: nil, timestamp: "20 Nov 2024", reason: "Hello would like to join this room, also this is a very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very long reason") static let aliceWithLongReason = KnockRequestCellInfo(id: "@alice:matrix.org", displayName: "Alice", avatarUrl: nil, timestamp: "20 Nov 2024", reason: "Hello would like to join this room, also this is a very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very long reason")
static let aliceWithShortReason = KnockRequestCellInfo(userID: "@alice:matrix.org", displayName: "Alice", avatarUrl: nil, timestamp: "20 Nov 2024", reason: "Hello, I am Alice and would like to join this room, please") static let aliceWithShortReason = KnockRequestCellInfo(id: "@alice:matrix.org", displayName: "Alice", avatarUrl: nil, timestamp: "20 Nov 2024", reason: "Hello, I am Alice and would like to join this room, please")
static let aliceWithNoReason = KnockRequestCellInfo(userID: "@alice:matrix.org", displayName: "Alice", avatarUrl: nil, timestamp: "20 Nov 2024", reason: nil) static let aliceWithNoReason = KnockRequestCellInfo(id: "@alice:matrix.org", displayName: "Alice", avatarUrl: nil, timestamp: "20 Nov 2024", reason: nil)
static let aliceWithNoName = KnockRequestCellInfo(userID: "@alice:matrix.org", displayName: nil, avatarUrl: nil, timestamp: "20 Nov 2024", reason: nil) static let aliceWithNoName = KnockRequestCellInfo(id: "@alice:matrix.org", displayName: nil, avatarUrl: nil, timestamp: "20 Nov 2024", reason: nil)
static var previews: some View { static var previews: some View {
KnockRequestCell(cellInfo: aliceWithLongReason, onAccept: { _ in }, onDecline: { _ in }, onDeclineAndBan: { _ in }) KnockRequestCell(cellInfo: aliceWithLongReason, onAccept: { _ in }, onDecline: { _ in }, onDeclineAndBan: { _ in })
@@ -158,5 +185,11 @@ struct KnockRequestCell_Previews: PreviewProvider, TestablePreview {
.previewDisplayName("No reason") .previewDisplayName("No reason")
KnockRequestCell(cellInfo: aliceWithNoName, onAccept: { _ in }, onDecline: { _ in }, onDeclineAndBan: { _ in }) KnockRequestCell(cellInfo: aliceWithNoName, onAccept: { _ in }, onDecline: { _ in }, onDeclineAndBan: { _ in })
.previewDisplayName("No name") .previewDisplayName("No name")
KnockRequestCell(cellInfo: aliceWithShortReason, onAccept: nil, onDecline: { _ in }, onDeclineAndBan: { _ in })
.previewDisplayName("No Accept")
KnockRequestCell(cellInfo: aliceWithShortReason, onAccept: nil, onDecline: nil, onDeclineAndBan: { _ in })
.previewDisplayName("No Accept and Decline")
KnockRequestCell(cellInfo: aliceWithShortReason, onAccept: { _ in }, onDecline: { _ in }, onDeclineAndBan: nil)
.previewDisplayName("No Ban")
} }
} }
@@ -0,0 +1,38 @@
//
// Copyright 2024 New Vector Ltd.
//
// SPDX-License-Identifier: AGPL-3.0-only
// Please see LICENSE in the repository root for full details.
//
import Compound
import SwiftUI
struct KnockRequestsListEmptyStateView: View {
var body: some View {
VStack(spacing: 16) {
BigIcon(icon: \.askToJoin)
VStack(spacing: 8) {
Text(L10n.screenKnockRequestsListEmptyStateTitle)
.multilineTextAlignment(.center)
.font(.compound.headingMDBold)
.foregroundStyle(.compound.textPrimary)
Text(L10n.screenKnockRequestsListEmptyStateDescription)
.multilineTextAlignment(.center)
.foregroundStyle(.compound.textSecondary)
.font(.compound.bodyMD)
}
Spacer()
}
.padding(.top, 53)
.padding(.horizontal, 40)
}
}
// MARK: - Previews
struct KnockRequestsListEmptyStateView_Previews: PreviewProvider, TestablePreview {
static var previews: some View {
KnockRequestsListEmptyStateView()
}
}
@@ -0,0 +1,96 @@
//
// Copyright 2022-2024 New Vector Ltd.
//
// SPDX-License-Identifier: AGPL-3.0-only
// Please see LICENSE in the repository root for full details.
//
import Compound
import SwiftUI
struct KnockRequestsListScreen: View {
@ObservedObject var context: KnockRequestsListScreenViewModel.Context
var body: some View {
mainContent
.navigationBarTitleDisplayMode(.inline)
.navigationTitle(L10n.screenKnockRequestsListTitle)
.background(.compound.bgCanvasDefault)
.overlay {
if context.viewState.requests.isEmpty {
KnockRequestsListEmptyStateView()
}
}
.safeAreaInset(edge: .bottom) {
if !context.viewState.requests.isEmpty {
acceptAllButton
}
}
}
@ViewBuilder
private var mainContent: some View {
ScrollView {
LazyVStack(spacing: 0) {
ForEach(context.viewState.requests) { requestInfo in
ListRow(kind: .custom {
KnockRequestCell(cellInfo: requestInfo,
mediaProvider: context.mediaProvider,
onAccept: context.viewState.canAccept ? onAccept : nil,
onDecline: context.viewState.canDecline ? onDecline : nil,
onDeclineAndBan: context.viewState.canBan ? onDeclineAndBan : nil)
})
}
}
.padding(.top, 40)
}
}
private var acceptAllButton: some View {
Button(L10n.screenKnockRequestsListAcceptAllButtonTitle) {
context.send(viewAction: .acceptAllRequests)
}
.buttonStyle(.compound(.secondary))
.padding(.horizontal, 16)
.padding(.top, 16)
.padding(.bottom, 4)
.background(.compound.bgCanvasDefault)
}
private func onAccept(userID: String) {
context.send(viewAction: .acceptRequest(userID: userID))
}
private func onDecline(userID: String) {
context.send(viewAction: .declineRequest(userID: userID))
}
private func onDeclineAndBan(userID: String) {
context.send(viewAction: .ban(userID: userID))
}
}
// MARK: - Previews
struct KnockRequestsListScreen_Previews: PreviewProvider, TestablePreview {
static let emptyViewModel = KnockRequestsListScreenViewModel.mockWithInitialState(.init())
static let viewModel = KnockRequestsListScreenViewModel.mockWithInitialState(.init(requests: [.init(id: "@alice:matrix.org", displayName: "Alice", avatarUrl: nil, timestamp: "Now", reason: "Hello"),
// swiftlint:disable:next line_length
.init(id: "@bob:matrix.org", displayName: "Bob", avatarUrl: nil, timestamp: "Now", reason: "Hello this one is a very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very very long reason"),
.init(id: "@charlie:matrix.org", displayName: "Charlie", avatarUrl: nil, timestamp: "Now", reason: nil),
.init(id: "@dan:matrix.org", displayName: "Dan", avatarUrl: nil, timestamp: "Now", reason: "Hello! It's a me! Dan!")],
canAccept: true,
canDecline: true,
canBan: true))
static var previews: some View {
NavigationStack {
KnockRequestsListScreen(context: viewModel.context)
}
NavigationStack {
KnockRequestsListScreen(context: emptyViewModel.context)
}
.previewDisplayName("Empty state")
}
}
@@ -29,6 +29,7 @@ enum RoomDetailsScreenCoordinatorAction {
case presentRolesAndPermissionsScreen case presentRolesAndPermissionsScreen
case presentCall case presentCall
case presentPinnedEventsTimeline case presentPinnedEventsTimeline
case presentKnockingRequestsListScreen
} }
final class RoomDetailsScreenCoordinator: CoordinatorProtocol { final class RoomDetailsScreenCoordinator: CoordinatorProtocol {
@@ -79,6 +80,8 @@ final class RoomDetailsScreenCoordinator: CoordinatorProtocol {
actionsSubject.send(.presentCall) actionsSubject.send(.presentCall)
case .displayPinnedEventsTimeline: case .displayPinnedEventsTimeline:
actionsSubject.send(.presentPinnedEventsTimeline) actionsSubject.send(.presentPinnedEventsTimeline)
case .displayKnockingRequests:
actionsSubject.send(.presentKnockingRequestsListScreen)
} }
} }
.store(in: &cancellables) .store(in: &cancellables)
@@ -22,6 +22,7 @@ enum RoomDetailsScreenViewModelAction {
case requestRolesAndPermissionsPresentation case requestRolesAndPermissionsPresentation
case startCall case startCall
case displayPinnedEventsTimeline case displayPinnedEventsTimeline
case displayKnockingRequests
} }
// MARK: View // MARK: View
@@ -42,9 +43,16 @@ struct RoomDetailsScreenViewState: BindableState {
var canEditRoomTopic = false var canEditRoomTopic = false
var canEditRoomAvatar = false var canEditRoomAvatar = false
var canEditRolesOrPermissions = false var canEditRolesOrPermissions = false
var canKickUsers = false
var canBanUsers = false
var notificationSettingsState: RoomDetailsNotificationSettingsState = .loading var notificationSettingsState: RoomDetailsNotificationSettingsState = .loading
var canJoinCall = false var canJoinCall = false
var pinnedEventsActionState = RoomDetailsScreenPinnedEventsActionState.loading var pinnedEventsActionState = RoomDetailsScreenPinnedEventsActionState.loading
var knockingEnabled = false
var canSeeKnockingRequests: Bool {
knockingEnabled && dmRecipient == nil && (canInviteUsers || canKickUsers || canBanUsers)
}
var canEdit: Bool { var canEdit: Bool {
!isDirect && (canEditRoomName || canEditRoomTopic || canEditRoomAvatar) !isDirect && (canEditRoomName || canEditRoomTopic || canEditRoomAvatar)
@@ -188,6 +196,7 @@ enum RoomDetailsScreenViewAction {
case processTapRolesAndPermissions case processTapRolesAndPermissions
case processTapCall case processTapCall
case processTapPinnedEvents case processTapPinnedEvents
case processTapRequestsToJoin
} }
enum RoomDetailsScreenViewShortcut { enum RoomDetailsScreenViewShortcut {
@@ -75,6 +75,10 @@ class RoomDetailsScreenViewModel: RoomDetailsScreenViewModelType, RoomDetailsScr
bindings: .init()), bindings: .init()),
mediaProvider: mediaProvider) mediaProvider: mediaProvider)
appSettings.$knockingEnabled
.weakAssign(to: \.state.knockingEnabled, on: self)
.store(in: &cancellables)
appMediator.networkMonitor.reachabilityPublisher appMediator.networkMonitor.reachabilityPublisher
.filter { $0 == .reachable } .filter { $0 == .reachable }
.receive(on: DispatchQueue.main) .receive(on: DispatchQueue.main)
@@ -160,6 +164,8 @@ class RoomDetailsScreenViewModel: RoomDetailsScreenViewModelType, RoomDetailsScr
case .processTapPinnedEvents: case .processTapPinnedEvents:
analyticsService.trackInteraction(name: .PinnedMessageRoomInfoButton) analyticsService.trackInteraction(name: .PinnedMessageRoomInfoButton)
actionsSubject.send(.displayPinnedEventsTimeline) actionsSubject.send(.displayPinnedEventsTimeline)
case .processTapRequestsToJoin:
actionsSubject.send(.displayKnockingRequests)
} }
} }
@@ -212,6 +218,8 @@ class RoomDetailsScreenViewModel: RoomDetailsScreenViewModelType, RoomDetailsScr
state.canEditRoomAvatar = await (try? roomProxy.canUser(userID: roomProxy.ownUserID, sendStateEvent: .roomAvatar).get()) == true state.canEditRoomAvatar = await (try? roomProxy.canUser(userID: roomProxy.ownUserID, sendStateEvent: .roomAvatar).get()) == true
state.canEditRolesOrPermissions = await (try? roomProxy.suggestedRole(for: roomProxy.ownUserID).get()) == .administrator state.canEditRolesOrPermissions = await (try? roomProxy.suggestedRole(for: roomProxy.ownUserID).get()) == .administrator
state.canInviteUsers = await (try? roomProxy.canUserInvite(userID: roomProxy.ownUserID).get()) == true state.canInviteUsers = await (try? roomProxy.canUserInvite(userID: roomProxy.ownUserID).get()) == true
state.canKickUsers = await (try? roomProxy.canUserKick(userID: roomProxy.ownUserID).get()) == true
state.canBanUsers = await (try? roomProxy.canUserBan(userID: roomProxy.ownUserID).get()) == true
} }
private func setupNotificationSettingsSubscription() { private func setupNotificationSettingsSubscription() {
@@ -160,6 +160,15 @@ struct RoomDetailsScreen: View {
}) })
.accessibilityIdentifier(A11yIdentifiers.roomDetailsScreen.people) .accessibilityIdentifier(A11yIdentifiers.roomDetailsScreen.people)
} }
if context.viewState.canSeeKnockingRequests {
ListRow(label: .default(title: L10n.screenRoomDetailsRequestsToJoinTitle,
icon: \.askToJoin),
// TODO: Display count if requests > 0 when an API for them is available
details: .counter(1),
kind: .navigationLink {
context.send(viewAction: .processTapRequestsToJoin)
})
}
ListRow(label: .default(title: L10n.screenPollsHistoryTitle, ListRow(label: .default(title: L10n.screenPollsHistoryTitle,
icon: \.polls), icon: \.polls),
kind: .navigationLink { kind: .navigationLink {
@@ -294,6 +303,7 @@ struct RoomDetailsScreen: View {
struct RoomDetailsScreen_Previews: PreviewProvider, TestablePreview { struct RoomDetailsScreen_Previews: PreviewProvider, TestablePreview {
static let genericRoomViewModel = { static let genericRoomViewModel = {
ServiceLocator.shared.settings.knockingEnabled = true
let members: [RoomMemberProxyMock] = [ let members: [RoomMemberProxyMock] = [
.mockMeAdmin, .mockMeAdmin,
.mockAlice, .mockAlice,
@@ -357,6 +367,7 @@ struct RoomDetailsScreen_Previews: PreviewProvider, TestablePreview {
}() }()
static let simpleRoomViewModel = { static let simpleRoomViewModel = {
ServiceLocator.shared.settings.knockingEnabled = true
let members: [RoomMemberProxyMock] = [ let members: [RoomMemberProxyMock] = [
.mockMeAdmin, .mockMeAdmin,
.mockAlice, .mockAlice,
@@ -18,7 +18,7 @@ struct KnockRequestInfo {
struct KnockRequestsBannerView: View { struct KnockRequestsBannerView: View {
let requests: [KnockRequestInfo] let requests: [KnockRequestInfo]
let onDismiss: () -> Void let onDismiss: () -> Void
let onAccept: (String) -> Void let onAccept: ((String) -> Void)?
let onViewAll: () -> Void let onViewAll: () -> Void
var mediaProvider: MediaProviderProtocol? var mediaProvider: MediaProviderProtocol?
@@ -34,9 +34,16 @@ struct KnockRequestsBannerView: View {
@ViewBuilder @ViewBuilder
private var mainContent: some View { private var mainContent: some View {
if requests.count == 1 { if requests.count == 1 {
SingleKnockRequestBannerContent(request: requests[0], onDismiss: onDismiss, onAccept: onAccept, onViewAll: onViewAll) SingleKnockRequestBannerContent(request: requests[0],
onDismiss: onDismiss,
onAccept: onAccept,
onViewAll: onViewAll,
mediaProvider: mediaProvider)
} else if requests.count > 1 { } else if requests.count > 1 {
MultipleKnockRequestsBannerContent(requests: requests, onDismiss: onDismiss, onViewAll: onViewAll) MultipleKnockRequestsBannerContent(requests: requests,
onDismiss: onDismiss,
onViewAll: onViewAll,
mediaProvider: mediaProvider)
} else { } else {
EmptyView() EmptyView()
} }
@@ -46,7 +53,7 @@ struct KnockRequestsBannerView: View {
private struct SingleKnockRequestBannerContent: View { private struct SingleKnockRequestBannerContent: View {
let request: KnockRequestInfo let request: KnockRequestInfo
let onDismiss: () -> Void let onDismiss: () -> Void
let onAccept: (String) -> Void let onAccept: ((String) -> Void)?
let onViewAll: () -> Void let onViewAll: () -> Void
var mediaProvider: MediaProviderProtocol? var mediaProvider: MediaProviderProtocol?
@@ -93,11 +100,13 @@ private struct SingleKnockRequestBannerContent: View {
private var actions: some View { private var actions: some View {
HStack(spacing: 12) { HStack(spacing: 12) {
Button(L10n.screenRoomSingleKnockRequestViewButtonTitle, action: onViewAll) Button(L10n.screenRoomSingleKnockRequestViewButtonTitle, action: onViewAll)
.buttonStyle(.compound(.secondary)) .buttonStyle(.compound(.secondary, size: .medium))
Button(L10n.screenRoomSingleKnockRequestAcceptButtonTitle, action: { if let onAccept {
onAccept(request.userID) Button(L10n.screenRoomSingleKnockRequestAcceptButtonTitle, action: {
}) onAccept(request.userID)
.buttonStyle(.compound(.primary)) })
.buttonStyle(.compound(.primary, size: .medium))
}
} }
.padding(.top, request.reason == nil ? 0 : 2) .padding(.top, request.reason == nil ? 0 : 2)
.frame(maxWidth: .infinity) .frame(maxWidth: .infinity)
@@ -142,7 +151,7 @@ private struct MultipleKnockRequestsBannerContent: View {
Button(L10n.screenRoomMultipleKnockRequestsViewAllButtonTitle) { Button(L10n.screenRoomMultipleKnockRequestsViewAllButtonTitle) {
onViewAll() onViewAll()
} }
.buttonStyle(.compound(.primary)) .buttonStyle(.compound(.primary, size: .medium))
} }
} }
} }
@@ -181,6 +190,8 @@ struct KnockRequestsBannerView_Previews: PreviewProvider, TestablePreview {
static var previews: some View { static var previews: some View {
KnockRequestsBannerView(requests: singleRequest, onDismiss: { }, onAccept: { _ in }, onViewAll: { }) KnockRequestsBannerView(requests: singleRequest, onDismiss: { }, onAccept: { _ in }, onViewAll: { })
.previewDisplayName("Single Request") .previewDisplayName("Single Request")
KnockRequestsBannerView(requests: singleRequest, onDismiss: { }, onAccept: nil, onViewAll: { })
.previewDisplayName("Single Request, no accept action")
KnockRequestsBannerView(requests: singleRequestWithReason, onDismiss: { }, onAccept: { _ in }, onViewAll: { }) KnockRequestsBannerView(requests: singleRequestWithReason, onDismiss: { }, onAccept: { _ in }, onViewAll: { })
.previewDisplayName("Single Request with reason") .previewDisplayName("Single Request with reason")
KnockRequestsBannerView(requests: singleRequestNoDisplayName, onDismiss: { }, onAccept: { _ in }, onViewAll: { }) KnockRequestsBannerView(requests: singleRequestNoDisplayName, onDismiss: { }, onAccept: { _ in }, onViewAll: { })
@@ -317,6 +317,18 @@ extension PreviewTests {
} }
} }
func test_knockRequestsListEmptyStateView() {
for preview in KnockRequestsListEmptyStateView_Previews._allPreviews {
assertSnapshots(matching: preview)
}
}
func test_knockRequestsListScreen() {
for preview in KnockRequestsListScreen_Previews._allPreviews {
assertSnapshots(matching: preview)
}
}
func test_legalInformationScreen() { func test_legalInformationScreen() {
for preview in LegalInformationScreen_Previews._allPreviews { for preview in LegalInformationScreen_Previews._allPreviews {
assertSnapshots(matching: preview) assertSnapshots(matching: preview)
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:5466569f96a2d74dc598b7d870ae76d237c0e7dbf181f3e0adf497b0956e2649 oid sha256:48b0893d0ea480cd8ed616725e802c369974107b7cc9ecf2776a638d3262fea3
size 119491 size 117222
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:ea688a6d22a077644d73dfda17acd4bc7e05ed333492c8344082fa4de452e8c9
size 93005
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:8a4f99e888211cbce93dc2337149c7ea3d3021c5fb7d5fe825e270b8d3ef0a0e
size 97309
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:35c6e2fcf10e9276b2d9db775959a82c7fc6a7a45414cc2a5bf1ab849eafc3bb
size 98028
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:b61e8c99338ff1316736d3f8945cbc32c407a276493a63de0ffe9f1325479cc3 oid sha256:7c7f218094ea94484039eb30960094fe69658867b2f6793ee5308ca1d5fc4e63
size 93546 size 91440
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:79a32205860de5d076cbf226156962519586058e50a89ea7c29cf15b2d66fb75 oid sha256:00f5defb9806f8957dd2f08e011b26017335b1d34c621a31148d053bd495737b
size 94500 size 92432
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:cc9ebf6bcd889f2d0a0a855404b6be2ae140d40a69a21767dc9ecc3958539a79 oid sha256:84b3af435f25e50fe78803eaae8b6a38847cf40cbe56606c7e3cb0142cb5bd00
size 103862 size 101763
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:af31b5df7d0f0d97a8c306ece8cbaa611bfbc3a98e78a189ed5349f16faa5cc5 oid sha256:afa4b8b10c68b1074955312dfd8fd58f9e4b6866cef1e1f41eac82f5d38c2366
size 121175 size 118761
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:64fbca409e089763527195e78ff4f5ce9b71ada7249ce177a35251a2b62e28b6
size 93548
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:0fa0e01f526285a00ed6ce491e6b0837c90244059d9cbc7eb0bc71e9b588e84e
size 98413
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:50e377ed4ad1eb150222e178caea25b2f1965688879722051b99fc4a3e9a0513
size 98936
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:98eec884b96bcaa6eec3510a8c362762d2a0d3238eecd287782e2d41a778af83 oid sha256:28abf5766be915dd6723e7bdee24725ac3cb702665dc105a96823ad8ba95bd92
size 95103 size 92951
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:b974d372c92c5fb724778d384fc3072d95cc2bea1c9662d123fc24fbfba6890a oid sha256:41011733a39814817ffb7c537d5e74761b4c2cec6848c20a27724f86592e0d53
size 96049 size 93942
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:97c9af346e966100a44f1db6814e516455ba90c3a4154de9a5f657f955dfefa3 oid sha256:2cd6faa13983c923bf7b7979a935ecf36607f6272577e53b66cc3f661ae820c8
size 105493 size 103297
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:ce6497c50fbf9e9b0f6bb6713cacb55bb389a31232785faa1368b341d300b563 oid sha256:e504a0e147399d856bbdd8b0b61bce6f5c79dd88221261f1a632ad77c8d3f472
size 62895 size 60864
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:0b41449a70b60e61b9437ca5c8f886f733d9ad67b672da9c43e643a2ece2daa7
size 50526
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:689ddaeb4c545fba7ae22a27c71eef58636193bfc2c552a892e895d08fd616f4
size 55394
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:2b2d39bfeb9c5eeb3bd0fbe081f1b30c310ca12fe9cedb972cafe38b3550797f
size 55280
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:b6360a04a6d30220c3b8d9aed2de8309aa54b4234824fa73cc44ac40c0c89ed2 oid sha256:dd4a4b2f42ff295cebc742c561f5eb45f7aac1b38fc32e3f6e05536e6f7fa5a6
size 50804 size 48788
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:6ca01bbaee8ec50a79370b222b15fcb9d028db3b3782d5ab0757cce738497821 oid sha256:4a313f92f2f98e591988a9feebbd70101a2979cb3ec3e20b54a7a38118d15fd1
size 51417 size 49405
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:fb2cfa269efe2a538abd7c93d577878366b84f4e44701f8a4314a2f4eb53a3d8 oid sha256:6c9ba64a469cf367399029c12fb37c61f0f5f2f1963d65cf45594259482a50d3
size 60576 size 58910
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:14478f6bac6fb2a792c369f8568e4cf51a89029dd4b9434262db4eb0e76e7328 oid sha256:40e1f746d1ba51e90b8e0e76baa3aa81368c724686865818d5c24fe871eaed42
size 70929 size 67968
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:e7fab6e0aec518e2ae448fb4934ffd5f7ce01eb2640b63199a1509f1e8b254dc
size 52786
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:0a51f19aa29edfadb1d2eb825b395b19aafe1330675a3fa540816d1a2d3430c2
size 58846
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:4704df4d40737803ba1cbde55a06db24e9e931240b5cde7432436e576972b9d7
size 59940
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:388b944b239c1dd130e6c1463e777c9aa85186e3bf70402d8853e88b7c19be22 oid sha256:9fd2286d9c82ad62a4204129d57f2ed20befa6cf4c72de6fc8f074fb0438d357
size 59396 size 56148
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:1257061c8bef2b9fd9173e696ffecbfbd017b0f06eabe1228e80d3873007e271 oid sha256:74f835f0d5895d2afbd05222a9e99d3e0192c3fa3d2178a8618cf9be6c52e771
size 60458 size 56928
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:4e982a79556a5fdef82435ec63dca8a24970e8c80248c751fb89f06b09fa6061 oid sha256:273e1de0f9ca8e78fab88213cc4170e13bdf76d4a1e769d698e410b070b595db
size 68971 size 65761
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:a00d27886b5820fc2f46d201f9e40460010470702c4de0c1889173e0e9b7a3bf oid sha256:3879eccedadd6ef4dd6ae91070a0271b0fa064c025614933d0ac364ded809340
size 93142 size 91991
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:bece9623232e1204708162f137c93120d8da2a75b88787b233aa2cb09b54f630 oid sha256:b6eda3b084f228d4aa583bdb8b7903d81f78738d01972be40854a9fa0e65a327
size 97166 size 95267
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:c70474ce9b6a549f77ab2a2253ef565a5d1d887f486f77a4ee20dc59f9a952eb
size 93164
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:00dbd02aed2799c2bd9d87ae1c551e0327fae075d4fc772f526572ed8771791d oid sha256:5abf4bc3d8d591e6ecf7b47a7bb368fab3734184e78c353e3de0dc6ab9ff0767
size 111929 size 109665
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:0526b9fca57c50bf32249b9b3557916eae97c430b430a19cedaa06d4dfaa0ce3 oid sha256:a740945882890eceb0c971bd87f4384f8a051db9640624ce5dd9cde1ffd09c69
size 99219 size 97409
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:04db101605f075891d02b3d46dff7cd12577e93808de4b58297147f81f9c4d00 oid sha256:494a4003821e6bdad2cafeaf1d3403de5801450a268b1a444fa227b3f04ecff9
size 94022 size 92830
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:ac5e83a0da72ff4f45cfa53ea53e97b45ace007d44ba6278f476f15b72e711e2 oid sha256:e1376bad4b66e258b3ab72baca9d9baa67344c7860ae3aa1de094ea791503c97
size 100502 size 98556
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:83bd0c9f15a4119624157a5e109b6de045f3deeceb9d38a8a91ba4d5aad4e5f0
size 97656
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:401ba2ecfaea3b01487163af4b49c23b2ec0677356f240fec177da2e839cc188 oid sha256:3977847df019b9ba0997e97f26fd26d2f82087af4685df8f36330d995a58ff27
size 116728 size 114432
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:1b75c803de335663b3447151060475fdcd9f1e488da36f96da250ecd1bea01bd oid sha256:6deb588da8f5614bc82f6c4ff40171cebb6788e303cec6b2dcf24eb164c258d0
size 104073 size 102325
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:4b4b78c20f278e17836ebf1685bd2c7a55c6f22f54f7cbadd430f606f369272d oid sha256:415af5d4976c78a0ea3d69441cf77498d3c2412592c8c4c920105bc1f5e0805d
size 50876 size 50054
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:a8c1312811b4df9e02203b4f6a1e72546311b1b6c5a476088e66b21712b15005 oid sha256:866773bffcc2adbc48607fce04578e874f96e4165b9c7d59ff032e5aa4b1c2a6
size 54839 size 53082
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:7121b64c323fe2aafd3b8339cd7568655633ffdba21a5fb1fcd63b3da8c8ac1b
size 49578
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:248c6ebf2601a23aa6c58642f4001e62d299e36c426e8948e3dac744a32ee801 oid sha256:a5c4174827ce2e8a6523e2583886ebc84deebb193ed3e31314ebb2fa00ed26aa
size 67213 size 65732
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:dc821155dedf651cb75fd830fe8436be1d5c2e1131a6c491934f8eb357f08024 oid sha256:1b2cb2a46e0aebed7ecf5524e535d26486d6f8257207990c3b4e6270c513a938
size 54814 size 53199
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:8c3e3e0747511cf80b1d0e546a0e16e9eac85dbd4bcfdda0585d21a6fc525d07 oid sha256:69c9eb6ef65eb92d7270002ceaa4a4e3d2326980c8656b6a5ea34f3c3cc62e98
size 50476 size 49455
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:f6b08d7f64d1719c39a1d9ce22725e1615f47843eb5b1918d926a4f30b13552d oid sha256:6ee70dfee6160813a77e9454e9f7ce9e15e07fbda752798c1e53919c5588646f
size 61108 size 59781
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:7e04373d07a3db38bda0b1d148a6292feddbc644fe02dfe86950a25045d5a4ac
size 56618
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:4f13de390d5293d48e7a360ce61c5bd0a363726a451a61b29a05444d00428bde oid sha256:4691136d112bd2fc4111a4098091702bd630e6bed8fc7b6846da7806bdd7d5cc
size 74128 size 72243
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:1291268bc8c285e9908505c371b3419c943bf694c267a959ab99c65779cdf6ff oid sha256:42ff41e8edc658a8566ebb9d14913d5f53fec54d2a8c338bbd0437e37f55ec28
size 63143 size 61177
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:1f33183a07c36917bec2694c171c89ad4e5ec0adaa4af6c8104435a84af52879
size 89328
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:18800fd1da9c4dd0df37b61398fe8149813794f37577bfc0064fb2236f002e0c
size 100061
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:8b6d8164231a4a6080e4d072708d3b1acc007369e00a5a6f201a48cdf864727c
size 47150
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:7edd4be41770ed698f301c0e309250f9b30e0b6c6a8ff07653a07cb5d270bc3c
size 65967
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:b80ef8df0aba9769a0043bc0c0566d02a2cd1fc7b5f6de759160de11f99151f6
size 179185
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:9f16763c4a89f74509642f65014a50f342901a591fb6aabd1e208c30d0f94044
size 93575
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:4fdd7f67cc4189b862040ccc77e40a2f53570049d00b97f87576fd0f9e6983a0
size 185315
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:b8311f3d620bbdea7ab23b388ee2d75b3fc48c7ac91d6f7f4087665827839139
size 104827
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:9c1ac9798ba13c0bb5b02e30e33496ad901793db6dde53214bc3b9378c87080e
size 116495
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:b37ef180f2c17dfa72f50ca93be65b23f060af632cd745686e4b39e83a38fdb2
size 51302
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:6d645007cbf2bbdc7153408a0709b99db9bb9c38c6ba196141927840baedad99
size 127708
@@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:4a8b0ca34a899b5500d4538f029630dc80859493d36d1010fed3bfe82102528f
size 70245
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:162f3f7d89b385d26a3dd7e83c560e148001271b94458f1c97ab3bc5ba04735e oid sha256:12f8dddc315ccc8ea2d4158254be65769f9d5bcc58bdd7613e4223ae22a36f70
size 173481 size 174040
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:299de08d08e1a8e31555b2cff1f2f74c3724a4f396ac8edff3004ba3500aa78b oid sha256:d7198ec0f5b671f2909415c3d87a499584d4afd6268507b37a7176bb261169fa
size 146568 size 149752
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:d3e4a05c141803ba5c7bdb7fee4c4059d1b28d88614e32c842cd6a5c8b711feb oid sha256:b9130f74c15d8f53f70ab3c6389ee97496f05996f4529864dd84a0854fb99371
size 179948 size 179894
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:a58443a60e339c3041d3c154f056559f558aeabefff42375cd11a1c8aa602c8b oid sha256:bca314935dec069cbc120122a131b512655f861cf8c9e5daa2ae5f1a8766d30f
size 155595 size 160283
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:2b181035e41897519ea7edd67feabdd46727000b7028bf3e2d35fa54b5d90a23 oid sha256:cda8e8481480985513bbba1a25a8621aafef7699d2f1f9297769ea20dc571e32
size 111799 size 111920
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:1ff2b602ea177f6324527e5531720e718c36e922b7606c0bc67f8c5f8b6a9d23 oid sha256:e8d59ded6b52bbdc156eaf01a8a26ed960e64c7d87f2d05c4b7923c4d8cf651d
size 93986 size 96987
@@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1 version https://git-lfs.github.com/spec/v1
oid sha256:f94ecc74654a4a51b6cc927d7fabf70f6465a433811447ce1e1bb0a80ab87cba oid sha256:0bf2e3e38fee10e28c1fa5415e7b97bd07a1c1cddc52d3cfd446fa9fdabb20bf
size 127605 size 128305
@@ -0,0 +1,23 @@
//
// Copyright 2022-2024 New Vector Ltd.
//
// SPDX-License-Identifier: AGPL-3.0-only
// Please see LICENSE in the repository root for full details.
//
import XCTest
@testable import ElementX
@MainActor
class KnockRequestsListScreenViewModelTests: XCTestCase {
var viewModel: KnockRequestsListScreenViewModelProtocol!
var context: KnockRequestsListScreenViewModelType.Context {
viewModel.context
}
override func setUpWithError() throws {
viewModel = KnockRequestsListScreenViewModel(roomProxy: JoinedRoomProxyMock(.init()), mediaProvider: MediaProviderMock())
}
}