zoukankan      html  css  js  c++  java
  • KeyBord事件分发和接收简要过程代码示例

    step1:调用ViewRootImpl的内部类ImeInputStage的成员函数onProcess来判断输入法是否处于激活状态

    final class ImeInputStage extends AsyncInputStage
    implements InputMethodManager.FinishedInputEventCallback {
    public ImeInputStage(InputStage next, String traceCounter) {
    super(next, traceCounter);
    }
    @Override
    protected int onProcess(QueuedInputEvent q) {
    if (mLastWasImTarget && !isInLocalFocusMode()) {
    InputMethodManager imm = InputMethodManager.peekInstance();
    if (imm != null) {
    final InputEvent event = q.mEvent;
    if (DEBUG_IMF) Log.v(TAG, "Sending input event to IME: " + event);
    int result = imm.dispatchInputEvent(event, q, this, mHandler);
    if (result == InputMethodManager.DISPATCH_HANDLED) {
    return FINISH_HANDLED;
    } else if (result == InputMethodManager.DISPATCH_NOT_HANDLED) {
    return FINISH_NOT_HANDLED;
    } else {return DEFER; // callback will be invoked later
    }
    }
    }
    return FORWARD;
    }

    setp2:调用viewRootImpl的内部类ViewPostImeInputStage的成员函数processKeyEvent

    final class ViewPostImeInputStage extends InputStage {
        public ViewPostImeInputStage(InputStage next) {
    super(next);
    }

    @Override
    protected int onProcess(QueuedInputEvent q) {
    if (q.mEvent instanceof KeyEvent) {
    return processKeyEvent(q);
    } else {
    // If delivering a new non-key event, make sure the window is
    // now allowed to start updating.
    handleDispatchDoneAnimating();
    final int source = q.mEvent.getSource();
    if ((source & InputDevice.SOURCE_CLASS_POINTER) != 0) {
    return processPointerEvent(q);
    } else if ((source & InputDevice.SOURCE_CLASS_TRACKBALL) != 0) {
    return processTrackballEvent(q);
    } else {
    return processGenericMotionEvent(q);
    }
    }
    }

    private int processKeyEvent(QueuedInputEvent q) {
    final KeyEvent event = (KeyEvent) q.mEvent;

    if (event.getAction() != KeyEvent.ACTION_UP) {
    // If delivering a new key event, make sure the window is
    // now allowed to start updating.
    handleDispatchDoneAnimating();
    }

    // Deliver the key to the view hierarchy.
    if (mView.dispatchKeyEvent(event)) {
    return FINISH_HANDLED;
    }
    ....
    }

    setp3:在viewPostImenputStaged的processKeyEvent的函数中调用Decorview的成员函数dispatchKeyEvent
    if (mView.dispatchKeyEvent(event)) {
                return FINISH_HANDLED;
    }


    step4:在DecorView的成员函数dispatchKeyEvent中调用Callback对象的dispatchKeyEvent函数
    private final class DecorView extends FrameLayout implements RootViewSurfaceTaker {
    ...    
    public DecorView(Context context, int featureId) {
    super(context);
    mFeatureId = featureId;
    }
    @Override
    public boolean dispatchKeyEvent(KeyEvent event) {
    final int keyCode = event.getKeyCode();
    final int action = event.getAction();
    final boolean isDown = action == KeyEvent.ACTION_DOWN;

    if (isDown && (event.getRepeatCount() == 0)) {
    // First handle chording of panel key: if a panel key is held
    // but not released, try to execute a shortcut in it.
    if ((mPanelChordingKey > 0) && (mPanelChordingKey != keyCode)) {
    boolean handled = dispatchKeyShortcutEvent(event);
    if (handled) {
    return true;
    }
    }
    if ((mPreparedPanel != null) && mPreparedPanel.isOpen) {
    if (performPanelShortcut(mPreparedPanel, keyCode, event, 0)) {
    return true;
    }
    }
    }
    if (!isDestroyed()) {
    final Callback cb = getCallback();
    final boolean handled = cb != null && mFeatureId < 0 ? cb.dispatchKeyEvent(event)
    : super.dispatchKeyEvent(event);
    if (handled) {
    return true;
    }
    }

    return isDown ? PhoneWindow.this.onKeyDown(mFeatureId, event.getKeyCode(), event)
    : PhoneWindow.this.onKeyUp(mFeatureId, event.getKeyCode(), event);
    }
    ...
    }

    setp5:
    在Callback对象的dispatchKeyEvent的函数中调用PhoneWindow对象的superDispatchKeyEvent函数
    public boolean dispatchKeyEvent(KeyEvent event) {
        onUserInteraction();

    // Let action bars open menus in response to the menu key prioritized over
    // the window handling it
    if (event.getKeyCode() == KeyEvent.KEYCODE_MENU &&
    mActionBar != null && mActionBar.onMenuKeyEvent(event)) {
    return true;
    }
    Window win = getWindow();
    if (win.superDispatchKeyEvent(event)) {
    return true;
    }
    View decor = mDecor;
    if (decor == null) decor = win.getDecorView();
    return event.dispatch(this, decor != null
    ? decor.getKeyDispatcherState() : null, this);
    }
     
     


     



     
  • 相关阅读:
    ssl双向认证
    keycloak管理用户权限
    Apollo单向SSL认证(2)
    Apollo单向SSL认证(1)
    apollo1.7.1初探(二)使用apollo订阅主题,发布主题消息
    apollo1.7.1初探(一)安装apollo、创建并启动broker
    Mosquito集群模式
    什么是MQTT协议?
    物影子操作
    kafka和mqtt的区别是什么?
  • 原文地址:https://www.cnblogs.com/lianghe01/p/5712640.html
Copyright © 2011-2022 走看看