Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 8e327009 authored by Tadashi G. Takaoka's avatar Tadashi G. Takaoka Committed by Android (Google) Code Review
Browse files

Merge "Refactor PointerTracker and MainKeyboardView"

parents 62ac89e1 53b6d627
Loading
Loading
Loading
Loading
+2 −6
Original line number Diff line number Diff line
@@ -269,13 +269,9 @@ public final class MainKeyboardAccessibilityDelegate
                eventTime, eventTime, MotionEvent.ACTION_DOWN, x, y, 0 /* metaState */);
        // Inject a fake down event to {@link PointerTracker} to handle a long press correctly.
        tracker.processMotionEvent(downEvent, mKeyDetector);
        // The above fake down event triggers an unnecessary long press timer that should be
        // canceled.
        tracker.cancelLongPressTimer();
        downEvent.recycle();
        // Invoke {@link MainKeyboardView#onLongPress(PointerTracker)} as if a long press timeout
        // has passed.
        mKeyboardView.onLongPress(tracker);
        // Invoke {@link PointerTracker#onLongPressed()} as if a long press timeout has passed.
        tracker.onLongPressed();
        // If {@link Key#hasNoPanelAutoMoreKeys()} is true (such as "0 +" key on the phone layout)
        // or a key invokes IME switcher dialog, we should just ignore the next
        // {@link #onRegisterHoverKey(Key,MotionEvent)}. It can be determined by whether
