Added registration code for incoming calls, add incoming call actions to the UI
This commit is contained in:
@@ -84,11 +84,11 @@
|
||||
children = (
|
||||
6604165624D451F10064FC6C /* AppDelegate.swift */,
|
||||
6604165824D451F10064FC6C /* SceneDelegate.swift */,
|
||||
6604166A24D453240064FC6C /* CallExample.swift */,
|
||||
6604165A24D451F10064FC6C /* ContentView.swift */,
|
||||
6604165C24D451F40064FC6C /* Assets.xcassets */,
|
||||
6604166124D451F40064FC6C /* LaunchScreen.storyboard */,
|
||||
6604166424D451F40064FC6C /* Info.plist */,
|
||||
6604166A24D453240064FC6C /* CallExample.swift */,
|
||||
6604165E24D451F40064FC6C /* Preview Content */,
|
||||
);
|
||||
path = CallTutorial;
|
||||
|
||||
@@ -29,18 +29,18 @@ class CallExampleContext : ObservableObject
|
||||
@Published var videoEnabled : Bool = false
|
||||
@Published var speakerEnabled : Bool = false
|
||||
@Published var callRunning : Bool = false
|
||||
@Published var isCallIncoming : Bool = false
|
||||
@Published var dest : String = "sip:arguillq@sip.linphone.org"
|
||||
|
||||
|
||||
var proxy_cfg: ProxyConfig!
|
||||
let mRegistrationDelegate = LinphoneRegistrationDelegate()
|
||||
@Published var id : String = "sip:peche5@sip.linphone.org"
|
||||
@Published var passwd : String = "peche5"
|
||||
@Published var loggedIn: Bool = false
|
||||
|
||||
|
||||
init()
|
||||
{
|
||||
mCallStateTracer.tutorialContext = self
|
||||
mRegistrationDelegate.tutorialContext = self
|
||||
|
||||
let factory = Factory.Instance // Instanciate
|
||||
|
||||
@@ -59,9 +59,35 @@ class CallExampleContext : ObservableObject
|
||||
try? mCore.start()
|
||||
|
||||
mVideoDevices = mCore.videoDevicesList
|
||||
|
||||
registrationExample()
|
||||
|
||||
mCore.addDelegate(delegate: mCallStateTracer)
|
||||
mCore.addDelegate(delegate: mRegistrationDelegate)
|
||||
}
|
||||
|
||||
func registrationExample()
|
||||
{
|
||||
|
||||
let factory = Factory.Instance
|
||||
do {
|
||||
let proxy_cfg = try mCore.createProxyConfig()
|
||||
let address = try factory.createAddress(addr: id)
|
||||
let info = try factory.createAuthInfo(username: address.username, userid: "", passwd: passwd, ha1: "", realm: "", domain: address.domain)
|
||||
mCore.addAuthInfo(info: info)
|
||||
|
||||
try proxy_cfg.setIdentityaddress(newValue: address)
|
||||
let server_addr = "sip:" + address.domain + ";transport=tls"
|
||||
try proxy_cfg.setServeraddr(newValue: server_addr)
|
||||
proxy_cfg.registerEnabled = true
|
||||
try mCore.addProxyConfig(config: proxy_cfg)
|
||||
if ( mCore.defaultProxyConfig == nil)
|
||||
{
|
||||
// IMPORTANT : default proxy config setting MUST be done AFTER adding the config to the core !
|
||||
mCore.defaultProxyConfig = proxy_cfg
|
||||
}
|
||||
|
||||
} catch {
|
||||
print(error)
|
||||
}
|
||||
}
|
||||
|
||||
// Initiate a call
|
||||
@@ -82,7 +108,6 @@ class CallExampleContext : ObservableObject
|
||||
print("Could not place call to \(dest)\n")
|
||||
} else {
|
||||
print("Call to \(dest) is in progress...")
|
||||
callRunning = true
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -96,18 +121,16 @@ class CallExampleContext : ObservableObject
|
||||
}
|
||||
|
||||
// Terminate a call
|
||||
func stopOutgoingCallExample()
|
||||
func stopCall()
|
||||
{
|
||||
if (callRunning)
|
||||
{
|
||||
callRunning = false
|
||||
if (mCall.state != Call.State.End){
|
||||
// terminate the call
|
||||
print("Terminating the call...\n")
|
||||
do {
|
||||
try mCall.terminate()
|
||||
} catch {
|
||||
callRunning = true
|
||||
print(error)
|
||||
}
|
||||
}
|
||||
@@ -138,67 +161,13 @@ class CallExampleContext : ObservableObject
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
func acceptCall(incomingCall call : Call)
|
||||
{
|
||||
mCall = call
|
||||
do {
|
||||
try call.accept()
|
||||
} catch {
|
||||
print(error)
|
||||
}
|
||||
}
|
||||
*/
|
||||
|
||||
func createProxyConfigAndRegister(identity sId : String, password sPwd : String, factoryUri fUri : String) -> ProxyConfig?
|
||||
func acceptCall()
|
||||
{
|
||||
let factory = Factory.Instance
|
||||
do {
|
||||
let proxy_cfg = try mCore.createProxyConfig()
|
||||
let address = try factory.createAddress(addr: sId)
|
||||
let info = try factory.createAuthInfo(username: address.username, userid: "", passwd: sPwd, ha1: "", realm: "", domain: address.domain)
|
||||
mCore.addAuthInfo(info: info)
|
||||
|
||||
try proxy_cfg.setIdentityaddress(newValue: address)
|
||||
let server_addr = "sip:" + address.domain + ";transport=tls"
|
||||
try proxy_cfg.setServeraddr(newValue: server_addr)
|
||||
proxy_cfg.registerEnabled = true
|
||||
proxy_cfg.conferenceFactoryUri = fUri
|
||||
try mCore.addProxyConfig(config: proxy_cfg)
|
||||
if ( mCore.defaultProxyConfig == nil)
|
||||
{
|
||||
// IMPORTANT : default proxy config setting MUST be done AFTER adding the config to the core !
|
||||
mCore.defaultProxyConfig = proxy_cfg
|
||||
}
|
||||
return proxy_cfg
|
||||
|
||||
} catch {
|
||||
print(error)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func registrationExample()
|
||||
{
|
||||
let factory = Factory.Instance
|
||||
do {
|
||||
let proxy_cfg = try mCore.createProxyConfig()
|
||||
let address = try factory.createAddress(addr: id)
|
||||
let info = try factory.createAuthInfo(username: address.username, userid: "", passwd: passwd, ha1: "", realm: "", domain: address.domain)
|
||||
mCore.addAuthInfo(info: info)
|
||||
|
||||
try proxy_cfg.setIdentityaddress(newValue: address)
|
||||
let server_addr = "sip:" + address.domain + ";transport=tls"
|
||||
try proxy_cfg.setServeraddr(newValue: server_addr)
|
||||
proxy_cfg.registerEnabled = true
|
||||
try mCore.addProxyConfig(config: proxy_cfg)
|
||||
if ( mCore.defaultProxyConfig == nil)
|
||||
{
|
||||
// IMPORTANT : default proxy config setting MUST be done AFTER adding the config to the core !
|
||||
mCore.defaultProxyConfig = proxy_cfg
|
||||
}
|
||||
loggedIn = true
|
||||
|
||||
try mCall.accept()
|
||||
callRunning = true
|
||||
isCallIncoming = false
|
||||
} catch {
|
||||
print(error)
|
||||
}
|
||||
@@ -206,7 +175,18 @@ class CallExampleContext : ObservableObject
|
||||
|
||||
}
|
||||
|
||||
|
||||
class LinphoneRegistrationDelegate: CoreDelegate {
|
||||
|
||||
var tutorialContext : CallExampleContext!
|
||||
|
||||
override func onRegistrationStateChanged(lc: Core, cfg: ProxyConfig, cstate: RegistrationState, message: String?) {
|
||||
print("New registration state \(cstate) for user id \( String(describing: cfg.identityAddress?.asString()))\n")
|
||||
if (cstate == .Ok)
|
||||
{
|
||||
tutorialContext.loggedIn = true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class LinphoneLoggingServiceManager: LoggingServiceDelegate {
|
||||
@@ -221,38 +201,20 @@ class LinphoneLoggingServiceManager: LoggingServiceDelegate {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
let mCallStateTracer = CallStateDelegate()
|
||||
class CallStateDelegate: CoreDelegate {
|
||||
|
||||
var tutorialContext : CallExampleContext!
|
||||
|
||||
override func onCallStateChanged(lc: Core, call: Call, cstate: Call.State, message: String) {
|
||||
print("CallTrace - \(cstate)")
|
||||
/*
|
||||
let traceFn = { print("CallTrace - \(cstate)") }
|
||||
switch cstate
|
||||
{
|
||||
case .IncomingReceived:
|
||||
tutorialContext.acceptCall(incomingCall: call)
|
||||
case .IncomingEarlyMedia:
|
||||
traceFn()
|
||||
case .PushIncomingReceived:
|
||||
traceFn()
|
||||
case .OutgoingRinging:
|
||||
print("CallTrace - It is now ringing remotely !\n")
|
||||
case .OutgoingEarlyMedia:
|
||||
print("CallTrace - Receiving some early media\n")
|
||||
case .Connected:
|
||||
print("CallTrace - We are connected !\n")
|
||||
case .StreamsRunning:
|
||||
print("CallTrace - Media streams established !\n")
|
||||
case .End:
|
||||
print("CallTrace - Call is terminated.\n")
|
||||
case .Error:
|
||||
print("CallTrace - Call failure !")
|
||||
default:
|
||||
print("CallTrace - Unhandled notification \(cstate)\n")
|
||||
if (cstate == .IncomingReceived) {
|
||||
tutorialContext.mCall = call
|
||||
tutorialContext.isCallIncoming = true
|
||||
} else if (cstate == .OutgoingRinging) {
|
||||
tutorialContext.callRunning = true
|
||||
} else if (cstate == .End) {
|
||||
tutorialContext.callRunning = false
|
||||
}
|
||||
*/
|
||||
}
|
||||
}
|
||||
|
||||
@@ -12,18 +12,73 @@ struct ContentView: View {
|
||||
|
||||
@ObservedObject var tutorialContext = CallExampleContext()
|
||||
|
||||
func getCallButtonText() -> String
|
||||
{
|
||||
if (tutorialContext.isCallIncoming) {
|
||||
return "Answer"
|
||||
}
|
||||
else if (tutorialContext.callRunning) {
|
||||
return "Update Call"
|
||||
}
|
||||
else {
|
||||
return "Call"
|
||||
}
|
||||
}
|
||||
|
||||
func callStateString() -> String
|
||||
{
|
||||
if (tutorialContext.isCallIncoming) {
|
||||
return "Incoming call"
|
||||
}
|
||||
else if (tutorialContext.callRunning) {
|
||||
return "Call running"
|
||||
}
|
||||
else {
|
||||
return "No Call"
|
||||
}
|
||||
}
|
||||
|
||||
var body: some View {
|
||||
|
||||
VStack(alignment: .leading) {
|
||||
Group {
|
||||
HStack {
|
||||
Text("Identity :")
|
||||
.font(.subheadline)
|
||||
TextField("", text : $tutorialContext.id)
|
||||
.textFieldStyle(RoundedBorderTextFieldStyle())
|
||||
}
|
||||
HStack {
|
||||
Text("Password :")
|
||||
.font(.subheadline)
|
||||
TextField("", text : $tutorialContext.passwd)
|
||||
.textFieldStyle(RoundedBorderTextFieldStyle())
|
||||
}
|
||||
HStack {
|
||||
Button(action: tutorialContext.registrationExample)
|
||||
{
|
||||
Text("Login")
|
||||
.font(.largeTitle)
|
||||
.foregroundColor(Color.white)
|
||||
.frame(width: 90.0, height: 42.0)
|
||||
.background(Color.gray)
|
||||
}
|
||||
Text("Login State : ")
|
||||
.font(.footnote)
|
||||
Text(tutorialContext.loggedIn ? "Looged in" : "Unregistered")
|
||||
.font(.footnote)
|
||||
.foregroundColor(tutorialContext.loggedIn ? Color.green : Color.black)
|
||||
}
|
||||
}
|
||||
VStack(spacing: 0.0) {
|
||||
Text("Call Settings")
|
||||
.font(.largeTitle)
|
||||
.padding(.top, 5)
|
||||
HStack {
|
||||
Text("Call destination :")
|
||||
TextField("", text : $tutorialContext.dest)
|
||||
.textFieldStyle(RoundedBorderTextFieldStyle())
|
||||
}
|
||||
.padding(.top)
|
||||
.padding(.top, 5)
|
||||
}
|
||||
VStack(alignment: .leading) {
|
||||
Toggle(isOn: $tutorialContext.audioEnabled) {
|
||||
@@ -56,15 +111,22 @@ struct ContentView: View {
|
||||
Spacer()
|
||||
VStack {
|
||||
HStack {
|
||||
Button(action: tutorialContext.outgoingCallExample)
|
||||
Button(action: {
|
||||
if (self.tutorialContext.isCallIncoming) {
|
||||
self.tutorialContext.acceptCall()
|
||||
}
|
||||
else {
|
||||
self.tutorialContext.outgoingCallExample()
|
||||
}
|
||||
})
|
||||
{
|
||||
Text(tutorialContext.callRunning ? "Update Call" : "Call")
|
||||
Text(getCallButtonText())
|
||||
.font(.largeTitle)
|
||||
.foregroundColor(Color.white)
|
||||
.frame(width: 180.0, height: 42.0)
|
||||
.background(Color.green)
|
||||
}
|
||||
Button(action: tutorialContext.stopOutgoingCallExample) {
|
||||
Button(action: tutorialContext.stopCall) {
|
||||
Text("Stop Call")
|
||||
.font(.largeTitle)
|
||||
.foregroundColor(Color.white)
|
||||
@@ -73,11 +135,9 @@ struct ContentView: View {
|
||||
}
|
||||
}
|
||||
HStack {
|
||||
Text("Call State : ")
|
||||
Text(callStateString())
|
||||
.font(.footnote)
|
||||
Text(tutorialContext.callRunning ? "Ongoing" : "Stopped")
|
||||
.font(.footnote)
|
||||
.foregroundColor(tutorialContext.callRunning ? Color.green : Color.black)
|
||||
.foregroundColor(tutorialContext.callRunning || tutorialContext.isCallIncoming ? Color.green : Color.black)
|
||||
}
|
||||
.padding(.top)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user