Step 18. EventHub.getEvent

这个函数定义在frameworks/base/libs/ui/EventHub.cpp文件中:

  1. boolEventHub::getEvent(RawEvent*outEvent)
  2. {
  3. outEvent->deviceId=0;
  4. outEvent->type=0;
  5. outEvent->scanCode=0;
  6. outEvent->keyCode=0;
  7. outEvent->flags=0;
  8. outEvent->value=0;
  9. outEvent->when=0;
  10. //NotethatweonlyallowonecallertogetEvent(),sodon'tneed
  11. //todolockinghere...onlywhenadding/removingdevices.
  12. if(!mOpened){
  13. mError=openPlatformInput()?NO_ERROR:UNKNOWN_ERROR;
  14. mOpened=true;
  15. mNeedToSendFinishedDeviceScan=true;
  16. }
  17. for(;;){
  18. //Reportanydevicesthathadlastbeenadded/removed.
  19. if(mClosingDevices!=NULL){
  20. device_t*device=mClosingDevices;
  21. LOGV("Reportingdeviceclosed:id=0x%x,name=%s\n",
  22. device->id,device->path.string());
  23. mClosingDevices=device->next;
  24. if(device->id==mFirstKeyboardId){
  25. outEvent->deviceId=0;
  26. }else{
  27. outEvent->deviceId=device->id;
  28. }
  29. outEvent->type=DEVICE_REMOVED;
  30. outEvent->when=systemTime(SYSTEM_TIME_MONOTONIC);
  31. deletedevice;
  32. mNeedToSendFinishedDeviceScan=true;
  33. returntrue;
  34. }
  35. if(mOpeningDevices!=NULL){
  36. device_t*device=mOpeningDevices;
  37. LOGV("Reportingdeviceopened:id=0x%x,name=%s\n",
  38. device->id,device->path.string());
  39. mOpeningDevices=device->next;
  40. if(device->id==mFirstKeyboardId){
  41. outEvent->deviceId=0;
  42. }else{
  43. outEvent->deviceId=device->id;
  44. }
  45. outEvent->type=DEVICE_ADDED;
  46. outEvent->when=systemTime(SYSTEM_TIME_MONOTONIC);
  47. mNeedToSendFinishedDeviceScan=true;
  48. returntrue;
  49. }
  50. if(mNeedToSendFinishedDeviceScan){
  51. mNeedToSendFinishedDeviceScan=false;
  52. outEvent->type=FINISHED_DEVICE_SCAN;
  53. outEvent->when=systemTime(SYSTEM_TIME_MONOTONIC);
  54. returntrue;
  55. }
  56. //Grabthenextinputevent.
  57. for(;;){
  58. //Consumebufferedinputevents,ifany.
  59. if(mInputBufferIndex<mInputBufferCount){
  60. conststructinput_event&iev=mInputBufferData[mInputBufferIndex++];
  61. constdevice_t*device=mDevices[mInputDeviceIndex];
  62. LOGV("%sgot:t0=%d,t1=%d,type=%d,code=%d,v=%d",device->path.string(),
  63. (int)iev.time.tv_sec,(int)iev.time.tv_usec,iev.type,iev.code,iev.value);
  64. if(device->id==mFirstKeyboardId){
  65. outEvent->deviceId=0;
  66. }else{
  67. outEvent->deviceId=device->id;
  68. }
  69. outEvent->type=iev.type;
  70. outEvent->scanCode=iev.code;
  71. if(iev.type==EV_KEY){
  72. status_terr=device->layoutMap->map(iev.code,
  73. &outEvent->keyCode,&outEvent->flags);
  74. LOGV("iev.code=%dkeyCode=%dflags=0x%08xerr=%d\n",
  75. iev.code,outEvent->keyCode,outEvent->flags,err);
  76. if(err!=0){
  77. outEvent->keyCode=AKEYCODE_UNKNOWN;
  78. outEvent->flags=0;
  79. }
  80. }else{
  81. outEvent->keyCode=iev.code;
  82. }
  83. outEvent->value=iev.value;
  84. //Useaneventtimestampinthesametimebaseas
  85. //java.lang.System.nanoTime()andandroid.os.SystemClock.uptimeMillis()
  86. //asexpectedbytherestofthesystem.
  87. outEvent->when=systemTime(SYSTEM_TIME_MONOTONIC);
  88. returntrue;
  89. }
  90. //Finishreadingalleventsfromdevicesidentifiedinpreviouspoll().
  91. //ThiscodeassumesthatmInputDeviceIndexisinitially0andthatthe
  92. //reventsmemberofpollfdisinitializedto0whenthedeviceisfirstadded.
  93. //SincemFDs[0]isusedforinotify,weprocessregulareventsstartingatindex1.
  94. mInputDeviceIndex+=1;
  95. if(mInputDeviceIndex>=mFDCount){
  96. break;
  97. }
  98. conststructpollfd&pfd=mFDs[mInputDeviceIndex];
  99. if(pfd.revents&POLLIN){
  100. int32_treadSize=read(pfd.fd,mInputBufferData,
  101. sizeof(structinput_event)*INPUT_BUFFER_SIZE);
  102. if(readSize<0){
  103. if(errno!=EAGAIN&&errno!=EINTR){
  104. LOGW("couldnotgetevent(errno=%d)",errno);
  105. }
  106. }elseif((readSize%sizeof(structinput_event))!=0){
  107. LOGE("couldnotgetevent(wrongsize:%d)",readSize);
  108. }else{
  109. mInputBufferCount=readSize/sizeof(structinput_event);
  110. mInputBufferIndex=0;
  111. }
  112. }
  113. }
  114. ......
  115. mInputDeviceIndex=0;
  116. //Pollforevents.Mindthewakelockdance!
  117. //Weholdawakelockatalltimesexceptduringpoll().Thisworksduetosome
  118. //subtlechoreography.Whenadevicedriverhaspending(unread)events,itacquires
  119. //akernelwakelock.However,oncethelastpendingeventhasbeenread,thedevice
  120. //driverwillreleasethekernelwakelock.Topreventthesystemfromgoingtosleep
  121. //whenthishappens,theEventHubholdsontoitsownuserwakelockwhiletheclient
  122. //isprocessingevents.Thusthesystemcanonlysleepiftherearenoevents
  123. //pendingorcurrentlybeingprocessed.
  124. release_wake_lock(WAKE_LOCK_ID);
  125. intpollResult=poll(mFDs,mFDCount,-1);
  126. acquire_wake_lock(PARTIAL_WAKE_LOCK,WAKE_LOCK_ID);
  127. if(pollResult<=0){
  128. if(errno!=EINTR){
  129. LOGW("pollfailed(errno=%d)\n",errno);
  130. usleep(100000);
  131. }
  132. }
  133. }
  134. }

