拨号界面输入密串,弹出选择界面的分析和实现
有个这样的需求:支持在拨号界面输入密串,暂定#*46825562*#弹出一个选择界面,然后对这个选择界面做出相应的处理。
因为这里需要对系统自带的拨号面板进行相关操作,所以必牵扯到framework层的分析。这里我们重点是对OutgoingCallBroadcaster这个类进行分析,
然后做个小的demo演示下这个功能需求。
当我们将要打电话的时候,就需要输入号码,然后按拨号键,实际上我们是可以取得这个号码的(这里不管输入的是什么,都可以捕获)在OutgoingCallBroadcaster这个类中的oncreate()方法有下面这几行代码
[java]
mPhone = PhoneApp.getInstance().phone;
Intent intent = getIntent();
if (LOGV) Log.v(TAG, "onResume: Got intent " + intent + ".");
String action = intent.getAction();
String number = PhoneNumberUtils.getNumberFromIntent(intent, this);
mPhone = PhoneApp.getInstance().phone;
Intent intent = getIntent();
if (LOGV) Log.v(TAG, "onResume: Got intent " + intent + ".");
String action = intent.getAction();
String number = PhoneNumberUtils.getNumberFromIntent(intent, this);就可以得到这个number,得到number后我们需要对其进行处理,如发送广播“Intent.ACTION_NEW_OUTGOING_CALL”,让别人进行处理
[java]
broadcastIntent.putExtra(EXTRA_ALREADY_CALLED, callNow);
broadcastIntent.putExtra(EXTRA_ORIGINAL_URI, intent.getData().toString());
if (LOGV) Log.v(TAG, "Broadcasting intent " + broadcastIntent + ".");
sendOrderedBroadcast(broadcastIntent, PERMISSION, null, null,
Activity.RESULT_OK, number, null);
broadcastIntent.putExtra(EXTRA_ALREADY_CALLED, callNow);
broadcastIntent.putExtra(EXTRA_ORIGINAL_URI, intent.getData().toString());
if (LOGV) Log.v(TAG, "Broadcasting intent " + broadcastIntent + ".");
sendOrderedBroadcast(broadcastIntent, PERMISSION, null, null,
Activity.RESULT_OK, number, null);发送广播后,在OutgoingCallBroadcaster类中有一个内部类OutgoingCallReceiver,这是一个继承了broadcastreceiver广播的类,在它的onReceive()方法中,就是说
接收到广播之后,从Intent里面取出电话号码及其URi
[java]
originalUri = intent.getStringExtra(
OutgoingCallBroadcaster.EXTRA_ORIGINAL_URI);
originalUri = intent.getStringExtra(
OutgoingCallBroadcaster.EXTRA_ORIGINAL_URI);这个时候就可以将InCallScreen启动
[java] view plaincopyprint?
Intent newIntent = new Intent(Intent.ACTION_CALL, uri);
newIntent.putExtra(Intent.EXTRA_PHONE_NUMBER, number);
newIntent.setClass(context, InCallScreen.class);
newIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(newIntent);
Intent newIntent = new Intent(Intent.ACTION_CALL, uri);
newIntent.putExtra(Intent.EXTRA_PHONE_NUMBER, number);
newIntent.setClass(context, InCallScreen.class);
newIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(newIntent);
基于上面的源码分析后,我们这时候可以思考,为什么不采用相应的方式,在InCallScreen界面之前调用我们自己需要的界面,而屏蔽InCallScreen界面呢?这个OutgoingCallBroadcaster的oncreate()方法不需要我们外部关心,它自己会调用,我们关心的就是自己在外部写一个广播以及我们需要的业务界面。
下面我们就做这样一个小的demo
1、新建一个广播
[java]
package com.huawei.test;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
// 支持在拨号界面输入密串,暂定 <span style="background-color: rgb(255, 255, 255); ">#*46825562*# 弹出天天聊调试功呢个选择界面</span>
public class TransferToDebugMode extends BroadcastReceiver{
private static final String TAG = "TransferToDebugMode" ;
private static final String ACTION_DEBUGMODE = "com.huawei.test.DebugModeActivity" ;
//是否开启Debug模式开关的开关值,默认值为true,可以在系统级别变量里设计
private boolean isNeedDebugModeOpen = true ;
//需要设计为系统变量
private final String DebugModeOpenCode = "#*46825562*#" ;
@Override
public void onReceive(Context context, Intent intent) {
if (intent.getAction().equals(Intent.ACTION_NEW_OUTGOING_CALL)) {
String number = intent.getStringExtra(Intent.EXTRA_PHONE_NUMBER) ;
Log.v(TAG, "Received intent " + intent + "(number = " + number + ".") ;
if (isNeedDebugModeOpen && number.equals(DebugModeOpenCode)) {
Intent newIntent = new Intent(ACTION_DEBUGMODE) ;
newIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK) ;
context.startActivity(newIntent) ;
setResultData(null) ;//这一步很关键,启动activity后将广播的数据清空
}
}
}
}
package com.huawei.test;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
// 支持在拨号界面输入密串,暂定 <span style="background-color: rgb(255, 255, 255); ">#*46825562*# 弹出天天聊调试功呢个选择界面</span>
public class TransferToDebugMode extends BroadcastReceiver{
private static final String TAG = "TransferToDebugMode" ;<
补充:移动开发 , Android ,