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

Commit e640689b authored by Ilya Matyukhin's avatar Ilya Matyukhin
Browse files

Fix incorrect state transitions

The illumination dot and HBM would sometimes stay after enrollment or
authentication. This was because the OnTouchListener would pick up
a "fingerDown" event while the dialog was in the process of hiding.

Fixed by removing the listener and forcing the dialog into the
"fingerUp" state when hiding the dialog.

Bug: 162010430
Test: manual on device
Change-Id: Icfc14ce04a6c9ca02538d9ff82caf32d380ee6d1
parent 08f71754
Loading
Loading
Loading
Loading
+21 −11
Original line number Diff line number Diff line
@@ -90,22 +90,23 @@ class UdfpsController {
    @SuppressLint("ClickableViewAccessibility")
    private final UdfpsView.OnTouchListener mOnTouchListener = (v, event) -> {
        UdfpsView view = (UdfpsView) v;
        final boolean isFingerDown = view.isScrimShowing();
        switch (event.getAction()) {
            case MotionEvent.ACTION_DOWN:
            case MotionEvent.ACTION_MOVE:
                boolean isValidTouch = view.isValidTouch(event.getX(), event.getY(),
                final boolean isValidTouch = view.isValidTouch(event.getX(), event.getY(),
                        event.getPressure());
                if (!view.isFingerDown() && isValidTouch) {
                if (!isFingerDown && isValidTouch) {
                    onFingerDown((int) event.getX(), (int) event.getY(), event.getTouchMinor(),
                            event.getTouchMajor());
                } else if (view.isFingerDown() && !isValidTouch) {
                } else if (isFingerDown && !isValidTouch) {
                    onFingerUp();
                }
                return true;

            case MotionEvent.ACTION_UP:
            case MotionEvent.ACTION_CANCEL:
                if (view.isFingerDown()) {
                if (isFingerDown) {
                    onFingerUp();
                }
                return true;
@@ -123,7 +124,6 @@ class UdfpsController {
        mLayoutParams = createLayoutParams(context);

        mView = (UdfpsView) LayoutInflater.from(context).inflate(R.layout.udfps_view, null, false);
        mView.setOnTouchListener(mOnTouchListener);

        mHbmPath = context.getResources().getString(R.string.udfps_hbm_sysfs_path);
        mHbmEnableCommand = context.getResources().getString(R.string.udfps_hbm_enable_command);
@@ -164,25 +164,32 @@ class UdfpsController {

    private void showUdfpsOverlay() {
        mHandler.post(() -> {
            Log.v(TAG, "showUdfpsOverlay | adding window");
            if (!mIsOverlayShowing) {
                try {
                    Log.v(TAG, "showUdfpsOverlay | adding window");
                    mWindowManager.addView(mView, mLayoutParams);
                    mIsOverlayShowing = true;
                    mView.setOnTouchListener(mOnTouchListener);
                } catch (RuntimeException e) {
                    Log.e(TAG, "showUdfpsOverlay | failed to add window", e);
                }
            } else {
                Log.v(TAG, "showUdfpsOverlay | the overlay is already showing");
            }
        });
    }

    private void hideUdfpsOverlay() {
        onFingerUp();
        mHandler.post(() -> {
            Log.v(TAG, "hideUdfpsOverlay | removing window");
            if (mIsOverlayShowing) {
                Log.v(TAG, "hideUdfpsOverlay | removing window");
                mView.setOnTouchListener(null);
                // Reset the controller back to its starting state.
                onFingerUp();
                mWindowManager.removeView(mView);
                mIsOverlayShowing = false;
            } else {
                Log.v(TAG, "hideUdfpsOverlay | the overlay is already hidden");
            }
        });
    }
@@ -215,25 +222,28 @@ class UdfpsController {

    private void onFingerDown(int x, int y, float minor, float major) {
        mView.setScrimAlpha(computeScrimOpacity());
        mView.showScrimAndDot();
        try {
            FileWriter fw = new FileWriter(mHbmPath);
            fw.write(mHbmEnableCommand);
            fw.close();
            mFingerprintManager.onFingerDown(x, y, minor, major);
        } catch (IOException e) {
            mView.hideScrimAndDot();
            Log.e(TAG, "onFingerDown | failed to enable HBM: " + e.getMessage());
        }
        mView.onFingerDown();
        mFingerprintManager.onFingerDown(x, y, minor, major);
    }

    private void onFingerUp() {
        mFingerprintManager.onFingerUp();
        mView.onFingerUp();
        // Hiding the scrim before disabling HBM results in less noticeable flicker.
        mView.hideScrimAndDot();
        try {
            FileWriter fw = new FileWriter(mHbmPath);
            fw.write(mHbmDisableCommand);
            fw.close();
        } catch (IOException e) {
            mView.showScrimAndDot();
            Log.e(TAG, "onFingerUp | failed to disable HBM: " + e.getMessage());
        }
    }
+11 −11
Original line number Diff line number Diff line
@@ -50,7 +50,7 @@ public class UdfpsView extends View {
    private final Rect mTouchableRegion;
    private final ViewTreeObserver.OnComputeInternalInsetsListener mInsetsListener;

    private boolean mIsFingerDown;
    private boolean mIsScrimShowing;

    public UdfpsView(Context context, AttributeSet attrs) {
        super(context, attrs);
@@ -93,7 +93,7 @@ public class UdfpsView extends View {
            internalInsetsInfo.touchableRegion.set(mTouchableRegion);
        };

        mIsFingerDown = false;
        mIsScrimShowing = false;
    }

    @Override
@@ -123,7 +123,7 @@ public class UdfpsView extends View {
    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        if (mIsFingerDown) {
        if (mIsScrimShowing) {
            canvas.drawRect(mScrimRect, mScrimPaint);
        }
        canvas.drawOval(mSensorRect, mSensorPaint);
@@ -140,19 +140,19 @@ public class UdfpsView extends View {
        mScrimPaint.setAlpha(alpha);
    }

    boolean isFingerDown() {
        return mIsFingerDown;
    boolean isScrimShowing() {
        return mIsScrimShowing;
    }

    void onFingerDown() {
        mIsFingerDown = true;
    void showScrimAndDot() {
        mIsScrimShowing = true;
        mSensorPaint.setStyle(Paint.Style.FILL);
        postInvalidate();
        invalidate();
    }

    void onFingerUp() {
        mIsFingerDown = false;
    void hideScrimAndDot() {
        mIsScrimShowing = false;
        mSensorPaint.setStyle(Paint.Style.STROKE);
        postInvalidate();
        invalidate();
    }
}