版權聲明
本文來自博客園,作者:觀心靜 ,轉載請註明原文鏈接:https://www.cnblogs.com/guanxinjing/p/17890899.html
前言
此博客基於Android10版本講解如何在系統中添加自定義的系統全局廣播。下面通過一個發送按鍵廣播的例子在說明
例子:發送按鍵廣播
系統廣播添加位置
修改文件路徑:/aosp/frameworks/base/core/res/AndroidManifest.xml
在PhoneWindowManager中添加發送廣播的代碼
修改文件路徑:/aosp/frameworks/base/services/core/java/com/android/server/policy/PhoneWindowManager.java
在PhoneWindowManager的interceptKeyBeforeQueueing方法中添加下面註釋中的代碼
@Override
public int interceptKeyBeforeQueueing(KeyEvent event, int policyFlags) {
if (!mSystemBooted) {
// If we have not yet booted, don't let key events do anything.
return 0;
}
final boolean interactive = (policyFlags & FLAG_INTERACTIVE) != 0;
final boolean down = event.getAction() == KeyEvent.ACTION_DOWN;
final boolean canceled = event.isCanceled();
final int keyCode = event.getKeyCode();
final int displayId = event.getDisplayId();
final boolean isInjected = (policyFlags & WindowManagerPolicy.FLAG_INJECTED) != 0;
//略..........
// If the key would be handled globally, just return the result, don't worry about special
// key processing.
if (isValidGlobalKey(keyCode)
&& mGlobalKeyManager.shouldHandleGlobalKey(keyCode, event)) {
if (isWakeKey) {
wakeUp(event.getEventTime(), mAllowTheaterModeWakeFromKey,
PowerManager.WAKE_REASON_WAKE_KEY, "android.policy:KEY");
}
return result;
}
// Enable haptics if down and virtual key without multiple repetitions. If this is a hard
// virtual key such as a navigation bar button, only vibrate if flag is enabled.
final boolean isNavBarVirtKey = ((event.getFlags() & KeyEvent.FLAG_VIRTUAL_HARD_KEY) != 0);
boolean useHapticFeedback = down
&& (policyFlags & WindowManagerPolicy.FLAG_VIRTUAL) != 0
&& (!isNavBarVirtKey || mNavBarVirtualKeyHapticFeedbackEnabled)
&& event.getRepeatCount() == 0;
//===============在此處添加要發送的按鍵廣播
Intent devKeyIntent = new Intent();
if (down) {
devKeyIntent.setAction("com.zhou.action.DEV_KEY_DOWN");
} else {
devKeyIntent.setAction("com.zhou.action.DEV_KEY_UP");
}
devKeyIntent.putExtra("keyCode", keyCode);
mContext.sendBroadcast(devKeyIntent);
//================
// Handle special keys.
switch (keyCode) {
case KeyEvent.KEYCODE_BACK: {
if (down) {
interceptBackKeyDown();
} else {
boolean handled = interceptBackKeyUp(event);
// Don't pass back press to app if we've already handled it via long press
if (handled) {
result &= ~ACTION_PASS_TO_USER;
}
}
break;
}
//略..............
在自己的應用中註冊並且接收廣播
在Activity中註冊並且接收廣播
class MainActivity : AppCompatActivity() {
lateinit var mReceiver: DevKeyReceiver
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
//註冊廣播
val intentFilter = IntentFilter()
intentFilter.addAction("com.zhou.action.DEV_KEY_UP")
intentFilter.addAction("com.zhou.action.DEV_KEY_DOWN")
mReceiver = DevKeyReceiver()
registerReceiver(mReceiver, intentFilter)
}
override fun onDestroy() {
super.onDestroy()
//註銷廣播
unregisterReceiver(mReceiver)
}
}
class DevKeyReceiver : BroadcastReceiver() {
override fun onReceive(context: Context, intent: Intent) {
Log.e("zh", "接受廣播 action = ${intent.action} keyCode = ${intent.getIntExtra("keyCode", -1)}")
Toast.makeText(context, "接受廣播 action = ${intent.action} keyCode = ${intent.getIntExtra("keyCode", -1)}", Toast.LENGTH_SHORT).show()
}
}
效果圖
這裏可以通過adb命令發送各種鍵值以達到測試目的,例如adb shell input keyevent 24 音量加 和 adb shell input keyevent 25 音量減
end