Devang Goswami
Devang Goswami

Reputation: 43

How can we handle multiple calls with pjsip and callkit

We are facing an issue regarding callKit Framework by iOS.

We have to implement following functionalities in app.

Issue : The issues we are facing are :

We have done following implementation for handling multiple calls :

We are reporting new call by following method.

- (void)reportNewIncomingCallWithUUID:(nonnull NSUUID *)UUID handle:(nonnull NSString *)handle
                       completion:(nullable void (^)(NSError *_Nullable error))completion {

CXCallUpdate *update = [[CXCallUpdate alloc] init];
update.remoteHandle = [[CXHandle alloc] initWithType:CXHandleTypeGeneric value:handle];
update.hasVideo = NO;
update.supportsDTMF = YES;
update.supportsHolding = YES;
update.supportsGrouping = YES;
update.supportsUngrouping = YES;    
[_provider reportNewIncomingCallWithUUID:UUID update:update completion:^(NSError * _Nullable error) {
    completion(error);
    if (!error) {
    }
}];     
}

On second call It will ask user for (End & Accept) OR (Hold & Accept)

this is how we are getting second call view

When we click on hold and accept

    - (BOOL)provider:(CXProvider *)provider executeTransaction:(CXTransaction* )transaction
{
    NSLog(@"executeTransaction : %@", transaction.debugDescription);
    BOOL callEnd = NO;
    BOOL callHold= NO;
    BOOL callAnswer = NO;


    NSPredicate *filter = [NSPredicate predicateWithFormat:@"self isKindOfClass: %@", [CXEndCallAction class]];
    NSArray *ends = [transaction.actions filteredArrayUsingPredicate:filter];
    callEnd = [ends count] >= 1;

    filter = [NSPredicate predicateWithFormat:@"self isKindOfClass: %@", [CXAnswerCallAction class]];
    NSArray *answer = [transaction.actions filteredArrayUsingPredicate:filter];
    callAnswer = [answer count] >= 1;

    filter = [NSPredicate predicateWithFormat:@"self isKindOfClass: %@", [CXSetHeldCallAction class]];
    NSArray *hold = [transaction.actions filteredArrayUsingPredicate:filter];
    callHold = [hold count] >= 1;


    if(callHold && callAnswer){
            pjsua_set_no_snd_dev();
        Call *currentCallObject = [self getCallObjectFromUUID:callAnswer.callUUID];
        if (currentCallObject != nil) {

            pjsua_call_id callId;
            callId = currentCallObject._call_id;            
            [self startAudio];
            [currentCallObject answerCallWithCompletion:^(BOOL isSucceed) {
                if (isSucceed) {
                    CallInfo *callForHold;
                    callForHold = [self getCallToBeHoldFromUUID:callHold.callUUID];                    
                    if (callForHold != nil) {
                        [callForHold holdCurrentCall];
                    }
                }
            }];
        }


        return YES;

    }else{
        return NO;
    }
}

This is how we are accepting second call while hold and accept. Which is working fine with no audio activated for accepted call. and following method is been called :

- (void)provider:(CXProvider *)provider didDeactivateAudioSession:(AVAudioSession *)audioSession{

Now the button of swapping calls are been disabled.

Queries :

Guys If anyone have worked with callKit and pjsip , Please help me out with this. Thanks.

Upvotes: 4

Views: 2005

Answers (1)

Rushang Prajapati
Rushang Prajapati

Reputation: 596

While accepting the call please fulfill the held action to make sure callkit hold the current call. That will enable Swap call button.

Don't forget to enable following stuffs for CXCallUpdate :

update.supportsHolding = YES;
update.supportsGrouping = NO;
update.supportsUngrouping = NO;



 -(void)provider:(CXProvider *)provider performSetHeldCallAction:(CXSetHeldCallAction *)action{
               if (action.onHold) {
                    [callForHold holdCurrentCall];
                }else{
                    [callForHold unHoldCurrentCall];
                }

            [action fulfill];
        }

Above is the code for hold. don't forget to do [action fulfill]

When you click on swap button , CXHeldCall will be triggered 2 times :

  • One call to be hold (Find the call object from callUUID of action and hold that call)
  • Second Call to be Unhold (Find the call object from callUUID of action and unhold that call)

Cheers ;)

Upvotes: 3

Related Questions