iOS - VialerSIP - отправка DTMF через Inband
Я использую VialerSIP для своего приложения iOS VOIP.
Я пытаюсь отправить DTMF через inband вместо метода:
- (BOOL)sendDTMF:(NSString * _Nonnull)character error:(NSError * _Nullable * _Nullable)error;
в классе VSLCall.
Потому что, похоже, некоторые страны (включая мою) не поддерживают:
PJMEDIA_RTP_PT_TELEPHONE_EVENTS 101
Итак, я решил отправить DTMF через inband с этим решением: https://www.google.com/url?sa=t&rct=j&q=&esrc=s&source=web&cd=1&cad=rja&uact=8&ved=2ahUKEwibuKSeg4HgAhUM6LwKHTECAAHHTQHAQAHQHHTQHAHQHOQHOQHOQHOQHPH % 2Ftrac.pjsip.org% 2Frepos% 2Fwiki% 2FFAQ% 23inband-USG & DTMF = AOvVaw3fYXthR0Z6btU2yOWovNIF
вот так (по-быстрому):
private func generateTone(_ callId: pjsua_call_id) -> UnsafeMutableRawPointer {
var ci = pjsua_call_info()
let pool = pjsua_pool_create("MyCall", 512, 512)!
let cd = pj_pool_zalloc(pool, MemoryLayout<MyCallData>.size)!
cd.storeBytes(of: pool.pointee, as: pj_pool_t.self)
let aPool = cd.assumingMemoryBound(to: pj_pool_t.self)
var aTonegen: UnsafeMutablePointer<pjmedia_port>? = cd.assumingMemoryBound(to: pjmedia_port.self)
let aToneslot = cd.assumingMemoryBound(to: pjsua_conf_port_id.self)
pjmedia_tonegen_create(aPool, 8000, 1, 160, 16, 0, &aTonegen)
pjsua_conf_add_port(aPool, aTonegen!, aToneslot)
pjsua_call_get_info(callId, &ci)
pjsua_conf_connect(aToneslot.pointee, ci.conf_slot)
pjsua_call_set_user_data(callId, cd)
return cd
}
private func play(callId: pjsua_call_id, digits: String) {
let cString = digits.cString(using: String.defaultCStringEncoding)!
let newString: String = NSString(bytes: cString, length: Int(digits.count), encoding:String.Encoding.ascii.rawValue)! as String
let key2Pointer = UnsafePointer<Int8>(newString)
let cd = pjsua_call_get_user_data(callId) ?? generateTone(callId)
let tonegen = cd.assumingMemoryBound(to: pjmedia_port.self)
var tone = pjmedia_tone_digit(digit: key2Pointer.pointee, on_msec: 100, off_msec: 200, volume: 0)
pjmedia_tonegen_play_digits(tonegen, 1, &tone, 0)
}
private func deinitTone(callId: pjsua_call_id) {
guard let cd = pjsua_call_get_user_data(callId) else { return }
let aPool = cd.assumingMemoryBound(to: pj_pool_t.self)
let aTonegen = cd.assumingMemoryBound(to: pjmedia_port.self)
let aToneslot = cd.assumingMemoryBound(to: pjsua_conf_port_id.self)
pjsua_conf_remove_port(aToneslot.pointee)
pjmedia_port_destroy(aTonegen)
pj_pool_release(aPool)
pjsua_call_set_user_data(callId, nil)
}
Затем я попытался отправить DTMF с помощью:
self.play(callId: pjsua_call_id(self.activeCall.callId), digits: numberString)
Но когда я вызываю эту функцию, процессор переполняется. Я не знаю почему:(.
Пожалуйста, дайте мне любой совет, это будет огромной помощью для решения моей проблемы.
Спасибо.