feat(ios) added ability to use an external CXProvider and CXCallController

This commit is contained in:
sorinant 2020-12-15 13:21:53 +02:00 committed by GitHub
parent b1a4b58f7a
commit e261bb5616
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 55 additions and 18 deletions

View File

@ -18,6 +18,29 @@
import CallKit import CallKit
import Foundation import Foundation
public protocol CXProviderProtocol: class {
var configuration: CXProviderConfiguration { get set }
func setDelegate(_ delegate: CXProviderDelegate?, queue: DispatchQueue?)
func reportNewIncomingCall(with UUID: UUID, update: CXCallUpdate, completion: @escaping (Error?) -> Void)
func reportCall(with UUID: UUID, updated update: CXCallUpdate)
func reportCall(with UUID: UUID, endedAt dateEnded: Date?, reason endedReason: CXCallEndedReason)
func reportOutgoingCall(with UUID: UUID, startedConnectingAt dateStartedConnecting: Date?)
func reportOutgoingCall(with UUID: UUID, connectedAt dateConnected: Date?)
func invalidate()
}
public protocol CXCallControllerProtocol: class {
var calls: [CXCall] { get }
func request(_ transaction: CXTransaction, completion: @escaping (Error?) -> Swift.Void)
}
extension CXProvider: CXProviderProtocol {}
extension CXCallController: CXCallControllerProtocol {
public var calls: [CXCall] {
return callObserver.calls
}
}
/// JitsiMeet CallKit proxy /// JitsiMeet CallKit proxy
// NOTE: The methods this class exposes are meant to be called in the UI thread. // NOTE: The methods this class exposes are meant to be called in the UI thread.
// All delegate methods called by JMCallKitEmitter will be called in the UI thread. // All delegate methods called by JMCallKitEmitter will be called in the UI thread.
@ -26,11 +49,17 @@ import Foundation
private override init() {} private override init() {}
// MARK: - CallKit proxy // MARK: - CallKit proxy
public static var callKitProvider: CXProviderProtocol?
public static var callKitCallController: CXCallControllerProtocol?
private static var provider: CXProvider = { private static var provider: CXProviderProtocol {
let configuration = CXProviderConfiguration(localizedName: "") callKitProvider ?? defaultProvider
return CXProvider(configuration: configuration) }
}()
private static var callController: CXCallControllerProtocol {
callKitCallController ?? defaultCallController
}
private static var providerConfiguration: CXProviderConfiguration? { private static var providerConfiguration: CXProviderConfiguration? {
didSet { didSet {
@ -39,10 +68,15 @@ import Foundation
provider.setDelegate(emitter, queue: nil) provider.setDelegate(emitter, queue: nil)
} }
} }
private static let callController: CXCallController = { private static let defaultCallController: CXCallController = {
return CXCallController() return CXCallController()
}() }()
private static var defaultProvider: CXProvider = {
let configuration = CXProviderConfiguration(localizedName: "")
return CXProvider(configuration: configuration)
}()
private static let emitter: JMCallKitEmitter = { private static let emitter: JMCallKitEmitter = {
return JMCallKitEmitter() return JMCallKitEmitter()
@ -52,10 +86,16 @@ import Foundation
/// Defaults to enabled, set to false when you don't want to use CallKit. /// Defaults to enabled, set to false when you don't want to use CallKit.
@objc public static var enabled: Bool = true { @objc public static var enabled: Bool = true {
didSet { didSet {
provider.invalidate() if callKitProvider == nil {
provider.invalidate()
}
if enabled { if enabled {
guard isProviderConfigured() else { return; } guard isProviderConfigured() else { return }
provider = CXProvider(configuration: providerConfiguration!) if callKitProvider == nil {
defaultProvider = CXProvider(configuration: providerConfiguration!)
}
provider.setDelegate(emitter, queue: nil) provider.setDelegate(emitter, queue: nil)
} else { } else {
provider.setDelegate(nil, queue: nil) provider.setDelegate(nil, queue: nil)
@ -92,19 +132,18 @@ import Foundation
} }
@objc public static func hasActiveCallForUUID(_ callUUID: String) -> Bool { @objc public static func hasActiveCallForUUID(_ callUUID: String) -> Bool {
let activeCallForUUID = callController.callObserver.calls.first { let activeCallForUUID = callController.calls.first {
$0.uuid == UUID(uuidString: callUUID) $0.uuid == UUID(uuidString: callUUID)
} }
guard activeCallForUUID != nil else { return false } guard activeCallForUUID != nil else { return false }
return true return true
} }
@objc public static func reportNewIncomingCall( @objc public static func reportNewIncomingCall(UUID: UUID,
UUID: UUID, handle: String?,
handle: String?, displayName: String?,
displayName: String?, hasVideo: Bool,
hasVideo: Bool, completion: @escaping (Error?) -> Void) {
completion: @escaping (Error?) -> Void) {
guard enabled else { return } guard enabled else { return }
let callUpdate = makeCXUpdate(handle: handle, let callUpdate = makeCXUpdate(handle: handle,
@ -132,7 +171,6 @@ import Foundation
endedAt dateEnded: Date?, endedAt dateEnded: Date?,
reason endedReason: CXCallEndedReason) { reason endedReason: CXCallEndedReason) {
guard enabled else { return } guard enabled else { return }
provider.reportCall(with: UUID, provider.reportCall(with: UUID,
endedAt: dateEnded, endedAt: dateEnded,
reason: endedReason) reason: endedReason)
@ -142,7 +180,6 @@ import Foundation
with UUID: UUID, with UUID: UUID,
startedConnectingAt dateStartedConnecting: Date?) { startedConnectingAt dateStartedConnecting: Date?) {
guard enabled else { return } guard enabled else { return }
provider.reportOutgoingCall(with: UUID, provider.reportOutgoingCall(with: UUID,
startedConnectingAt: dateStartedConnecting) startedConnectingAt: dateStartedConnecting)
} }