针对客户端数据处理逻辑:
InputConsumer 用于消费数据 (InputChannel.cpp中),其中核心的函数是:
status_t InputConsumer::consume(InputEventFactoryInterface* factory, InputEvent** outEvent) {
switch (mSharedMessage->type) {
case AINPUT_EVENT_TYPE_KEY: {
KeyEvent* keyEvent = factory->createKeyEvent();
if (! keyEvent) return NO_MEMORY;
populateKeyEvent(keyEvent);
*outEvent = keyEvent;
break;
}
case AINPUT_EVENT_TYPE_MOTION: {
MotionEvent* motionEvent = factory->createMotionEvent();
if (! motionEvent) return NO_MEMORY;
populateMotionEvent(motionEvent);
*outEvent = motionEvent;
break;
}
...
}
JNI 函数处理数据: Android_view_InputQueue.cpp
int NativeInputQueue::handleReceiveCallback(int receiveFd, int events, void* data) {
/* 先收到信号 */
status_t status = connection->inputConsumer.receiveDispatchSignal();
/* 再处理数据 */
status = connection->inputConsumer.consume(& connection->inputEventFactory, & inputEvent);
/* 转换成java对象native数据 */
android_view_KeyEvent_fromNative 及 android_view_MotionEvent_fromNative
/* 回调数据给Java层*/
env->CallStaticVoidMethod(gInputQueueClassInfo.clazz,
dispatchMethodId, inputHandlerObjLocal, inputEventObj,
jlong(finishedToken));
}
对于最后C++调用Java的方法说明一下:
首先注册两个方法:
env->CallStaticVoidMethod(gInputQueueClassInfo.clazz,
dispatchMethodId, inputHandlerObjLocal, inputEventObj,
jlong(finishedToken));
GET_STATIC_METHOD_ID(gInputQueueClassInfo.dispatchKeyEvent, gInputQueueClassInfo.clazz,
"dispatchKeyEvent",
"(Landroid/view/InputHandler;Landroid/view/KeyEvent;J)V");
GET_STATIC_METHOD_ID(gInputQueueClassInfo.dispatchMotionEvent, gInputQueueClassInfo.clazz,
"dispatchMotionEvent",
"(Landroid/view/InputHandler;Landroid/view/MotionEvent;J)V");
然后在InputQueue.java中有这两个方法的定义:
env->CallStaticVoidMethod(gInputQueueClassInfo.clazz,
dispatchMethodId, inputHandlerObjLocal, inputEventObj,
jlong(finishedToken));
private static void dispatchKeyEvent(InputHandler inputHandler,
KeyEvent event, long finishedToken) {
Runnable finishedCallback = FinishedCallback.obtain(finishedToken);
inputHandler.handleKey(event, finishedCallback);
}
@SuppressWarnings("unused")
private static void dispatchMotionEvent(InputHandler inputHandler,
MotionEvent event, long finishedToken) {
Runnable finishedCallback = FinishedCallback.obtain(finishedToken);
inputHandler.handleMotion(event, finishedCallback);
}
env->CallStaticVoidMethod(gInputQueueClassInfo.clazz,
dispatchMethodId, inputHandlerObjLocal, inputEventObj,
jlong(finishedToken));
handleKey最后由InputHandler 处理keyevent及motionevent事件
客户端数据回调机制:
对于每个客户端注册了一个InputChannel
status_t NativeInputQueue::registerInputChannel(JNIEnv* env, jobject inputChannelObj,
添加notify回调函数
looper->addFd(receiveFd, 0, ALOOPER_EVENT_INPUT, handleReceiveCallback, this);
env->CallStaticVoidMethod(gInputQueueClassInfo.clazz,
dispatchMethodId, inputHandlerObjLocal, inputEventObj,
jlong(finishedToken));