这个函数比较长,我们一步一步来分析。

首先,如果是第一次进入到这个函数中时,成员变量mOpened的值为false,于是就会调用openPlatformInput函数来打开系统输入设备,在本文中,我们主要讨论的输入设备就是键盘了。打开了这些输入设备文件后,就可以对这些输入设备进行是监控了。如果不是第一次进入到这个函数,那么就会分析当前有没有输入事件发生,如果有,就返回这个事件,否则就会进入等待状态,等待下一次输入事件的发生。在我们这个场景中,就是等待下一次键盘事件的发生了。

我们先分析openPlatformInput函数的实现,然后回过头来分析这个getEvent函数的具体的实现。

更多相关文章

  1. 箭头函数的基础使用
  2. Python技巧匿名函数、回调函数和高阶函数
  3. 浅析android通过jni控制service服务程序的简易流程
  4. Android(安卓)bluetooth介绍(四): a2dp connect流程分析
  5. 第17天android:《android从零开始》视频(1-5)
  6. Android(安卓)EditView
  7. Android架构分析之使用自定义硬件抽象层(HAL)模块
  8. [android]在上下文菜单的选中事件中获取列表选中的元素
  9. android 多点触控

随机推荐

  1. 【Android】AsyncTask实现异步处理
  2. Android导入导出txt通讯录工具(源码共享)
  3. Android(安卓)画虚线显示实线的BUG
  4. Android跳转支付宝生活缴费界面
  5. Android(安卓)Activity堆栈信息
  6. 手机上的Wifi分析仪
  7. android视频播放简单实现(VideoView&Media
  8. 快过年了,推荐款好应用
  9. Intent的使用
  10. 使用adb时,为什么只有RockChip的ID需要加