IMS:MotionEvent 坐标点(上)

Posted xhBruce

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了IMS:MotionEvent 坐标点(上)相关的知识,希望对你有一定的参考价值。

IMS:MotionEvent 坐标点(上)

android12-security-release
主要查看获取hal底层原始坐标,并通过InputChannel发送流程,其中只关注坐标点


Android屏幕x、y轴

屏幕的左上角作为坐标原点,X轴向右为正,Y轴向下为正。

开发者选项中指针位置、ViewRootImpl坐标

打开IMS:开发者选项中指针位置开关,比较直观查看:


X:640.9 Y:1250.9这个就是坐标点(640.9,1250.9),这里(ps.mCoords.x,ps.mCoords.y)通过PointerEventDispatcher/InputChannel传递上来的MotionEvent

ViewRootImpl是通过WindowInputEventReceiver\\InputChannel传递上来的MotionEvent,实质都是InputEventReceiver\\InputChannel

InputEventReceiver传递MotionEvent

IMS:InputChannel通过socket发送Input给App

frameworks/base/core/java/android/view/InputEventReceiver.java

frameworks/base/core/jni/android_view_InputEventReceiver.cpp

绕不开的JNI

frameworks/base/core/java/android/view/MotionEvent.java
frameworks/base/core/jni/android_view_MotionEvent.cpp
frameworks/native/include/input/Input.h
对象PointerCoords中:

InputDispatcher分发时坐标点

IMS:InputDispatcher线程分发事件
frameworks/native/libs/input/InputTransport.cpp
frameworks/native/services/inputflinger/dispatcher/InputDispatcher.cpp

(motionEntry.xCursorPosition,motionEntry.yCursorPosition)
InputDispatcher.cpp中对象传递:(建议倒着查看流程

mInboundQueue.push_back(std::move(newEntry));【enqueueInboundEventLocked(std::move(newEntry));】
mPendingEvent = mInboundQueue.front();
std::shared_ptr<MotionEntry> motionEntry = std::static_pointer_cast<MotionEntry>(mPendingEvent);
connection->outboundQueue.push_back(dispatchEntry.release());【enqueueDispatchEntryLocked(…)】
DispatchEntry* dispatchEntry = connection->outboundQueue.front();
EventEntry& eventEntry = *(dispatchEntry->eventEntry);
MotionEntry& motionEntry = static_cast<const MotionEntry&>(eventEntry);

InputReader获取处理MotionEvent

IMS:InputReader线程获取输入事件

frameworks/native/services/inputflinger/InputListener.cpp
frameworks/native/services/inputflinger/reader/InputReader.cpp
frameworks/native/services/inputflinger/reader/InputDevice.cpp
size_t count = mEventHub->getEvents(timeoutMillis, mEventBuffer, EVENT_BUFFER_SIZE);
processEventsLocked(mEventBuffer, count);
processEventsForDeviceLocked(deviceId, rawEvent, batchSize);
device->process(rawEvents, count);
mapper.process(rawEvent);

// --- NotifyMotionArgs ---

NotifyMotionArgs::NotifyMotionArgs(
        int32_t id, nsecs_t eventTime, nsecs_t readTime, int32_t deviceId, uint32_t source,
        int32_t displayId, uint32_t policyFlags, int32_t action, int32_t actionButton,
        int32_t flags, int32_t metaState, int32_t buttonState, MotionClassification classification,
        int32_t edgeFlags, uint32_t pointerCount, const PointerProperties* pointerProperties,
        const PointerCoords* pointerCoords, float xPrecision, float yPrecision,
        float xCursorPosition, float yCursorPosition, nsecs_t downTime,
        const std::vector<TouchVideoFrame>& videoFrames)
      : NotifyArgs(id, eventTime),
        deviceId(deviceId),
        source(source),
        displayId(displayId),
        policyFlags(policyFlags),
        action(action),
        actionButton(actionButton),
        flags(flags),
        metaState(metaState),
        buttonState(buttonState),
        classification(classification),
        edgeFlags(edgeFlags),
        pointerCount(pointerCount),
        xPrecision(xPrecision),
        yPrecision(yPrecision),
        xCursorPosition(xCursorPosition),
        yCursorPosition(yCursorPosition),
        downTime(downTime),
        readTime(readTime),
        videoFrames(videoFrames) 
    for (uint32_t i = 0; i < pointerCount; i++) 
        this->pointerProperties[i].copyFrom(pointerProperties[i]);
        this->pointerCoords[i].copyFrom(pointerCoords[i]);
    

//... ...
void NotifyMotionArgs::notify(const sp<InputListenerInterface>& listener) const 
    listener->notifyMotion(this);

SingleTouchInputMapper\\MultiTouchInputMapper处理

  1. EventHub连接硬件设备\\外部设备时,匹配添加相应InputMapper
  2. ......TouchInputMapper::process处理–processRawTouchescookAndDispatchdispatch...dispatchMotion
  3. NotifyMotionArgs 初始化参数xPrecision, yPrecisionmOrientedXPrecision, mOrientedYPrecision
void TouchInputMapper::dispatchMotion(nsecs_t when, nsecs_t readTime, uint32_t policyFlags,
                                      uint32_t source, int32_t action, int32_t actionButton,
                                      int32_t flags, int32_t metaState, int32_t buttonState,
                                      int32_t edgeFlags, const PointerProperties* properties,
                                      const PointerCoords* coords, const uint32_t* idToIndex,
                                      BitSet32 idBits, int32_t changedId, float xPrecision,
                                      float yPrecision, nsecs_t downTime) 
    // ... ...
    NotifyMotionArgs args(getContext()->getNextId(), when, readTime, deviceId, source, displayId,
                          policyFlags, action, actionButton, flags, metaState, buttonState,
                          MotionClassification::NONE, edgeFlags, pointerCount, pointerProperties,
                          pointerCoords, xPrecision, yPrecision, xCursorPosition, yCursorPosition,
                          downTime, std::move(frames));
    getListener()->notifyMotion(&args);

  1. RawPointerAxes

EventHub获取屏幕硬件上报

IMS:EventHub设备底层上报Input事件对象处理

以上是关于IMS:MotionEvent 坐标点(上)的主要内容,如果未能解决你的问题,请参考以下文章

百度地图坐标点的颜色能显示不同颜色吗

C# 计算地图上某个坐标点的到多边形各边的距离

在 sf 对象上设置正确的 crs 以绘制坐标点

怎么计算2个坐标点的距离?

高德地图的Marker和MarkerCluster的应用场景分析

为啥当我放大Windows尺寸时,pyqt5中笔没有在鼠标坐标点上绘画