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

Commit 344519f5 authored by Fabian Kozynski's avatar Fabian Kozynski
Browse files

Fix defined DrawableWrappers with proper ConstantState

DrawableWrappers extend from InsetDrawable instead, so a proper internal
state is created. This way, we can use the proper drawable attribute and
delegate most of the work to DrawableWrapper correctly.

Also, create ConstantState that are able to create new instances of the
correct drawables.

Fixes: 179928515
Fixes: 175026098
Test: manual
Change-Id: I8d07fd518ad66e6c456f7a1a6aa31fbaa18ba8aa
parent ef1fdf18
Loading
Loading
Loading
Loading
+0 −5
Original line number Diff line number Diff line
@@ -168,7 +168,6 @@

    <declare-styleable name="AlphaTintDrawableWrapper">
        <attr name="android:tint" />
        <attr name="android:drawable" />
        <attr name="android:alpha" />
    </declare-styleable>

@@ -189,9 +188,5 @@
        <attr name="borderThickness" format="dimension" />
        <attr name="borderColor" format="color" />
    </declare-styleable>

    <declare-styleable name="RoundedCornerProgressDrawable">
        <attr name="android:drawable" />
    </declare-styleable>
</resources>
+0 −34
Original line number Diff line number Diff line
@@ -17,8 +17,6 @@
package com.android.systemui.settings.brightness;

import android.content.Context;
import android.graphics.drawable.Drawable;
import android.graphics.drawable.LayerDrawable;
import android.view.LayoutInflater;
import android.view.MotionEvent;
import android.view.View;
@@ -29,10 +27,8 @@ import android.widget.SeekBar;
import androidx.annotation.Nullable;

import com.android.settingslib.RestrictedLockUtils;
import com.android.settingslib.Utils;
import com.android.systemui.R;
import com.android.systemui.statusbar.policy.BrightnessMirrorController;
import com.android.systemui.util.RoundedCornerProgressDrawable;
import com.android.systemui.util.ViewController;

import javax.inject.Inject;
@@ -274,9 +270,6 @@ public class BrightnessSlider
        private BrightnessSlider fromTree(ViewGroup root, boolean useMirror) {
            BrightnessSliderView v = root.requireViewById(R.id.brightness_slider);

            // TODO(175026098) Workaround. Remove when b/175026098 is fixed
            applyTheme(v);

            return new BrightnessSlider(root, v, useMirror);
        }

@@ -286,32 +279,5 @@ public class BrightnessSlider
                    ? R.layout.quick_settings_brightness_dialog_thick
                    : R.layout.quick_settings_brightness_dialog;
        }

        private LayerDrawable findProgressClippableDrawable(BrightnessSliderView v) {
            SeekBar b = v.requireViewById(R.id.slider);
            if (b.getProgressDrawable() instanceof LayerDrawable) {
                Drawable progress = ((LayerDrawable) b.getProgressDrawable())
                        .findDrawableByLayerId(com.android.internal.R.id.progress);
                if (progress instanceof RoundedCornerProgressDrawable) {
                    Drawable inner = ((RoundedCornerProgressDrawable) progress).getDrawable();
                    if (inner instanceof LayerDrawable) {
                        return (LayerDrawable) inner;
                    }
                }
            }
            return null;
        }

        private void applyTheme(BrightnessSliderView v) {
            LayerDrawable layer = findProgressClippableDrawable(v);
            if (layer != null) {
                layer.findDrawableByLayerId(R.id.slider_foreground).setTintList(
                        Utils.getColorAttr(v.getContext(),
                                com.android.internal.R.attr.colorControlActivated));
                layer.findDrawableByLayerId(R.id.slider_icon).setTintList(
                        Utils.getColorAttr(v.getContext(),
                                com.android.internal.R.attr.colorBackground));
            }
        }
    }
}
+66 −8
Original line number Diff line number Diff line
@@ -16,15 +16,18 @@

package com.android.systemui.util;

import android.annotation.NonNull;
import android.annotation.Nullable;
import android.content.res.ColorStateList;
import android.content.res.Resources;
import android.content.res.Resources.Theme;
import android.content.res.TypedArray;
import android.graphics.drawable.Drawable;
import android.graphics.drawable.DrawableWrapper;
import android.graphics.drawable.InsetDrawable;
import android.util.AttributeSet;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;

import com.android.systemui.R;

import org.xmlpull.v1.XmlPullParser;
@@ -45,13 +48,18 @@ import java.io.IOException;
 * @attr ref R.styleable#AlphaTintDrawableWrapper_tint
 * @attr ref R.styleable#AlphaTintDrawableWrapper_alpha
 */
public class AlphaTintDrawableWrapper extends DrawableWrapper {
public class AlphaTintDrawableWrapper extends InsetDrawable {
    private ColorStateList mTint;
    private int[] mThemeAttrs;

    /** No-arg constructor used by drawable inflation. */
    public AlphaTintDrawableWrapper() {
        super(null);
        super(null, 0);
    }

    AlphaTintDrawableWrapper(Drawable drawable, int[] themeAttrs) {
        super(drawable, 0);
        mThemeAttrs = themeAttrs;
    }

