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

Commit ad4f7030 authored by Chet Haase's avatar Chet Haase
Browse files

Fix flashing artifacts caused by invalidation bugs

Therea re 2 fixes here:
- We sometimes cleared a flag in ViewAncestor too soon that controlled
how invalidated areas were redrawn (related to whether the invalidates
happened on opaque views or not).
- TransitionDrawable was always setting/restoring alpha values on its
drawables every time it was drawn. setAlpha on BitmapDrawable causes
an invalidation, so essentially this was an infinite invalidation/redrawing
loop. The fix was to notice when the animation was done and to simply
draw the appropriate drawable[s].

Change-Id: I1849a5a909b0039a0e9bce0aa3cfc33c50f8f854
parent 8969d992
Loading
Loading
Loading
Loading
+11 −2
Original line number Diff line number Diff line
@@ -288,6 +288,10 @@ public final class ViewAncestor extends Handler implements ViewParent,

    private final int mDensity;

    // This flag tracks when the mIgnoreDirtyState flag is set during draw(), to avoid
    // clearing that flag prematurely
    private boolean mSetIgnoreDirtyState = false;

    /**
     * Consistency verifier for debugging purposes.
     */
@@ -672,6 +676,7 @@ public final class ViewAncestor extends Handler implements ViewParent,
            }
        }
        if (!mDirty.isEmpty() && !mDirty.contains(dirty)) {
            mSetIgnoreDirtyState = true;
            mAttachInfo.mIgnoreDirtyState = true;
        }
        mDirty.union(dirty);
@@ -1878,10 +1883,14 @@ public final class ViewAncestor extends Handler implements ViewParent,
                        }
                        canvas.setScreenDensity(scalingRequired
                                ? DisplayMetrics.DENSITY_DEVICE : 0);
                        mSetIgnoreDirtyState = false;
                        mView.draw(canvas);
                    } finally {
                        if (!mSetIgnoreDirtyState) {
                            // Only clear the flag if it was not set during the mView.draw() call
                            mAttachInfo.mIgnoreDirtyState = false;
                        }
                    }

                    if (false && ViewDebug.consistencyCheckEnabled) {
                        mView.dispatchConsistencyCheck(ViewDebug.CONSISTENCY_DRAWING);
+5 −2
Original line number Diff line number Diff line
@@ -405,9 +405,12 @@ public class BitmapDrawable extends Drawable {

    @Override
    public void setAlpha(int alpha) {
        int oldAlpha = mBitmapState.mPaint.getAlpha();
        if (alpha != oldAlpha) {
            mBitmapState.mPaint.setAlpha(alpha);
            invalidateSelf();
        }
    }

    @Override
    public void setColorFilter(ColorFilter cf) {
+13 −1
Original line number Diff line number Diff line
@@ -187,8 +187,20 @@ public class TransitionDrawable extends LayerDrawable implements Drawable.Callba
        final int alpha = mAlpha;
        final boolean crossFade = mCrossFade;
        final ChildDrawable[] array = mLayerState.mChildren;
        Drawable d;

        if (done) {
            // the setAlpha() calls below trigger invalidation and redraw. If we're done, just draw
            // the appropriate drawable[s] and return
            if (!crossFade || alpha == 0) {
                array[0].mDrawable.draw(canvas);
            }
            if (alpha == 0xFF) {
                array[1].mDrawable.draw(canvas);
            }
            return;
        }

        Drawable d;
        d = array[0].mDrawable;
        if (crossFade) {
            d.setAlpha(255 - alpha);