CallKit可以在交换呼叫后重新激活声音

时间:2017-11-21 15:16:43

标签: ios webrtc callkit

我正在开发CallKit应用程序,我遇到了问题,Call Hold无法重新启动音频"交换"调用CallKit屏幕,直到用户返回应用内呼叫屏幕。我可以通过更新来绕过这个:

supportsHolding = false

但是我能解决这个问题,例如whatsapp可以正确地解决这个问题!

P.S。我正在使用webrtc拨打电话!

谢谢!

编辑:

这是提供者代码:

public func provider(_ provider: CXProvider, perform action: CXSetHeldCallAction) {

    guard let call = conductor!.callWithUUID(uuid: action.callUUID) else {
        WebRtcConductor.debug("\(self.TAG)  failed to perform HeldAction: uuid: \(action.uuid), calluiid: \(action.callUUID)")
        action.fail()
        return
    }

    setIsHeld(call: call, isHeld: action.isOnHold)
    action.fulfill()
}

setIsHeld函数只需执行:

audioTrack.isEnabled = enabled

如果我使用"静音" callkit屏幕按钮,一切正常,但是如果我有2个活动呼叫,当我从webrtc调用刷到正常呼叫时,调用CXSetHeldCallAction并禁用音频轨道,如果我再次刷到webrtc呼叫,音频轨道启用但是我没有听到什么,如果我回到主应用程序屏幕,音频再次正常工作!

2 个答案:

答案 0 :(得分:3)

实际上,Google WebRTC库中存在一个局限性,导致实现支持交换呼叫的CallKit集成时出现上述问题。

WebRTC Issue 8126的知名度已超过一年,但尚未集成到WebRTC主分支中。但是,您可以在原始票证中找到必要的代码更改以解决此问题。

但是,作为一种解决方法,您可以触发由WebRTC内部订阅的系统通知。

在CallKit提供程序的“ AVAudioSessionInterruptionType.ended”方法中发布didActivate audioSession通知:

var userInfo = Dictionary<AnyHashable, Any>()
let interrupttioEndedRaw = AVAudioSessionInterruptionType.ended.rawValue
userInfo[AVAudioSessionInterruptionTypeKey] = interrupttioEndedRaw
NotificationCenter.default.post(name: NSNotification.Name.AVAudioSessionInterruption, object: self, userInfo: userInfo)

PS:凝视票证以增加合并的机会;-)

答案 1 :(得分:0)

有同样的问题。如果我有1个活动呼叫,则新呼叫即将进入,我点击保持和接受。新通话有效,但在class Events extends React.Component { render() { const event = this.props.event; return ( <Transition timeout={300} key={event._id} onEntering={el => console.log("Entering", el)} onEnter={el => console.log("enter", el)} onExit={el => console.log("exit", el)} in={true} > <li key={event._id} className="items" > <h1>{event.title}</h1> </li> </Transition> ); } } 音频停止工作后使用Swap后。

发现来自CallKit协议的provider:performSetHeldCallAction:方法是您可以通过CXProviderDelegate原生接口实际停用/激活Swap来电的音频的地方。

在我的情况下,我使用CallKit方法进行了OnHold的调用。 但是,当通过CallKit点击audioController.deactivateAudioSession()按钮时,发现同样的方法provider:performSetHeldCallAction:被激活用于其他被激活的呼叫(来自OnHold状态)。

所以你只需要分别停用/激活音频来调用状态(是否保持)。

通常它应该是这样的:

Swap

P.S。看起来你应该有一些响应Audio会话的类。它应该实现func provider(_ provider: CXProvider, perform action: CXSetHeldCallAction) { // Retrieve the Call instance corresponding to the action's call UUID guard let call = callManager.callWithUUID(uuid: action.callUUID) else { action.fail() return } // Update the Call's underlying hold state. call.isOnHold = action.isOnHold // Stop or start audio in response to holding or unholding the call. if call.isOnHold { stopAudio() } else { startAudio() } // Signal to the system that the action has been successfully performed. action.fulfill() } / activate audio session