    @Override
@@ -74,7 +82,7 @@ public class AlphaTintDrawableWrapper extends DrawableWrapper {
    public void applyTheme(Theme t) {
        super.applyTheme(t);

        if (mThemeAttrs != null) {
        if (mThemeAttrs != null && t != null) {
            final TypedArray a = t.resolveAttributes(mThemeAttrs,
                    R.styleable.AlphaTintDrawableWrapper);
            updateStateFromTypedArray(a);
@@ -92,9 +100,6 @@ public class AlphaTintDrawableWrapper extends DrawableWrapper {
    }

    private void updateStateFromTypedArray(@NonNull TypedArray a) {
        if (a.hasValue(R.styleable.AlphaTintDrawableWrapper_android_drawable)) {
            setDrawable(a.getDrawable(R.styleable.AlphaTintDrawableWrapper_android_drawable));
        }
        if (a.hasValue(R.styleable.AlphaTintDrawableWrapper_android_tint)) {
            mTint = a.getColorStateList(R.styleable.AlphaTintDrawableWrapper_android_tint);
        }
@@ -109,4 +114,57 @@ public class AlphaTintDrawableWrapper extends DrawableWrapper {
            getDrawable().mutate().setTintList(mTint);
        }
    }

    @Nullable
    @Override
    public ConstantState getConstantState() {
        return new AlphaTintState(super.getConstantState(), mThemeAttrs, getAlpha(), mTint);
    }

    static class AlphaTintState extends Drawable.ConstantState {

        private ConstantState mWrappedState;
        private int[] mThemeAttrs;
        private int mAlpha;
        private ColorStateList mColorStateList;

        AlphaTintState(
                ConstantState wrappedState,
                int[] themeAttrs,
                int alpha,
                ColorStateList colorStateList
        ) {
            mWrappedState = wrappedState;
            mThemeAttrs = themeAttrs;
            mAlpha = alpha;
            mColorStateList = colorStateList;
        }

        @NonNull
        @Override
        public Drawable newDrawable() {
            return newDrawable(null, null);
        }

        @NonNull
        @Override
        public Drawable newDrawable(Resources res, Theme theme) {
            DrawableWrapper wrapper = (DrawableWrapper) mWrappedState.newDrawable(res, theme);
            AlphaTintDrawableWrapper alphaTintDrawableWrapper =
                    new AlphaTintDrawableWrapper(wrapper.getDrawable(), mThemeAttrs);
            alphaTintDrawableWrapper.setTintList(mColorStateList);
            alphaTintDrawableWrapper.setAlpha(mAlpha);
            return alphaTintDrawableWrapper;
        }

        @Override
        public boolean canApplyTheme() {
            return true;
        }

        @Override
        public int getChangingConfigurations() {
            return mWrappedState.getChangingConfigurations();
        }
    }
}
+24 −31
Original line number Diff line number Diff line
@@ -17,15 +17,12 @@
package com.android.systemui.util

import android.content.res.Resources
import android.content.res.TypedArray
import android.graphics.Canvas
import android.graphics.Path
import android.graphics.Rect
import android.graphics.drawable.Drawable
import android.graphics.drawable.DrawableWrapper
import android.util.AttributeSet
import com.android.systemui.R
import org.xmlpull.v1.XmlPullParser
import android.graphics.drawable.InsetDrawable

/**
 * [DrawableWrapper] to use in the progress of a slider.
@@ -38,9 +35,9 @@ import org.xmlpull.v1.XmlPullParser
 * is meant to be smaller than the rounded corner. The background should have rounded corners that
 * are half of the height.
 */
class RoundedCornerProgressDrawable(drawable: Drawable?) : DrawableWrapper(drawable) {

    constructor() : this(null)
class RoundedCornerProgressDrawable @JvmOverloads constructor(
    drawable: Drawable? = null
) : InsetDrawable(drawable, 0) {

    companion object {
        private const val MAX_LEVEL = 10000 // Taken from Drawable
@@ -52,35 +49,11 @@ class RoundedCornerProgressDrawable(drawable: Drawable?) : DrawableWrapper(drawa
        setClipPath(Rect())
    }

    override fun inflate(
        r: Resources,
        parser: XmlPullParser,
        attrs: AttributeSet,
        theme: Resources.Theme?
    ) {
        val a = obtainAttributes(r, theme, attrs, R.styleable.RoundedCornerProgressDrawable)

        // Inflation will advance the XmlPullParser and AttributeSet.
        super.inflate(r, parser, attrs, theme)

        updateStateFromTypedArray(a)
        if (drawable == null) {
            throw IllegalStateException("${this::class.java.simpleName} needs a drawable")
        }
        a.recycle()
    }

    override fun onLayoutDirectionChanged(layoutDirection: Int): Boolean {
        onLevelChange(level)
        return super.onLayoutDirectionChanged(layoutDirection)
    }

    private fun updateStateFromTypedArray(a: TypedArray) {
        if (a.hasValue(R.styleable.RoundedCornerProgressDrawable_android_drawable)) {
            setDrawable(a.getDrawable(R.styleable.RoundedCornerProgressDrawable_android_drawable))
        }
    }

    override fun onBoundsChange(bounds: Rect) {
        setClipPath(bounds)
        super.onBoundsChange(bounds)
@@ -115,4 +88,24 @@ class RoundedCornerProgressDrawable(drawable: Drawable?) : DrawableWrapper(drawa
        super.draw(canvas)
        canvas.restore()
    }

    override fun getConstantState(): ConstantState? {
        // This should not be null as it was created with a state in the constructor.
        return RoundedCornerState(super.getConstantState()!!)
    }

    private class RoundedCornerState(private val wrappedState: ConstantState) : ConstantState() {
        override fun newDrawable(): Drawable {
            return newDrawable(null, null)
        }

        override fun newDrawable(res: Resources?, theme: Resources.Theme?): Drawable {
            val wrapper = wrappedState.newDrawable(res, theme) as DrawableWrapper
            return RoundedCornerProgressDrawable(wrapper.drawable)
        }

        override fun getChangingConfigurations(): Int {
            return wrappedState.changingConfigurations
        }
    }
}
 No newline at end of file