自定义语音融合呼叫的 UI 界面

更新时间: 2022/09/06 02:44:11

本文介绍自定义语音融合呼叫的 UI 界面的方法。

实现方法

  1. 添加呼叫监听,如果为主叫用户,则发起融合呼叫。
javapublic class PstnAudioActivity extends Activity {
    /**
     * rtc 呼叫参数,主叫/被叫都会收到对应参数,具体的参数说明请参见本文的“CallParam 参数说明”
     */
    private CallParam callParam;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_pstn_audio_layout);
        // 添加呼叫监听
        PstnFunctionMgr.addCallback(callback);

        // 解析呼叫参数
        callParam = getIntent().getParcelableExtra(Constants.PARAM_KEY_CALL);
      	// 呼叫参数为空则呼叫存在问题,直接进行页面关闭 
        if (callParam == null) {
            ALog.e(TAG, "callParam is null then finish the activity.");
            finish();
            return;
        }

        // 判断为主叫用户,进行发起融合呼叫
        if (!callParam.isCalled()) { // 主叫
            // 通过rtc 呼叫参数获取 pstn 呼叫参数
            PstnCallParam pstnCallParam = PstnExtendsUtilsKt.toPstnCallParam(callParam);
            if (pstnCallParam == null) {
                ALog.e(TAG, "pstnCallParam is null then finish the activity.");
                finish();
                return;
            }
            // 发起融合呼叫,此呼叫会携带话单,但话单依赖于主叫方发送
            PstnExtendsUtilsKt.callWithCorAndOrder(PstnFunctionMgr.INSTANCE, pstnCallParam);
            // 发起融合呼叫,不带 pstn 相关话单
            // PstnFunctionMgr.callWithCor(pstnCallParam);
        }
    }

    @Override
    protected void onPause() {
        super.onPause();
        if (isFinishing()) {
            PstnFunctionMgr.removeCallback(callback);// 移除呼叫监听,避免内存泄漏
        }
    }
}
  1. 添加融合呼叫相关回调。
javaprivate final AbsPstnCallback callback = new AbsPstnCallback() {

        /**
         * pstn 开始呼叫回调
         *
         * @param code 呼叫结果 code
         * @param errorMsg 呼叫信息提示
         */
        @Override
        public void onDirectStartCall(int code, @Nullable String errorMsg) {
            super.onDirectStartCall(code, errorMsg);
            ALog.d(TAG, new ParameterMap("onDirectStartCall").append("code", code)
                    .append("errorMsg", errorMsg)
                    .toValue()
            );
            if (code != 0) {
                finish();
            }
        }

        /**
         * pstn 通话,被叫方开始响铃
         *
         * @param code 响铃结果
         */
        @Override
        public void onDirectCallRing(int code) {
            super.onDirectCallRing(code);
            ALog.d(TAG, new ParameterMap("onDirectCallRing").append("code", code).toValue());
        }

        /**
         * pstn 通话,被叫接听
         *
         * @param code 接听结果
         */
        @Override
        public void onDirectCallAccept(int code) {
            super.onDirectCallAccept(code);
            ALog.d(TAG, new ParameterMap("onDirectCallAccept").append("code", code).toValue());
            if (code == 0) {
                findViewById(R.id.btAccept).setVisibility(View.GONE);
                return;
            }
            finish();
        }

        /**
         * pstn 通话,挂断原因
         *
         * @param reason 原因错误码
         * @param code 挂断结果码
         * @param errorMsg 消息提示
         * @param isCallEstablished 是否建立通话,true,建立;false,未建立。
         */
        @Override
        public void onDirectCallHangupWithReason(int reason, int code, @Nullable String errorMsg, boolean isCallEstablished) {
            super.onDirectCallHangupWithReason(reason, code, errorMsg, isCallEstablished);
            ALog.d(TAG, new ParameterMap("onDirectCallHangupWithReason").append("reason", reason)
                    .append("code", code).append("errorMsg", errorMsg)
                    .append("isCallEstablished", isCallEstablished).toValue()
            );
            finish();
        }

        /**
         * pstn 通话中,对方断开链接时触发此回调
         *
         * @param code 断开原因
         * @param errorMsg 错误提示
         */
        @Override
        public void onDirectCallDisconnectWithError(int code, @Nullable String errorMsg) {
            super.onDirectCallDisconnectWithError(code, errorMsg);
            ALog.d(TAG, new ParameterMap("onDirectCallDisconnectWithError")
                    .append("code", code).append("errorMsg", errorMsg)
                    .toValue()
            );
            finish();
        }

        /**
         * pstn 通话,出现的任何错误,出现错误后直接关闭页面
         *
         * @param result 包含错误原因
         */
        @Override
        public void onTransError(@NonNull ResultInfo<?> result) {
            super.onTransError(result);
            ALog.d(TAG, new ParameterMap("transError")
                    .append("result", result)
                    .toValue()
            );
            finish();
        }

        /**
         * 融合呼叫通话超时,超时后直接关闭页面
         */
        @Override
        public void onTimeOutWithPstn() {
            super.onTimeOutWithPstn();
            ALog.d(TAG, new ParameterMap("onTimeOutWithPstn").toValue());
            finish();
        }

        /**
         * rtc 通话中出现的错误
         *
         * @param errorCode 错误码
         * @param errorMsg 错误提示信息
         * @param needFinish 是否需要结束通话
         */
        @Override
        public void onError(int errorCode, String errorMsg, boolean needFinish) {
            super.onError(errorCode, errorMsg, needFinish);
            ALog.d(TAG, new ParameterMap("onError")
                    .append("errorCode", errorCode)
                    .append("errorMsg", errorMsg)
                    .append("needFinish", needFinish)
                    .toValue()
            );
            if (needFinish) {
                finish();
            }
        }

        /**
         *
         * rtc 通话,通话建立
         * @param userId 对端用户id
         */
        @Override
        public void onUserEnter(String userId) {
            super.onUserEnter(userId);
            ALog.d(TAG, new ParameterMap("onUserEnter")
                    .append("userId", userId)
                    .toValue()
            );
            findViewById(R.id.btAccept).setVisibility(View.GONE);
        }

        /**
         * rtc 通话收到对方挂断
         *
         * @param userId 挂断用户id
         */
        @Override
        public void onCallEnd(String userId) {
            super.onCallEnd(userId);
            ALog.d(TAG, new ParameterMap("onCallEnd")
                    .append("userId", userId)
                    .toValue()
            );
            finish();
        }

        /**
         * rtc 通话,另外一方用户正常离开 rtc 房间
         *
         * @param userId 离开用户 id
         */
        @Override
        public void onUserLeave(String userId) {
            super.onUserLeave(userId);
            ALog.d(TAG, new ParameterMap("onUserLeave")
                    .append("userId", userId)
                    .toValue()
            );
            finish();
        }

        /**
         * rtc 通话,另外一方用户非正常离开 rtc 房间
         *
         * @param userId 离开用户 id
         */
        @Override
        public void onUserDisconnect(String userId) {
            super.onUserDisconnect(userId);
            ALog.d(TAG, new ParameterMap("onUserDisconnect")
                    .append("userId", userId)
                    .toValue()
            );
            finish();
        }

        /**
         * rtc 通话中,本端离开 rtc 房间
         *
         * @param res 离开的原因 code
         */
        @Override
        public void onDisconnect(int res) {
            super.onDisconnect(res);
            finish();
        }

        /**
         * 主叫呼叫时被被叫拒绝
         *
         * @param userId 被叫拒绝用户id
         */
        @Override
        public void onRejectByUserId(String userId) {
            super.onRejectByUserId(userId);
            ALog.d(TAG, new ParameterMap("onRejectByUserId")
                    .append("userId", userId)
                    .toValue()
            );
            finish();
        }

        /**
         * 主叫呼叫时被叫占线
         *
         * @param userId 被叫用户id
         */
        @Override
        public void onUserBusy(String userId) {
            super.onUserBusy(userId);
            ALog.d(TAG, new ParameterMap("onUserBusy")
                    .append("userId", userId)
                    .toValue()
            );
            finish();
        }

        /**
         * 被主叫用户取消
         *
         * @param userId 取消用户id
         */
        @Override
        public void onCancelByUserId(String userId) {
            super.onCancelByUserId(userId);
            ALog.d(TAG, new ParameterMap("onCancelByUserId")
                    .append("userId", userId)
                    .toValue()
            );
            finish();
        }

        /**
         * rtc 呼叫/接听超时,pstn 场景下主叫忽略,被叫处理
         */
        @Override
        public void timeOut() {
            super.timeOut();
            if (callParam.isCalled()) {
                finish();
            }
        }
    };
  1. 添加接听和挂断方法。
