Android Framework 输入子系统(06)Global Key 一键启动 应用程序案例

系列文章解读&说明:

Android Framework 输入子系统 的 分析主要分为以下部分:

(01)核心机制 inotify和epoll

(02)核心机制 双向通信(socketpair+binder)

(03)输入系统框架

(04)InputReader解读

(05)InputDispatcher解读

(06)Global Key 一键启动 应用程序案例

(07)APP建立联系

(08)activity window decor view

(09)InputStage简介

(10)Input系统常见工具(getevent & sendevent & input)

本模块分享的内容:Global Key 一键启动 应用程序案例

本章关键点总结 & 说明:

这里主要关注➕ 案例 部分即可,主要是Global Key 一键启动应用的一个实际案例。

1 实现原理

通过配置framework层的global_keys.xml来实现,Global Key直接实现发送广播的功能,再写一个可以接收此广播的APP即可。于是就实现了一键启动应用的功能。在这里首先注册广播,使用 手动 发广播的方式启动APP,如下所示:

am broadcast -a android.intent.action.GLOBAL_BUTTON -n com.thisway.app_0001_leddemo/.MyBroadcastReceiver

测试APP接收广播后可以启动,这样测试通过后,开始framework层的配置,如下:
修改 /work/android-5.0.2/frameworks/base/core/res/res/xml/global_keys.xml

添加其中一项:

<key keyCode="KEYCODE_TV" component="com.thisway.app_0001_leddemo/.MyBroadcastReceiver" />

接下来开始编译:

mmm frameworks/base/core/res

此时会生成 framework-res.apk,把它拷贝到设备上替换/整体编译即可实现该功能。接下来给出一份参考测试APP。

2 APP测试应用相关代码说明

@1 这里以一个简单启动APP的流程为案例,APP相关代码如下,MainActivity.java的实现如下:

package com.thisway.app_0001_leddemo;

import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.Button;
import android.view.View;
import android.widget.CheckBox;
import android.widget.Toast;

public class MainActivity extends AppCompatActivity {

    private boolean ledon = false;
    private Button button = null;
    private CheckBox checkBoxLed1 = null;

    class MyButtonListener implements View.OnClickListener {
        @Override
        public void onClick(View v) {
            ledon = !ledon;
            if (ledon) {
                button.setText("ALL OFF");
                checkBoxLed1.setChecked(true);
            }
            else {
                button.setText("ALL ON");
                checkBoxLed1.setChecked(false);
            }
        }
    }

    public void onCheckboxClicked(View view) {
        // Is the view now checked?
        boolean checked = ((CheckBox) view).isChecked();

        // Check which checkbox was clicked
        switch(view.getId()) {
            case R.id.LED1:
                if (checked) {
                    // Put some meat on the sandwich
                    Toast.makeText(getApplicationContext(), "LED1 on", Toast.LENGTH_SHORT).show();
                }
                else {
                    // Remove the meat
                    Toast.makeText(getApplicationContext(), "LED1 off", Toast.LENGTH_SHORT).show();
                }
                break;
        }
    }
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        button = (Button) findViewById(R.id.BUTTON);
        checkBoxLed1 = (CheckBox) findViewById(R.id.LED1);
        button.setOnClickListener(new MyButtonListener());
    }
	//...
}

@2 MyBroadcastReceiver的代码实现如下:

package com.thisway.app_0001_leddemo;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.widget.Toast;

public class MyBroadcastReceiver extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {
        Toast.makeText(context, "Get BroadcastReceiver", Toast.LENGTH_SHORT).show();

        Intent intentNewTask =new Intent(context, MainActivity.class);
        intentNewTask.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
        context.startActivity(intentNewTask);
    }
}

@3 Layout布局代码如下:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
    android:layout_height="match_parent" android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    android:paddingBottom="@dimen/activity_vertical_margin" tools:context=".MainActivity"
    android:orientation="vertical"
    >

    <TextView android:text="www.100ask.net, 100ask.taobao.com, for LEDDemo"
        android:layout_width="wrap_content"
    android:layout_height="wrap_content" />

    <Button
        android:id="@+id/BUTTON"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:text="ALL ON"
        />

    <CheckBox
        android:id="@+id/LED1"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:text="LED1"
        android:onClick="onCheckboxClicked"
        />
</LinearLayout>

@4 整个APP的代码架构如下所示:

├── AndroidManifest.xml
├── java
│   └── com
│       └── thisway
│           └── app_0001_leddemo
│               ├── MainActivity.java
│               └── MyBroadcastReceiver.java
└── res
    ├── layout
    │   └── activity_main.xml
    ├── menu
    │   └── menu_main.xml
    ├── mipmap-hdpi
    │   └── ic_launcher.png
    ├── mipmap-mdpi
    │   └── ic_launcher.png
    ├── mipmap-xhdpi
    │   └── ic_launcher.png
    ├── mipmap-xxhdpi
    │   └── ic_launcher.png
    ├── values
    │   ├── dimens.xml
    │   ├── strings.xml
    │   └── styles.xml
    └── values-w820dp
        └── dimens.xml

在这里仅仅是一个简单的案例,实际上大家也可以直接使用自己写的APP,关键在于有Broadcastreceiver的注册和启动即可,原理都是类似的。

猜你喜欢

转载自blog.csdn.net/vviccc/article/details/92797146