element-ios/Riot/Modules/Room/RoomCoordinatorBridgePresenter.swift
2021-10-08 17:15:14 +02:00

145 lines
5.5 KiB
Swift

//
// 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
@objc protocol RoomCoordinatorBridgePresenterDelegate {
func roomCoordinatorBridgePresenterDidLeaveRoom(_ bridgePresenter: RoomCoordinatorBridgePresenter)
func roomCoordinatorBridgePresenterDidCancelRoomPreview(_ bridgePresenter: RoomCoordinatorBridgePresenter)
func roomCoordinatorBridgePresenter(_ bridgePresenter: RoomCoordinatorBridgePresenter, didSelectRoomWithId roomId: String)
func roomCoordinatorBridgePresenterDidDismissInteractively(_ bridgePresenter: RoomCoordinatorBridgePresenter)
}
@objcMembers
class RoomCoordinatorBridgePresenterParameters: NSObject {
/// The matrix session in which the room should be available.
let session: MXSession
/// The room identifier
let roomId: String
/// If not nil, the room will be opened on this event.
let eventId: String?
/// The data for the room preview.
let previewData: RoomPreviewData?
init(session: MXSession,
roomId: String,
eventId: String?,
previewData: RoomPreviewData?) {
self.session = session
self.roomId = roomId
self.eventId = eventId
self.previewData = previewData
}
}
/// RoomCoordinatorBridgePresenter enables to start RoomCoordinator from a view controller.
/// This bridge is used while waiting for global usage of coordinator pattern.
/// **WARNING**: This class breaks the Coordinator abstraction and it has been introduced for **Objective-C compatibility only** (mainly for integration in legacy view controllers). Each bridge should be removed once the underlying Coordinator has been integrated by another Coordinator.
@objcMembers
final class RoomCoordinatorBridgePresenter: NSObject {
// MARK: - Properties
// MARK: Private
private let bridgeParameters: RoomCoordinatorBridgePresenterParameters
private var coordinator: RoomCoordinator?
// MARK: Public
weak var delegate: RoomCoordinatorBridgePresenterDelegate?
// MARK: - Setup
init(parameters: RoomCoordinatorBridgePresenterParameters) {
self.bridgeParameters = parameters
super.init()
}
// MARK: - Public
func present(from viewController: UIViewController, animated: Bool) {
let coordinator = self.createRoomCoordinator()
coordinator.delegate = self
let presentable = coordinator.toPresentable()
presentable.modalPresentationStyle = .formSheet
viewController.present(presentable, animated: animated, completion: nil)
coordinator.start()
self.coordinator = coordinator
}
func push(from navigationController: UINavigationController, animated: Bool) {
let navigationRouter = NavigationRouterStore.shared.navigationRouter(for: navigationController)
let coordinator = self.createRoomCoordinator(with: navigationRouter)
coordinator.delegate = self
coordinator.start() // Will trigger view controller push
self.coordinator = coordinator
}
func dismiss(animated: Bool, completion: (() -> Void)?) {
guard let coordinator = self.coordinator else {
return
}
coordinator.toPresentable().dismiss(animated: animated) {
self.coordinator = nil
completion?()
}
}
// MARK: - Private
private func createRoomCoordinator(with navigationRouter: NavigationRouterType = NavigationRouter(navigationController: RiotNavigationController())) -> RoomCoordinator {
let coordinatorParameters: RoomCoordinatorParameters
if let previewData = self.bridgeParameters.previewData {
coordinatorParameters = RoomCoordinatorParameters(navigationRouter: navigationRouter, previewData: previewData)
} else {
coordinatorParameters = RoomCoordinatorParameters(navigationRouter: navigationRouter, session: self.bridgeParameters.session, roomId: self.bridgeParameters.roomId, eventId: self.bridgeParameters.eventId)
}
return RoomCoordinator(parameters: coordinatorParameters)
}
}
// MARK: - RoomNotificationSettingsCoordinatorDelegate
extension RoomCoordinatorBridgePresenter: RoomCoordinatorDelegate {
func roomCoordinator(_ coordinator: RoomCoordinatorProtocol, didSelectRoomWithId roomId: String) {
self.delegate?.roomCoordinatorBridgePresenter(self, didSelectRoomWithId: roomId)
}
func roomCoordinatorDidLeaveRoom(_ coordinator: RoomCoordinatorProtocol) {
self.delegate?.roomCoordinatorBridgePresenterDidLeaveRoom(self)
}
func roomCoordinatorDidCancelRoomPreview(_ coordinator: RoomCoordinatorProtocol) {
self.delegate?.roomCoordinatorBridgePresenterDidCancelRoomPreview(self)
}
func roomCoordinatorDidDismissInteractively(_ coordinator: RoomCoordinatorProtocol) {
self.delegate?.roomCoordinatorBridgePresenterDidDismissInteractively(self)
}
}