javapublic void acceptAction(View view) {
		// rtc 被叫接听,融合呼叫被叫如果在 app 中一定为 rtc 呼叫,所以呼叫接听为rtc 接听
		NERTCVideoCall.sharedInstance().accept(OthersKt.toInviteParamBuilder(callParam),
              CallKitUI.INSTANCE.getCurrentUserAccId(), null);
}

public void hangupAction(View view) {
  	// 被叫场景下挂断一定是 rtc 挂断,主叫挂断是融合呼叫的
    if (callParam.isCalled()) { // 被叫挂断使用 rtc 挂断
        NERTCVideoCall.sharedInstance().hangup(null, null);
    } else { // 主叫挂断使用 融合呼叫挂断
        PstnFunctionMgr.hangup();
    }
    finish();// 关闭页面
}
  1. 注册呼叫页面。

在初始化配置中增加类似如下代码,其他的初始化代码请参见语音融合呼叫

java......
.p2pVideoActivity(TestActivity.class)// 注册对应视频呼叫页面
.....

CallParam 参数说明

参考上文实现时从 Intent 中解析的 CallParam 参数,无论是被叫还是主叫都可通过上文中的方法进行参数解析,具体参数说明如下表所示。

方法 返回类型 说明
isCalled Boolean
  • true:被叫
  • false:主叫
getChannelType int
  • 1- 音频通话
  • 2- 视频通话
getCallerAccId String 呼叫方 IM 账号 ID
getCurrentAccId String 当前用户 IM 账号 ID
getCalledAccIdList List<String> 被呼叫用户 IM 账号列表
getGroupId String 群组 ID(1v1 呼叫不存在)
getExtras Map<String, Object> 自定义扩展参数(包含 callExtraInfo 参数,通过 intent 传入到 Activity,value 需支持序列化)
getP2pCalledAccId String 获取一对一通话的被叫账号 ID
getCallExtraInfo String 获取呼叫时传入的自定义参数(此参数对应 NERtcVideoCall.call 中的自定义参数)

后续步骤

语音融合呼叫

此文档是否对你有帮助?
有帮助
去反馈
  • 实现方法
  • CallParam 参数说明
  • 后续步骤