// // InvitationObserverService.swift // TUIRoomKit // // Created by jeremiawang on 2024/8/23. // import Foundation import RTCRoomEngine import Factory import TUICore import Combine public class InvitationObserverService: NSObject { @objc public static let shared = InvitationObserverService() private var invitationWindow: UIWindow? private var getInvitationListCursor: String = "" private let singleFetchCount: Int = 20 private let bellFeature = BellFeature() private let vibrationFeature = VibrationFeature() private override init() { } @objc public func show(extString: String) { let store = Container.shared.conferenceStore() let isEnteredRoom = store.selectCurrent(RoomSelectors.getIsEnteredRoom) if isEnteredRoom || invitationWindow != nil { return } guard let dict = extString.convertToDic() else { return } guard let roomId = dict["RoomId"] as? String else { return } guard let roomName = dict["RoomName"] as? String else { return } guard let ownerName = dict["OwnerName"] as? String else { return } guard let memberCount = dict["MemberCount"] as? Int else { return } var roomInfo = RoomInfo() roomInfo.roomId = roomId roomInfo.name = roomName roomInfo.ownerName = ownerName roomInfo.memberCount = memberCount self.getInvitationList(roomInfo: roomInfo) } func showInvitationWindow(roomInfo: RoomInfo, invitation: TUIInvitation) { DispatchQueue.main.async { let invitationViewController = ConferenceInvitationViewController(roomInfo: roomInfo, invitation: invitation) self.invitationWindow = UIWindow() self.invitationWindow?.windowLevel = .alert + 1 self.invitationWindow?.rootViewController = invitationViewController self.invitationWindow?.isHidden = false self.invitationWindow?.t_makeKeyAndVisible() } } func dismissInvitationWindow() { DispatchQueue.main.async { self.invitationWindow?.isHidden = true self.invitationWindow = nil } } func playCallingBellAndVibration() { bellFeature.playBell() vibrationFeature.playVibrate() } func stopCallingBellAndVibration() { bellFeature.stopBell() vibrationFeature.stopVibrate() } private func getInvitationList(roomInfo: RoomInfo) { let invitationManager = TUIRoomEngine.sharedInstance().getExtension(extensionType: .conferenceInvitationManager) as? TUIConferenceInvitationManager let selfUserId = TUILogin.getUserID() invitationManager?.getInvitationList(roomInfo.roomId, cursor: getInvitationListCursor, count: singleFetchCount) { [weak self] invitations, cursor in guard let self = self else { return } for invitation in invitations { if invitation.invitee.userId != selfUserId { continue } if invitation.status == .pending { self.showInvitationWindow(roomInfo: roomInfo, invitation: invitation) self.playCallingBellAndVibration() return } } self.getInvitationListCursor = cursor if !cursor.isEmpty { self.getInvitationList(roomInfo: roomInfo) } } onError: { error, message in } } } extension InvitationObserverService: TUIConferenceInvitationObserver { public func onReceiveInvitation(roomInfo: TUIRoomInfo, invitation: TUIInvitation, extensionInfo: String) { let store = Container.shared.conferenceStore() store.dispatch(action: ConferenceInvitationActions.onReceiveInvitation(payload: (roomInfo, invitation))) } public func onInvitationHandledByOtherDevice(roomInfo: TUIRoomInfo, accepted: Bool) { } public func onInvitationCancelled(roomInfo: TUIRoomInfo, invitation: TUIInvitation) { } public func onInvitationAccepted(roomInfo: TUIRoomInfo, invitation: TUIInvitation) { } public func onInvitationRejected(roomInfo: TUIRoomInfo, invitation: TUIInvitation, reason: TUIInvitationRejectedReason) { } public func onInvitationTimeout(roomInfo: TUIRoomInfo, invitation: TUIInvitation) { } public func onInvitationRevokedByAdmin(roomInfo: TUIRoomInfo, invitation: TUIInvitation, admin: TUIUserInfo) { } public func onInvitationAdded(roomId: String, invitation: TUIInvitation) { } public func onInvitationRemoved(roomId: String, invitation: TUIInvitation) { } public func onInvitationStatusChanged(roomId: String, invitation: TUIInvitation) { } } extension UIWindow { public func t_makeKeyAndVisible() { if #available(iOS 13.0, *) { for windowScene in UIApplication.shared.connectedScenes { if windowScene.activationState == UIScene.ActivationState.foregroundActive || windowScene.activationState == UIScene.ActivationState.background { self.windowScene = windowScene as? UIWindowScene break } } } self.makeKeyAndVisible() } }