+32 −58
Original line number Diff line number Diff line
@@ -461,12 +461,17 @@ public final class MainKeyboardView extends KeyboardView implements DrawingProxy
        windowContentView.addView(mDrawingPreviewPlacerView);
    }

    // Implements {@link DrawingProxy#onKeyPressed(Key,boolean)}.
    @Override
    public void showKeyPreview(@Nonnull final Key key) {
        // If the key is invalid or has no key preview, we must not show key preview.
        if (key.noKeyPreview()) {
            return;
    public void onKeyPressed(@Nonnull final Key key, final boolean withPreview) {
        key.onPressed();
        invalidateKey(key);
        if (withPreview && !key.noKeyPreview()) {
            showKeyPreview(key);
        }
    }

    private void showKeyPreview(@Nonnull final Key key) {
        final Keyboard keyboard = getKeyboard();
        if (keyboard == null) {
            return;
@@ -483,15 +488,26 @@ public final class MainKeyboardView extends KeyboardView implements DrawingProxy
                getWidth(), mOriginCoords, mDrawingPreviewPlacerView, isHardwareAccelerated());
    }

    // Implements {@link DrawingProxy#dismissKeyPreviewWithoutDelay(Key)}.
    @Override
    public void dismissKeyPreviewWithoutDelay(@Nonnull final Key key) {
    private void dismissKeyPreviewWithoutDelay(@Nonnull final Key key) {
        mKeyPreviewChoreographer.dismissKeyPreview(key, false /* withAnimation */);
        invalidateKey(key);
    }

    // Implements {@link DrawingProxy#onKeyReleased(Key,boolean)}.
    @Override
    public void dismissKeyPreview(@Nonnull final Key key) {
    public void onKeyReleased(@Nonnull final Key key, final boolean withAnimation) {
        key.onReleased();
        invalidateKey(key);
        if (!key.noKeyPreview()) {
            if (withAnimation) {
                dismissKeyPreview(key);
            } else {
                dismissKeyPreviewWithoutDelay(key);
            }
        }
    }

    private void dismissKeyPreview(@Nonnull final Key key) {
        if (isHardwareAccelerated()) {
            mKeyPreviewChoreographer.dismissKeyPreview(key, true /* withAnimation */);
            return;
@@ -574,7 +590,11 @@ public final class MainKeyboardView extends KeyboardView implements DrawingProxy
        mDrawingPreviewPlacerView.removeAllViews();
    }

    private MoreKeysPanel onCreateMoreKeysPanel(final Key key, final Context context) {
    // Implements {@link DrawingProxy@showMoreKeysKeyboard(Key,PointerTracker)}.
    @Override
    @Nullable
    public MoreKeysPanel showMoreKeysKeyboard(@Nonnull final Key key,
            @Nonnull final PointerTracker tracker) {
        final MoreKeySpec[] moreKeys = key.getMoreKeys();
        if (moreKeys == null) {
            return null;
@@ -590,7 +610,7 @@ public final class MainKeyboardView extends KeyboardView implements DrawingProxy
                    && !key.noKeyPreview() && moreKeys.length == 1
                    && mKeyPreviewDrawParams.getVisibleWidth() > 0;
            final MoreKeysKeyboard.Builder builder = new MoreKeysKeyboard.Builder(
                    context, key, getKeyboard(), isSingleMoreKeyWithPreview,
                    getContext(), key, getKeyboard(), isSingleMoreKeyWithPreview,
                    mKeyPreviewDrawParams.getVisibleWidth(),
                    mKeyPreviewDrawParams.getVisibleHeight(), newLabelPaint(key));
            moreKeysKeyboard = builder.build();
@@ -603,50 +623,6 @@ public final class MainKeyboardView extends KeyboardView implements DrawingProxy
                (MoreKeysKeyboardView)container.findViewById(R.id.more_keys_keyboard_view);
        moreKeysKeyboardView.setKeyboard(moreKeysKeyboard);
        container.measure(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        return moreKeysKeyboardView;
    }

    // Implements {@link DrawingProxy@onLongPress(PointerTracker)}.
    /**
     * Called when a key is long pressed.
     * @param tracker the pointer tracker which pressed the parent key
     */
    @Override
    public void onLongPress(@Nonnull final PointerTracker tracker) {
        if (isShowingMoreKeysPanel()) {
            return;
        }
        final Key key = tracker.getKey();
        if (key == null) {
            return;
        }
        final KeyboardActionListener listener = mKeyboardActionListener;
        if (key.hasNoPanelAutoMoreKey()) {
            final int moreKeyCode = key.getMoreKeys()[0].mCode;
            tracker.onLongPressed();
            listener.onPressKey(moreKeyCode, 0 /* repeatCount */, true /* isSinglePointer */);
            listener.onCodeInput(moreKeyCode, Constants.NOT_A_COORDINATE,
                    Constants.NOT_A_COORDINATE, false /* isKeyRepeat */);
            listener.onReleaseKey(moreKeyCode, false /* withSliding */);
            return;
        }
        final int code = key.getCode();
        if (code == Constants.CODE_SPACE || code == Constants.CODE_LANGUAGE_SWITCH) {
            // Long pressing the space key invokes IME switcher dialog.
            if (listener.onCustomRequest(Constants.CUSTOM_CODE_SHOW_INPUT_METHOD_PICKER)) {
                tracker.onLongPressed();
                listener.onReleaseKey(code, false /* withSliding */);
                return;
            }
        }
        openMoreKeysPanel(key, tracker);
    }

    private void openMoreKeysPanel(final Key key, final PointerTracker tracker) {
        final MoreKeysPanel moreKeysPanel = onCreateMoreKeysPanel(key, getContext());
        if (moreKeysPanel == null) {
            return;
        }

        final int[] lastCoords = CoordinateUtils.newInstance();
        tracker.getLastCoordinates(lastCoords);
@@ -664,10 +640,8 @@ public final class MainKeyboardView extends KeyboardView implements DrawingProxy
        // {@code mPreviewVisibleOffset} has been set appropriately in
        // {@link KeyboardView#showKeyPreview(PointerTracker)}.
        final int pointY = key.getY() + mKeyPreviewDrawParams.getVisibleOffset();
        moreKeysPanel.showMoreKeysPanel(this, this, pointX, pointY, mKeyboardActionListener);
        tracker.onShowMoreKeysPanel(moreKeysPanel);
        // TODO: Implement zoom in animation of more keys panel.
        mKeyPreviewChoreographer.dismissKeyPreview(key, false /* withAnimation */);
        moreKeysKeyboardView.showMoreKeysPanel(this, this, pointX, pointY, mKeyboardActionListener);
        return moreKeysKeyboardView;
    }

    public boolean isInDraggingFinger() {
+56 −42
Original line number Diff line number Diff line
@@ -222,7 +222,7 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
        final int trackersSize = sTrackers.size();
        for (int i = 0; i < trackersSize; ++i) {
            final PointerTracker tracker = sTrackers.get(i);
            tracker.setReleasedKeyGraphics(tracker.getKey());
            tracker.setReleasedKeyGraphics(tracker.getKey(), true /* withAnimation */);
        }
    }

@@ -382,19 +382,18 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
        return mKeyDetector.detectHitKey(x, y);
    }

    private void setReleasedKeyGraphics(@Nullable final Key key) {
    private void setReleasedKeyGraphics(@Nullable final Key key, final boolean withAnimation) {
        if (key == null) {
            return;
        }

        sDrawingProxy.dismissKeyPreview(key);
        // Even if the key is disabled, update the key release graphics just in case.
        updateReleaseKeyGraphics(key);
        sDrawingProxy.onKeyReleased(key, withAnimation);

        if (key.isShift()) {
            for (final Key shiftKey : mKeyboard.mShiftKeys) {
                if (shiftKey != key) {
                    updateReleaseKeyGraphics(shiftKey);
                    sDrawingProxy.onKeyReleased(shiftKey, false /* withAnimation */);
                }
            }
        }
@@ -403,11 +402,11 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
            final int altCode = key.getAltCode();
            final Key altKey = mKeyboard.getKey(altCode);
            if (altKey != null) {
                updateReleaseKeyGraphics(altKey);
                sDrawingProxy.onKeyReleased(altKey, false /* withAnimation */);
            }
            for (final Key k : mKeyboard.mAltCodeKeysWhileTyping) {
                if (k != key && k.getAltCode() == altCode) {
                    updateReleaseKeyGraphics(k);
                    sDrawingProxy.onKeyReleased(k, false /* withAnimation */);
                }
            }
        }
@@ -418,7 +417,7 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
        return sTypingTimeRecorder.needsToSuppressKeyPreviewPopup(eventTime);
    }

    private void setPressedKeyGraphics(final Key key, final long eventTime) {
    private void setPressedKeyGraphics(@Nullable final Key key, final long eventTime) {
        if (key == null) {
            return;
        }
@@ -430,15 +429,13 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
            return;
        }

        if (!key.noKeyPreview() && !sInGesture && !needsToSuppressKeyPreviewPopup(eventTime)) {
            sDrawingProxy.showKeyPreview(key);
        }
        updatePressKeyGraphics(key);
        final boolean noKeyPreview = sInGesture || needsToSuppressKeyPreviewPopup(eventTime);
        sDrawingProxy.onKeyPressed(key, !noKeyPreview);

        if (key.isShift()) {
            for (final Key shiftKey : mKeyboard.mShiftKeys) {
                if (shiftKey != key) {
                    updatePressKeyGraphics(shiftKey);
                    sDrawingProxy.onKeyPressed(shiftKey, false /* withPreview */);
                }
            }
        }
@@ -447,24 +444,14 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
            final int altCode = key.getAltCode();
            final Key altKey = mKeyboard.getKey(altCode);
            if (altKey != null) {
                updatePressKeyGraphics(altKey);
                sDrawingProxy.onKeyPressed(altKey, false /* withPreview */);
            }
            for (final Key k : mKeyboard.mAltCodeKeysWhileTyping) {
                if (k != key && k.getAltCode() == altCode) {
                    updatePressKeyGraphics(k);
                }
                    sDrawingProxy.onKeyPressed(k, false /* withPreview */);
                }
            }
        }

    private static void updateReleaseKeyGraphics(final Key key) {
        key.onReleased();
        sDrawingProxy.invalidateKey(key);
    }

    private static void updatePressKeyGraphics(final Key key) {
        key.onPressed();
        sDrawingProxy.invalidateKey(key);
    }

    public GestureStrokeDrawingPoints getGestureStrokeDrawingPoints() {
@@ -837,7 +824,7 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
    }

    private void processDraggingFingerOutFromOldKey(final Key oldKey) {
        setReleasedKeyGraphics(oldKey);
        setReleasedKeyGraphics(oldKey, true /* withAnimation */);
        callListenerOnRelease(oldKey, oldKey.getCode(), true /* withSliding */);
        startKeySelectionByDraggingFinger(oldKey);
        sTimerProxy.cancelKeyTimersOf(this);
@@ -880,12 +867,12 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
            }
            onUpEvent(x, y, eventTime);
            cancelTrackingForAction();
            setReleasedKeyGraphics(oldKey);
            setReleasedKeyGraphics(oldKey, true /* withAnimation */);
        } else {
            if (!mIsDetectingGesture) {
                cancelTrackingForAction();
            }
            setReleasedKeyGraphics(oldKey);
            setReleasedKeyGraphics(oldKey, true /* withAnimation */);
        }
    }

@@ -913,7 +900,7 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
            onGestureMoveEvent(x, y, eventTime, true /* isMajorEvent */, newKey);
            if (sInGesture) {
                mCurrentKey = null;
                setReleasedKeyGraphics(oldKey);
                setReleasedKeyGraphics(oldKey, true /* withAnimation */);
                return;
            }
        }
@@ -978,7 +965,7 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
        final int currentRepeatingKeyCode = mCurrentRepeatingKeyCode;
        mCurrentRepeatingKeyCode = Constants.NOT_A_CODE;
        // Release the last pressed key.
        setReleasedKeyGraphics(currentKey);
        setReleasedKeyGraphics(currentKey, true /* withAnimation */);

        if (isShowingMoreKeysPanel()) {
            if (!mIsTrackingForActionDisabled) {
@@ -1015,14 +1002,6 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
        }
    }

    public void onShowMoreKeysPanel(final MoreKeysPanel panel) {
        setReleasedKeyGraphics(mCurrentKey);
        final int translatedX = panel.translateX(mLastX);
        final int translatedY = panel.translateY(mLastY);
        panel.onDownEvent(translatedX, translatedY, mPointerId, SystemClock.uptimeMillis());
        mMoreKeysPanel = panel;
    }

    @Override
    public void cancelTrackingForAction() {
        if (isShowingMoreKeysPanel()) {
@@ -1035,14 +1014,49 @@ public final class PointerTracker implements PointerTrackerQueue.Element,
        return !mIsTrackingForActionDisabled;
    }

    public void cancelLongPressTimer() {
    public void onLongPressed() {
        sTimerProxy.cancelLongPressTimersOf(this);
        if (isShowingMoreKeysPanel()) {
            return;
        }
        final Key key = getKey();
        if (key == null) {
            return;
        }
        if (key.hasNoPanelAutoMoreKey()) {
            cancelKeyTracking();
            final int moreKeyCode = key.getMoreKeys()[0].mCode;
            sListener.onPressKey(moreKeyCode, 0 /* repeatCont */, true /* isSinglePointer */);
            sListener.onCodeInput(moreKeyCode, Constants.NOT_A_COORDINATE,
                    Constants.NOT_A_COORDINATE, false /* isKeyRepeat */);
            sListener.onReleaseKey(moreKeyCode, false /* withSliding */);
            return;
        }
        final int code = key.getCode();
        if (code == Constants.CODE_SPACE || code == Constants.CODE_LANGUAGE_SWITCH) {
            // Long pressing the space key invokes IME switcher dialog.
            if (sListener.onCustomRequest(Constants.CUSTOM_CODE_SHOW_INPUT_METHOD_PICKER)) {
                cancelKeyTracking();
                sListener.onReleaseKey(code, false /* withSliding */);
                return;
            }
        }

    public void onLongPressed() {
        setReleasedKeyGraphics(key, false /* withAnimation */);
        final MoreKeysPanel moreKeysPanel = sDrawingProxy.showMoreKeysKeyboard(key, this);
        if (moreKeysPanel == null) {
            return;
        }
        final int translatedX = moreKeysPanel.translateX(mLastX);
        final int translatedY = moreKeysPanel.translateY(mLastY);
        moreKeysPanel.onDownEvent(translatedX, translatedY, mPointerId, SystemClock.uptimeMillis());
        mMoreKeysPanel = moreKeysPanel;
    }

    private void cancelKeyTracking() {
        resetKeySelectionByDraggingFinger();
        cancelTrackingForAction();
        setReleasedKeyGraphics(mCurrentKey);
        setReleasedKeyGraphics(mCurrentKey, true /* withAnimation */);
        sPointerTrackerQueue.remove(this);
    }

@@ -1059,7 +1073,7 @@ public final class PointerTracker implements PointerTrackerQueue.Element,

    private void onCancelEventInternal() {
        sTimerProxy.cancelKeyTimersOf(this);
        setReleasedKeyGraphics(mCurrentKey);
        setReleasedKeyGraphics(mCurrentKey, true /* withAnimation */);
        resetKeySelectionByDraggingFinger();
        dismissMoreKeysPanel();
    }
+20 −13
Original line number Diff line number Diff line
@@ -17,29 +17,36 @@
package com.android.inputmethod.keyboard.internal;

import com.android.inputmethod.keyboard.Key;
import com.android.inputmethod.keyboard.MoreKeysPanel;
import com.android.inputmethod.keyboard.PointerTracker;

import javax.annotation.Nonnull;
import javax.annotation.Nullable;

public interface DrawingProxy {
    // TODO: Remove this method.
    public void invalidateKey(@Nullable Key key);

    // TODO: Rename this method to onKeyPressed.
    public void showKeyPreview(@Nonnull Key key);

    // TODO: Rename this method to onKeyReleased.
    public void dismissKeyPreview(@Nonnull Key key);
    /**
     * Called when a key is being pressed.
     * @param key the {@link Key} that is being pressed.
     * @param withPreview true if key popup preview should be displayed.
     */
    public void onKeyPressed(@Nonnull Key key, boolean withPreview);

    /**
     * Dismiss a key preview visual without delay.
     * @param key the key whose preview visual should be dismissed.
     * Called when a key is being released.
     * @param key the {@link Key} that is being released.
     * @param withAnimation when true, key popup preview should be dismissed with animation.
     */
    public void dismissKeyPreviewWithoutDelay(@Nonnull Key key);
    public void onKeyReleased(@Nonnull Key key, boolean withAnimation);

    // TODO: Rename this method to onKeyLongPressed.
    public void onLongPress(@Nonnull PointerTracker tracker);
    /**
     * Start showing more keys keyboard of a key that is being long pressed.
     * @param key the {@link Key} that is being long pressed and showing more keys keyboard.
     * @param tracker the {@link PointerTracker} that detects this long pressing.
     * @return {@link MoreKeysPanel} that is being shown. null if there is no need to show more keys
     *     keyboard.
     */
    @Nullable
    public MoreKeysPanel showMoreKeysKeyboard(@Nonnull Key key, @Nonnull PointerTracker tracker);

    /**
     * Start a while-typing-animation.
+2 −3
Original line number Diff line number Diff line
@@ -66,7 +66,7 @@ public final class TimerHandler extends LeakGuardHandlerWrapper<DrawingProxy>
        case MSG_LONGPRESS_SHIFT_KEY:
            cancelLongPressTimers();
            final PointerTracker tracker2 = (PointerTracker) msg.obj;
            drawingProxy.onLongPress(tracker2);
            tracker2.onLongPressed();
            break;
        case MSG_UPDATE_BATCH_INPUT:
            final PointerTracker tracker3 = (PointerTracker) msg.obj;
@@ -74,8 +74,7 @@ public final class TimerHandler extends LeakGuardHandlerWrapper<DrawingProxy>
            startUpdateBatchInputTimer(tracker3);
            break;
        case MSG_DISMISS_KEY_PREVIEW:
            final Key key = (Key) msg.obj;
            drawingProxy.dismissKeyPreviewWithoutDelay(key);
            drawingProxy.onKeyReleased((Key) msg.obj, false /* withAnimation */);
            break;
        case MSG_DISMISS_GESTURE_FLOATING_PREVIEW_TEXT:
            drawingProxy.dismissGestureFloatingPreviewTextWithoutDelay();