Android N拨打电话的流程

  • Post author:
  • Post category:其他



1

. 从Dialer工程开始,DialtactsActivity中打开

DialpadFragment

界面,在

DialpadFragment

中实现OnClickListener的onClick()方法,根据点击事件如果是拨号按钮(R.id.dialpad_floating_action_button)则调用handleDialButtonPressed()方法,开启拨号流程。


2

. handleDialButtonPressed方法中首先判断所拨打的号码是否为空号,是否为禁止拨打的号码,如果都不是则继续调用DialerUtils中的startActivityWithErrorToast()方法将拨号的请求继续往下传递,通过ContactsCommon中的TelecomManagerCompat类传递到

telecomm

(TelecomService)中的

TelecomManager

中。


3

.在

TelecomManager

中调用placeCall()方法,通过该方法远程调用

ITelecomService.aidl

的方式调用

TelecomServiceImpl

(进入Telecom工程)中的placeCall()方法(ITelecomService的实现类为TelecomServiceImpl中的ITelecomService.Stub mBinderImpl)。


4

. placeCall()方法中通过工厂模式生成

UserCallIntentProcessor

对象,通过调用UserCallIntentProcessor中的processIntent()方法向

PrimaryCallReceiver

发送请求通话的广播(processIntent()—>processOutgoingCallIntent()–>sendBroadcastToReceiver())。


5

. 在

PrimaryCallReceiver

的回调方法中获取

TelecomSystem

实例,然后通过再获取CallIntentProcessor实例,调用CallIntentProcessor中的

processIntent()

方法。


6

. processIntent()方法中对unKnownCall和outgoingcall进行判断,分别处理:

if (isUnknownCall) {
            processUnknownCallIntent(mCallsManager, intent);
        } else {
            processOutgoingCallIntent(mContext, mCallsManager, intent);
        }


processOutgoingCallIntent

方法处理拨打正常号码的流程。


7

. processOutgoingCallIntent()方法中通过

CallsManager



startOutgoingCall()

方法获取

Call

实例(startOutgoingCal()l方法中同时对手机是单卡双卡进行判断):

// Send to CallsManager to ensure the InCallUI gets kicked off before the broadcast returns
        Call call = callsManager
                .startOutgoingCall(handle, phoneAccountHandle, clientExtras, initiatingUser);

如果call不为空,new一个

NewOutgoingCallIntentBroadcaster

对象,然后调用processIntent()方法。


8

. processIntent()方法中对所拨打的号码进行处理。如果不是紧急拨号或者语音拨号,则继续调用broadcastIntent()方法,发生action为

ACTION_NEW_OUTGOING_CALL

的有序广播到

NewOutgoingCallBroadcastIntentReceiver




9

.

NewOutgoingCallBroadcastIntentReceiver

中回调到CallsManager中的

placeOutgoingCall()

方法,该方法中继续调用

Call

中的

startCreateConnection()

方法开始建立通话连接。


10

. startCreateConnection()方法中生成

CreateConnectionProcessor

对象,然后调用

process()

方法。


11

. process()方法中调用自身的

attemptNextPhoneAccount()

方法,此方法中通过

ConnectionServiceWrapper

实例调用

createConnection()

方法,createConnection()方法中通过IConnectionService.aidl远程调用

ConnectionService

中的

IConnectionService的实现类中的createConnection()

方法,通过handler继续传递

MSG_CREATE_CONNECTION

消息。在handler的处理消息的方法中调用ConnectionService的createConnection()方法(注意和IConnectionService的实现类中的createConnection()区分,此时有进入telecomm工程。)。


12

. 判断建立的连接是否为outgoingConnection:

Connection connection = isUnknown ? onCreateUnknownConnection(callManagerAccount, request)
                : isIncoming ? onCreateIncomingConnection(callManagerAccount, request)
                : onCreateOutgoingConnection(callManagerAccount, request);

在onCreateOutgoingConnection()方法中处理外拨电话的流程。


13

. onCreateOutgoingConnection()方法中调用

placeOutgoingConnection

()方法,获取

GsmCdmaPhone

的对象,通过dial()方法获取连接。


14

. 获取mCT,创建RIL对象,通过RILSender发送消息,通过RILReceiver接收处理消息。


15

. 如果通过成功则在CallsManager中的

onSuccessfulOutgoingCall()

方法中调用

setCallState()

方法生成通话记录(setCallState()–>CallsManagerListener.onCallStateChanged()–>CallLogManager.onCallStateChanged()–>logCall()–>logCallAsync()–>LogCallAsyncTask)。



版权声明:本文为wf_kingofring原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。