Merge branch 'develop' into ismail/4384_room_summary_store

This commit is contained in:
ismailgulek
2021-10-12 11:49:55 +03:00
120 changed files with 3683 additions and 1012 deletions
+10 -15
View File
@@ -19,17 +19,13 @@
#import "AuthenticationViewController.h"
#import "RoomPreviewData.h"
#import "HomeViewController.h"
#import "FavouritesViewController.h"
#import "PeopleViewController.h"
#import "RoomsViewController.h"
#import "GroupsViewController.h"
#import "RoomViewController.h"
#import "ContactDetailsViewController.h"
#import "GroupDetailsViewController.h"
#import "UnifiedSearchViewController.h"
#define TABBAR_HOME_INDEX 0
#define TABBAR_FAVOURITES_INDEX 1
#define TABBAR_PEOPLE_INDEX 2
@@ -175,23 +171,17 @@ typedef NS_ENUM(NSUInteger, MasterTabBarIndex) {
@property (nonatomic, readonly) RoomsViewController *roomsViewController;
@property (nonatomic, readonly) GroupsViewController *groupsViewController;
// The current unified search screen if any
@property (nonatomic, weak) UnifiedSearchViewController *unifiedSearchViewController;
// References on the currently selected room and its view controller
@property (nonatomic, readonly) RoomViewController *currentRoomViewController;
// References on the currently selected room
@property (nonatomic, readonly) NSString *selectedRoomId;
@property (nonatomic, readonly) NSString *selectedEventId;
@property (nonatomic, readonly) MXSession *selectedRoomSession;
@property (nonatomic, readonly) MXKRoomDataSource *selectedRoomDataSource;
@property (nonatomic, readonly) RoomPreviewData *selectedRoomPreviewData;
// References on the currently selected contact and its view controller
@property (nonatomic, readonly) ContactDetailsViewController *currentContactDetailViewController;
// References on the currently selected contact
@property (nonatomic, readonly) MXKContact *selectedContact;
// References on the currently selected group and its view controller
@property (nonatomic, readonly) GroupDetailsViewController *currentGroupDetailViewController;
// References on the currently selected group
@property (nonatomic, readonly) MXGroup *selectedGroup;
@property (nonatomic, readonly) MXSession *selectedGroupSession;
@@ -203,13 +193,18 @@ typedef NS_ENUM(NSUInteger, MasterTabBarIndex) {
- (void)removeTabAt:(MasterTabBarIndex)index;
- (void)selectTabAtIndex:(MasterTabBarIndex)tabBarIndex;
@end
@protocol MasterTabBarControllerDelegate <NSObject>
- (void)masterTabBarControllerDidCompleteAuthentication:(MasterTabBarController *)masterTabBarController;
- (void)masterTabBarController:(MasterTabBarController*)masterTabBarController wantsToDisplayDetailViewController:(UIViewController*)detailViewController;
- (void)masterTabBarController:(MasterTabBarController*)masterTabBarController needsSideMenuIconWithNotification:(BOOL)displayNotification;
- (void)masterTabBarController:(MasterTabBarController *)masterTabBarController didSelectRoomWithId:(NSString*)roomId andEventId:(NSString*)eventId inMatrixSession:(MXSession*)matrixSession completion:(void (^)(void))completion;
- (void)masterTabBarController:(MasterTabBarController *)masterTabBarController didSelectRoomPreviewWithData:(RoomPreviewData*)roomPreviewData;
- (void)masterTabBarController:(MasterTabBarController *)masterTabBarController didSelectContact:(MXKContact*)contact;
- (void)masterTabBarController:(MasterTabBarController *)masterTabBarController didSelectGroup:(MXGroup*)group inMatrixSession:(MXSession*)matrixSession;
@end
+34 -240
View File
@@ -17,8 +17,6 @@
#import "MasterTabBarController.h"
#import "UnifiedSearchViewController.h"
#import "RecentsDataSource.h"
#import "GroupsDataSource.h"
@@ -234,12 +232,6 @@
[[AppDelegate theDelegate] checkAppVersion];
}
if (self.unifiedSearchViewController)
{
[self.unifiedSearchViewController destroy];
self.unifiedSearchViewController = nil;
}
}
- (void)viewDidDisappear:(BOOL)animated
@@ -325,6 +317,12 @@
}
}
- (void)selectTabAtIndex:(MasterTabBarIndex)tabBarIndex
{
NSInteger index = [self indexOfTabItemWithTag:tabBarIndex];
self.selectedIndex = index;
}
#pragma mark -
- (NSArray<MXSession*>*)mxSessions
@@ -588,60 +586,6 @@
}
}
- (void)showRoomDetails
{
[self releaseCurrentDetailsViewController];
if (_selectedRoomPreviewData)
{
// Replace the rootviewcontroller with a room view controller
// Get the RoomViewController from the storyboard
UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"Main" bundle:[NSBundle mainBundle]];
_currentRoomViewController = [storyboard instantiateViewControllerWithIdentifier:@"RoomViewControllerStoryboardId"];
[self.masterTabBarDelegate masterTabBarController:self wantsToDisplayDetailViewController:_currentRoomViewController];
[_currentRoomViewController displayRoomPreview:_selectedRoomPreviewData];
_selectedRoomPreviewData = nil;
[self setupLeftBarButtonItem];
}
else
{
MXWeakify(self);
void (^openRoomDataSource)(MXKRoomDataSource *roomDataSource) = ^(MXKRoomDataSource *roomDataSource) {
MXStrongifyAndReturnIfNil(self);
// Replace the rootviewcontroller with a room view controller
// Get the RoomViewController from the storyboard
UIStoryboard *storyboard = [UIStoryboard storyboardWithName:@"Main" bundle:[NSBundle mainBundle]];
self->_currentRoomViewController = [storyboard instantiateViewControllerWithIdentifier:@"RoomViewControllerStoryboardId"];
[self.masterTabBarDelegate masterTabBarController:self wantsToDisplayDetailViewController:self.currentRoomViewController];
[self.currentRoomViewController displayRoom:roomDataSource];
[self setupLeftBarButtonItem];
};
if (_selectedRoomDataSource)
{
// If the room data source is already loaded, display it
openRoomDataSource(_selectedRoomDataSource);
_selectedRoomDataSource = nil;
}
else
{
// Else, load it. The user may see the EmptyDetailsViewControllerStoryboardId
// screen in this case
[self dataSourceOfRoomToDisplay:^(MXKRoomDataSource *roomDataSource) {
openRoomDataSource(roomDataSource);
}];
}
}
}
- (void)selectRoomWithId:(NSString*)roomId andEventId:(NSString*)eventId inMatrixSession:(MXSession*)matrixSession
{
[self selectRoomWithId:roomId andEventId:eventId inMatrixSession:matrixSession completion:nil];
@@ -649,98 +593,51 @@
- (void)selectRoomWithId:(NSString*)roomId andEventId:(NSString*)eventId inMatrixSession:(MXSession*)matrixSession completion:(void (^)(void))completion
{
if (_selectedRoomId && [_selectedRoomId isEqualToString:roomId]
&& _selectedEventId && [_selectedEventId isEqualToString:eventId]
&& _selectedRoomSession && _selectedRoomSession == matrixSession)
{
// Nothing to do
if (completion)
{
completion();
}
return;
}
[self releaseSelectedItem];
_selectedRoomId = roomId;
_selectedEventId = eventId;
_selectedRoomSession = matrixSession;
_selectedRoomSession = matrixSession;
if (roomId && matrixSession)
{
// Preload the data source before performing the segue
MXWeakify(self);
[self dataSourceOfRoomToDisplay:^(MXKRoomDataSource *roomDataSource) {
MXStrongifyAndReturnIfNil(self);
self->_selectedRoomDataSource = roomDataSource;
[self showRoomDetails];
if (completion)
{
completion();
}
}];
}
else
{
[self releaseSelectedItem];
if (completion)
{
completion();
}
}
[self.masterTabBarDelegate masterTabBarController:self didSelectRoomWithId:roomId andEventId:eventId inMatrixSession:matrixSession completion:completion];
[self refreshSelectedControllerSelectedCellIfNeeded];
}
- (void)showRoomPreview:(RoomPreviewData *)roomPreviewData
{
[self releaseSelectedItem];
_selectedRoomPreviewData = roomPreviewData;
_selectedRoomId = roomPreviewData.roomId;
_selectedRoomSession = roomPreviewData.mxSession;
[self showRoomDetails];
[self.masterTabBarDelegate masterTabBarController:self didSelectRoomPreviewWithData:roomPreviewData];
[self refreshSelectedControllerSelectedCellIfNeeded];
}
- (void)selectContact:(MXKContact*)contact
{
[self releaseSelectedItem];
_selectedContact = contact;
[self showContactDetails];
}
- (void)showContactDetails
{
[self releaseCurrentDetailsViewController];
[self.masterTabBarDelegate masterTabBarController:self didSelectContact:contact];
// Replace the rootviewcontroller with a contact details view controller
_currentContactDetailViewController = [ContactDetailsViewController contactDetailsViewController];
_currentContactDetailViewController.enableVoipCall = NO;
_currentContactDetailViewController.contact = _selectedContact;
[self.masterTabBarDelegate masterTabBarController:self wantsToDisplayDetailViewController:_currentContactDetailViewController];
[self setupLeftBarButtonItem];
[self refreshSelectedControllerSelectedCellIfNeeded];
}
- (void)selectGroup:(MXGroup*)group inMatrixSession:(MXSession*)matrixSession
{
[self releaseSelectedItem];
_selectedGroup = group;
_selectedGroupSession = matrixSession;
[self showGroupDetails];
}
- (void)showGroupDetails
{
[self releaseCurrentDetailsViewController];
[self.masterTabBarDelegate masterTabBarController:self didSelectGroup:group inMatrixSession:matrixSession];
// Replace the rootviewcontroller with a group details view controller
_currentGroupDetailViewController = [GroupDetailsViewController groupDetailsViewController];
[_currentGroupDetailViewController setGroup:_selectedGroup withMatrixSession:_selectedGroupSession];
[self.masterTabBarDelegate masterTabBarController:self wantsToDisplayDetailViewController:_currentGroupDetailViewController];
[self setupLeftBarButtonItem];
[self refreshSelectedControllerSelectedCellIfNeeded];
}
- (void)releaseSelectedItem
@@ -748,15 +645,12 @@
_selectedRoomId = nil;
_selectedEventId = nil;
_selectedRoomSession = nil;
_selectedRoomDataSource = nil;
_selectedRoomPreviewData = nil;
_selectedContact = nil;
_selectedGroup = nil;
_selectedGroupSession = nil;
[self releaseCurrentDetailsViewController];
_selectedGroupSession = nil;
}
- (NSUInteger)missedDiscussionsCount
@@ -844,84 +738,6 @@
#pragma mark -
/**
Load the data source of the room to open.
@param onComplete a block providing the loaded room data source.
*/
- (void)dataSourceOfRoomToDisplay:(void (^)(MXKRoomDataSource *roomDataSource))onComplete
{
// Check whether an event has been selected from messages or files search tab.
MXEvent *selectedSearchEvent = self.unifiedSearchViewController.selectedSearchEvent;
MXSession *selectedSearchEventSession = self.unifiedSearchViewController.selectedSearchEventSession;
if (!selectedSearchEvent)
{
if (!_selectedEventId)
{
// LIVE: Show the room live timeline managed by MXKRoomDataSourceManager
MXKRoomDataSourceManager *roomDataSourceManager = [MXKRoomDataSourceManager sharedManagerForMatrixSession:_selectedRoomSession];
[roomDataSourceManager roomDataSourceForRoom:_selectedRoomId create:YES onComplete:^(MXKRoomDataSource *roomDataSource) {
onComplete(roomDataSource);
}];
}
else
{
// Open the room on the requested event
[RoomDataSource loadRoomDataSourceWithRoomId:_selectedRoomId initialEventId:_selectedEventId andMatrixSession:_selectedRoomSession onComplete:^(id roomDataSource) {
((RoomDataSource*)roomDataSource).markTimelineInitialEvent = YES;
// Give the data source ownership to the room view controller.
self.currentRoomViewController.hasRoomDataSourceOwnership = YES;
onComplete(roomDataSource);
}];
}
}
else
{
// Search result: Create a temp timeline from the selected event
[RoomDataSource loadRoomDataSourceWithRoomId:selectedSearchEvent.roomId initialEventId:selectedSearchEvent.eventId andMatrixSession:selectedSearchEventSession onComplete:^(id roomDataSource) {
[roomDataSource finalizeInitialization];
((RoomDataSource*)roomDataSource).markTimelineInitialEvent = YES;
// Give the data source ownership to the room view controller.
self.currentRoomViewController.hasRoomDataSourceOwnership = YES;
onComplete(roomDataSource);
}];
}
}
- (void)setupLeftBarButtonItem
{
if (self.splitViewController)
{
// Refresh selected cell without scrolling the selected cell (We suppose it's visible here)
[self refreshCurrentSelectedCell:NO];
if (_currentRoomViewController)
{
_currentRoomViewController.navigationItem.leftBarButtonItem = self.splitViewController.displayModeButtonItem;
_currentRoomViewController.navigationItem.leftItemsSupplementBackButton = YES;
}
else if (_currentContactDetailViewController)
{
_currentContactDetailViewController.navigationItem.leftBarButtonItem = self.splitViewController.displayModeButtonItem;
_currentContactDetailViewController.navigationItem.leftItemsSupplementBackButton = YES;
}
else if (_currentGroupDetailViewController)
{
_currentGroupDetailViewController.navigationItem.leftBarButtonItem = self.splitViewController.displayModeButtonItem;
_currentGroupDetailViewController.navigationItem.leftItemsSupplementBackButton = YES;
}
}
}
-(void)setupTitleView
{
titleView = [MainTitleView new];
@@ -936,6 +752,15 @@
[super presentViewController:viewControllerToPresent animated:flag completion:completion];
}
- (void)refreshSelectedControllerSelectedCellIfNeeded
{
if (self.splitViewController)
{
// Refresh selected cell without scrolling the selected cell (We suppose it's visible here)
[self refreshCurrentSelectedCell:NO];
}
}
// Made the actual selected view controller update its selected cell.
- (void)refreshCurrentSelectedCell:(BOOL)forceVisible
{
@@ -947,37 +772,6 @@
}
}
- (void)releaseCurrentDetailsViewController
{
// Release the existing details view controller (if any).
if (_currentRoomViewController)
{
// If the displayed data is not a preview, let the manager release the room data source
// (except if the view controller has the room data source ownership).
if (!_currentRoomViewController.roomPreviewData && _currentRoomViewController.roomDataSource && !_currentRoomViewController.hasRoomDataSourceOwnership)
{
MXSession *mxSession = _currentRoomViewController.roomDataSource.mxSession;
MXKRoomDataSourceManager *roomDataSourceManager = [MXKRoomDataSourceManager sharedManagerForMatrixSession:mxSession];
// Let the manager release live room data sources where the user is in
[roomDataSourceManager closeRoomDataSourceWithRoomId:_currentRoomViewController.roomDataSource.roomId forceClose:NO];
}
[_currentRoomViewController destroy];
_currentRoomViewController = nil;
}
else if (_currentContactDetailViewController)
{
[_currentContactDetailViewController destroy];
_currentContactDetailViewController = nil;
}
else if (_currentGroupDetailViewController)
{
[_currentGroupDetailViewController destroy];
_currentGroupDetailViewController = nil;
}
}
- (void)setHidden:(BOOL)hidden
{
_hidden = hidden;
+187 -89
View File
@@ -18,18 +18,6 @@
import UIKit
/// TabBarCoordinator input parameters
class TabBarCoordinatorParameters {
let userSessionsService: UserSessionsService
let appNavigator: AppNavigatorProtocol
init(userSessionsService: UserSessionsService, appNavigator: AppNavigatorProtocol) {
self.userSessionsService = userSessionsService
self.appNavigator = appNavigator
}
}
@objcMembers
final class TabBarCoordinator: NSObject, TabBarCoordinatorType {
@@ -39,8 +27,10 @@ final class TabBarCoordinator: NSObject, TabBarCoordinatorType {
private let parameters: TabBarCoordinatorParameters
/// Completion called when `popToHomeAnimated:` has been completed.
private var popToHomeViewControllerCompletion: (() -> Void)?
// Indicate if the Coordinator has started once
private var hasStartedOnce: Bool {
return self.masterTabBarController != nil
}
// TODO: Move MasterTabBarController navigation code here
// and if possible use a simple: `private let tabBarController: UITabBarController`
@@ -57,6 +47,10 @@ final class TabBarCoordinator: NSObject, TabBarCoordinatorType {
return parameters.userSessionsService.mainUserSession?.matrixSession
}
private var isTabBarControllerTopMostController: Bool {
return self.navigationRouter.modules.last is MasterTabBarController
}
// MARK: Public
// Must be used only internally
@@ -85,8 +79,8 @@ final class TabBarCoordinator: NSObject, TabBarCoordinatorType {
func start(with spaceId: String?) {
self.currentSpaceId = spaceId
// If start has been done once do setup view controllers again
if self.masterTabBarController == nil {
// If start has been done once do not setup view controllers again
if self.hasStartedOnce == false {
let masterTabBarController = self.createMasterTabBarController()
masterTabBarController.masterTabBarDelegate = self
self.masterTabBarController = masterTabBarController
@@ -102,20 +96,18 @@ final class TabBarCoordinator: NSObject, TabBarCoordinatorType {
}
self.registerUserSessionsServiceNotifications()
self.registerSessionChange()
if let homeViewController = homeViewControllerWrapperViewController {
let versionCheckCoordinator = VersionCheckCoordinator(rootViewController: masterTabBarController,
bannerPresenter: homeViewController,
themeService: ThemeService.shared())
versionCheckCoordinator.start()
add(childCoordinator: versionCheckCoordinator)
}
}
self.updateMasterTabBarController(with: spaceId)
self.registerUserSessionsServiceNotifications()
self.registerSessionChange()
if let homeViewController = homeViewControllerWrapperViewController {
let versionCheckCoordinator = VersionCheckCoordinator(rootViewController: masterTabBarController,
bannerPresenter: homeViewController,
themeService: ThemeService.shared())
versionCheckCoordinator.start()
add(childCoordinator: versionCheckCoordinator)
}
}
func toPresentable() -> UIViewController {
@@ -127,43 +119,70 @@ final class TabBarCoordinator: NSObject, TabBarCoordinatorType {
}
func popToHome(animated: Bool, completion: (() -> Void)?) {
// Force back to the main screen if this is not the one that is displayed
if masterTabBarController != masterNavigationController.visibleViewController {
// Listen to the masterNavigationController changes
// We need to be sure that masterTabBarController is back to the screen
popToHomeViewControllerCompletion = completion
masterNavigationController.delegate = self
let didPopToHome: (() -> Void) = {
// For unknown reason, the navigation bar is not restored correctly by [popToViewController:animated:]
// when a ViewController has hidden it (see MXKAttachmentsViewController).
// Patch: restore navigation bar by default here.
self.masterNavigationController.isNavigationBarHidden = false
if masterNavigationController.viewControllers.last == masterTabBarController {
self.navigationController(masterNavigationController, didShow: masterTabBarController, animated: false)
// Release the current selected item (room/contact/...).
self.masterTabBarController.releaseSelectedItem()
// Select home tab
self.masterTabBarController.selectTab(at: .home)
completion?()
}
// If MasterTabBarController is not visible because there is a modal above it
// but still the top view controller of navigation controller
if self.isTabBarControllerTopMostController {
didPopToHome()
} else {
masterNavigationController.popToViewController(masterTabBarController, animated: animated)
// Otherwise MasterTabBarController is not the top controller of the navigation controller
// Waiting for `self.navigationRouter` popping to MasterTabBarController
var token: NSObjectProtocol?
token = NotificationCenter.default.addObserver(forName: NavigationRouter.didPopModule, object: self.navigationRouter, queue: OperationQueue.main) { [weak self] (notification) in
guard let self = self else {
return
}
// If MasterTabBarController is now the top most controller in navigation controller stack call the completion
if self.isTabBarControllerTopMostController {
didPopToHome()
if let token = token {
NotificationCenter.default.removeObserver(token)
}
}
}
// Pop to root view controller
self.navigationRouter.popToRootModule(animated: animated)
}
} else {
// Tab bar controller is already visible
// Select the Home tab
masterTabBarController.selectedIndex = Int(TABBAR_HOME_INDEX)
masterTabBarController.selectTab(at: .home)
completion?()
}
}
// MARK: - SplitViewMasterPresentable
var collapseDetailViewController: Bool {
if (masterTabBarController.currentRoomViewController == nil) && (masterTabBarController.currentContactDetailViewController == nil) && (masterTabBarController.currentGroupDetailViewController == nil) {
// Return YES to indicate that we have handled the collapse by doing nothing; the secondary controller will be discarded.
return true
} else {
return false
}
}
func secondViewControllerWhenSeparatedFromPrimary() -> UIViewController? {
// Return the top view controller of the master navigation controller, if it is a navigation controller itself.
if let topViewController = masterNavigationController.topViewController as? UINavigationController {
// Keep the detail scene
return topViewController
}
return nil
var selectedNavigationRouter: NavigationRouterType? {
return self.navigationRouter
}
// MARK: - Private methods
@@ -302,6 +321,10 @@ final class TabBarCoordinator: NSObject, TabBarCoordinatorType {
self.parameters.appNavigator.sideMenu.show(from: self.masterTabBarController, animated: true)
}
private func dismissSideMenu(animated: Bool) {
self.parameters.appNavigator.sideMenu.dismiss(animated: animated)
}
// FIXME: Should be displayed per tab.
private func showSettings() {
let viewController = self.createSettingsViewController()
@@ -313,23 +336,96 @@ final class TabBarCoordinator: NSObject, TabBarCoordinatorType {
private func showUnifiedSearch() {
let viewController = self.createUnifiedSearchController()
self.masterTabBarController.unifiedSearchViewController = viewController
self.navigationRouter.push(viewController, animated: true, popCompletion: nil)
}
// FIXME: Should be displayed from a tab.
private func showContactDetails() {
// TODO: Implement
private func showContactDetails(with contact: MXKContact) {
let coordinatorParameters = ContactDetailsCoordinatorParameters(contact: contact)
let coordinator = ContactDetailsCoordinator(parameters: coordinatorParameters)
coordinator.start()
self.add(childCoordinator: coordinator)
self.replaceSplitViewDetails(with: coordinator) { [weak self] in
self?.remove(childCoordinator: coordinator)
}
}
// FIXME: Should be displayed from a tab.
private func showRoomDetails() {
// TODO: Implement
private func showGroupDetails(with group: MXGroup, for matrixSession: MXSession) {
let coordinatorParameters = GroupDetailsCoordinatorParameters(session: matrixSession, group: group)
let coordinator = GroupDetailsCoordinator(parameters: coordinatorParameters)
coordinator.start()
self.add(childCoordinator: coordinator)
self.replaceSplitViewDetails(with: coordinator) {
[weak self] in
self?.remove(childCoordinator: coordinator)
}
}
// FIXME: Should be displayed from a tab.
private func showGroupDetails() {
// TODO: Implement
private func showRoom(with roomId: String) {
guard let matrixSession = self.parameters.userSessionsService.mainUserSession?.matrixSession else {
return
}
self.showRoom(with: roomId, eventId: nil, matrixSession: matrixSession)
}
private func showRoom(with roomId: String, eventId: String?, matrixSession: MXSession, completion: (() -> Void)? = nil) {
// RoomCoordinator will be presented by the split view.
// As we don't know which navigation controller instance will be used,
// give the NavigationRouterStore instance and let it find the associated navigation controller
let roomCoordinatorParameters = RoomCoordinatorParameters(navigationRouterStore: NavigationRouterStore.shared, session: matrixSession, roomId: roomId, eventId: eventId)
self.showRoom(with: roomCoordinatorParameters, completion: completion)
}
private func showRoomPreview(with previewData: RoomPreviewData) {
// RoomCoordinator will be presented by the split view
// We don't which navigation controller instance will be used
// Give the NavigationRouterStore instance and let it find the associated navigation controller if needed
let roomCoordinatorParameters = RoomCoordinatorParameters(navigationRouterStore: NavigationRouterStore.shared, previewData: previewData)
self.showRoom(with: roomCoordinatorParameters)
}
private func showRoom(with parameters: RoomCoordinatorParameters, completion: (() -> Void)? = nil) {
if let topRoomCoordinator = self.splitViewMasterPresentableDelegate?.detailModules.last as? RoomCoordinatorProtocol,
parameters.roomId == topRoomCoordinator.roomId && parameters.session == topRoomCoordinator.mxSession {
// RoomCoordinator with the same room id and Matrix session is shown
if let eventId = parameters.eventId {
// If there is an event id ask the RoomCoordinator to start with this one
topRoomCoordinator.start(withEventId: eventId, completion: completion)
} else {
// If there is no event id defined do nothing
completion?()
}
return
}
let coordinator = RoomCoordinator(parameters: parameters)
coordinator.delegate = self
coordinator.start(withCompletion: completion)
self.add(childCoordinator: coordinator)
self.replaceSplitViewDetails(with: coordinator) {
[weak self] in
// NOTE: The RoomDataSource releasing is handled in SplitViewCoordinator
self?.remove(childCoordinator: coordinator)
}
}
/// If the split view is collapsed (one column visible) it will push the Presentable on the primary navigation controller, otherwise it will show the Presentable as the secondary view of the split view.
private func replaceSplitViewDetails(with presentable: Presentable, popCompletion: (() -> Void)? = nil) {
self.splitViewMasterPresentableDelegate?.splitViewMasterPresentable(self, wantsToReplaceDetailWith: presentable, popCompletion: popCompletion)
}
// MARK: UserSessions management
@@ -387,45 +483,27 @@ final class TabBarCoordinator: NSObject, TabBarCoordinatorType {
}
}
// MARK: - UINavigationControllerDelegate
extension TabBarCoordinator: UINavigationControllerDelegate {
func navigationController(_ navigationController: UINavigationController, didShow viewController: UIViewController, animated: Bool) {
if viewController == masterTabBarController {
masterNavigationController.delegate = nil
// For unknown reason, the navigation bar is not restored correctly by [popToViewController:animated:]
// when a ViewController has hidden it (see MXKAttachmentsViewController).
// Patch: restore navigation bar by default here.
masterNavigationController.isNavigationBarHidden = false
// Release the current selected item (room/contact/...).
masterTabBarController.releaseSelectedItem()
if let popToHomeViewControllerCompletion = self.popToHomeViewControllerCompletion {
let popToHomeViewControllerCompletion2: (() -> Void)? = popToHomeViewControllerCompletion
self.popToHomeViewControllerCompletion = nil
DispatchQueue.main.async {
popToHomeViewControllerCompletion2?()
}
}
}
}
}
// MARK: - MasterTabBarControllerDelegate
extension TabBarCoordinator: MasterTabBarControllerDelegate {
func masterTabBarController(_ masterTabBarController: MasterTabBarController!, didSelectRoomPreviewWith roomPreviewData: RoomPreviewData!) {
self.showRoomPreview(with: roomPreviewData)
}
func masterTabBarController(_ masterTabBarController: MasterTabBarController!, didSelect contact: MXKContact!) {
self.showContactDetails(with: contact)
}
func masterTabBarControllerDidCompleteAuthentication(_ masterTabBarController: MasterTabBarController!) {
self.delegate?.tabBarCoordinatorDidCompleteAuthentication(self)
}
func masterTabBarController(_ masterTabBarController: MasterTabBarController!, wantsToDisplayDetailViewController detailViewController: UIViewController!) {
self.splitViewMasterPresentableDelegate?.splitViewMasterPresentable(self, wantsToDisplay: detailViewController)
func masterTabBarController(_ masterTabBarController: MasterTabBarController!, didSelectRoomWithId roomId: String!, andEventId eventId: String!, inMatrixSession matrixSession: MXSession!, completion: (() -> Void)!) {
self.showRoom(with: roomId, eventId: eventId, matrixSession: matrixSession, completion: completion)
}
func masterTabBarController(_ masterTabBarController: MasterTabBarController!, didSelect group: MXGroup!, inMatrixSession matrixSession: MXSession!) {
self.showGroupDetails(with: group, for: matrixSession)
}
func masterTabBarController(_ masterTabBarController: MasterTabBarController!, needsSideMenuIconWithNotification displayNotification: Bool) {
@@ -439,6 +517,26 @@ extension TabBarCoordinator: MasterTabBarControllerDelegate {
}
}
// MARK: - RoomCoordinatorDelegate
extension TabBarCoordinator: RoomCoordinatorDelegate {
func roomCoordinatorDidDismissInteractively(_ coordinator: RoomCoordinatorProtocol) {
self.remove(childCoordinator: coordinator)
}
func roomCoordinatorDidLeaveRoom(_ coordinator: RoomCoordinatorProtocol) {
self.navigationRouter.popModule(animated: true)
}
func roomCoordinatorDidCancelRoomPreview(_ coordinator: RoomCoordinatorProtocol) {
self.navigationRouter.popModule(animated: true)
}
func roomCoordinator(_ coordinator: RoomCoordinatorProtocol, didSelectRoomWithId roomId: String) {
self.showRoom(with: roomId)
}
}
// MARK: - UIGestureRecognizerDelegate
/**
@@ -0,0 +1,29 @@
//
// Copyright 2021 New Vector Ltd
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
import Foundation
/// TabBarCoordinator input parameters
class TabBarCoordinatorParameters {
let userSessionsService: UserSessionsService
let appNavigator: AppNavigatorProtocol
init(userSessionsService: UserSessionsService, appNavigator: AppNavigatorProtocol) {
self.userSessionsService = userSessionsService
self.appNavigator = appNavigator
}
}