原创内容,转载请注明出处,多谢配合。

一、Android输入系统介绍

牵涉到的模块:

  • InputReader: 负责从硬件获取输入,转换成事件(Event), 并传给Input Dispatcher.
  • InputDispatcher: 将InputReader传送过来的Events分发给合适的窗口,并监控ANR。
  • InputManagerService: 负责InputReader 和 InputDispatcher的创建,并提供Policy 用于Events的预处理。
  • WindowManagerService:管理InputManager 与 View(Window) 以及 ActivityManager 之间的通信。
  • View and Activity:接收按键并处理。
  • ActivityManagerService:ANR 处理。

牵涉到的进程
system_server 与 应用进程。
进程对应的主要工作线程
其中system_server中包含InputReaderThread和InputDispatcherThread。
应用进程相关的主要是 UIThread。

二、初始化

在SystemServer的初始化过程中,IMS和WMS 被创建出来,并将WMS中的monitor传给了IMS,作为回调。

frameworks/base/services/java/com/android/server/SystemServer.javaprivate void startOtherServices() {   WindowManagerService wm = null;   InputManagerService inputManager = null;   …   inputManager = new InputManagerService(context);   ...   wm = WindowManagerService.main(context, inputManager,             mFactoryTestMode != FactoryTest.FACTORY_TEST_LOW_LEVEL,             !mFirstBoot, mOnlyCore, new PhoneWindowManager());   ServiceManager.addService(Context.WINDOW_SERVICE, wm);   ServiceManager.addService(Context.INPUT_SERVICE, inputManager);   …   inputManager.setWindowManagerCallbacks(wm.getInputMonitor());   inputManager.start();   ...}

IMS的构造方法中执行了nativeInit,这是个native方法,属于jni调用,该方法中创建了一个NativeInputManager实例,并且和java层使用的是同一个looper。

frameworks/base/services/core/java/com/android/server/input/InputManagerService.javapublic InputManagerService(Context context) {    this.mContext = context;   this.mHandler = new InputManagerHandler(DisplayThread.get().getLooper());    ...   mPtr = nativeInit(this, mContext, mHandler.getLooper().getQueue());    ...}frameworks/base/services/core/jni/com_android_server_input_InputManagerService.cppstatic jlong nativeInit(JNIEnv* env, jclass /* clazz */,        jobject serviceObj, jobject contextObj, jobject messageQueueObj) {    sp messageQueue = android_os_MessageQueue_getMessageQueue(env, messageQueueObj);    if (messageQueue == NULL) {        jniThrowRuntimeException(env, "MessageQueue is not initialized.");        return 0;    }    NativeInputManager* im = new NativeInputManager(contextObj, serviceObj,            messageQueue->getLooper());    im->incStrong(0);    return reinterpret_cast(im);}

在NativeInputManager的初始化中创建了一个Eventhub,同时将这个Eventhub传给新建的Inputmanager,Eventhub就是将数据从硬件驱动上读出来然后传递上来的通道。

frameworks/base/services/core/jni/com_android_server_input_InputManagerService.cppNativeInputManager::NativeInputManager(jobject contextObj,        jobject serviceObj, const sp& looper) :        mLooper(looper), mInteractive(true) {    ...    sp eventHub = new EventHub();    mInputManager = new InputManager(eventHub, this, this);}

InputManager初始化时创建了两个重要操作类:InputReaderInputDispatcher

frameworks/native/services/inputflinger/InputManager.cppInputManager::InputManager(        const sp& eventHub,        const sp& readerPolicy,        const sp& dispatcherPolicy) {    mDispatcher = new InputDispatcher(dispatcherPolicy);    mReader = new InputReader(eventHub, readerPolicy, mDispatcher);    initialize();}

initialize方法初始化对应的两个线程:InputReaderThreadInputDispatcherThread

void InputManager::initialize() {    mReaderThread = new InputReaderThread(mReader);    mDispatcherThread = new InputDispatcherThread(mDispatcher);}

InputManager的start方法,让两个线程run起来。

frameworks/native/services/inputflinger/InputManager.cppstatus_t InputManager::start() {    status_t result = mDispatcherThread->run("InputDispatcher", PRIORITY_URGENT_DISPLAY);    if (result) {        ALOGE("Could not start InputDispatcher thread due to error %d.", result);        return result;    }    result = mReaderThread->run("InputReader", PRIORITY_URGENT_DISPLAY);    if (result) {        ALOGE("Could not start InputReader thread due to error %d.", result);        mDispatcherThread->requestExit();        return result;    }    return OK;}

那么这个InputManager的start方法在哪调的呢?回看IMS的start方法

frameworks/base/services/core/java/com/android/server/input/InputManagerService.javapublic void start() {    Slog.i(TAG, "Starting input manager");   nativeStart(mPtr); ...}

这里又是调的native方法: nativeStart(mPtr)

frameworks/base/services/core/jni/com_android_server_input_InputManagerService.cppstatic void nativeStart(JNIEnv* env, jclass /* clazz */, jlong ptr) {    NativeInputManager* im = reinterpret_cast(ptr);    status_t result = im->getInputManager()->start();    if (result) {        jniThrowRuntimeException(env, "Input manager could not be started.");    }}

这里获取InputManager并调用它的start方法。

所以根据以上的初始化过程总结整个层次关系:

从这个初始化过程来看:IMS的逻辑基本上都是通过jni实现在native层。

下一篇文章:
Android Input(二)-输入子系统

更多相关文章

  1. Android性能优化一些方法
  2. android — JNI注册方法说明
  3. Android绘制圆形图片的3个方法
  4. Android(安卓)初级面试者拾遗(前台界面篇)之 Activity 和 Fragment
  5. 深入理解SharedPrefences实现原理
  6. Android文件操作说明
  7. Android之提示错误Can not perform this action after onSaveIns
  8. Android中多USB摄像头解决方案——UVCCamera
  9. 【学习笔记】Android中Service通信

随机推荐

  1. [置顶] Android之SharedPreferences两个
  2. 处理JNI ERROR (app bug): accessed stal
  3. 使用zipalign对齐应用程序
  4. Android面试常客之Handler全解
  5. Android(安卓)应用中十大常见 UX 错误
  6. Android欢迎界面,一个Activity搞定
  7. Android(安卓)学习之路 之 第2组UI组件:Te
  8. 定制Android关机界面
  9. Android(安卓)ProGuard技术详解
  10. Android(安卓)Handler 用法解析