summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--packages/SystemUI/src/com/android/systemui/ScreenDecorations.java229
-rw-r--r--packages/SystemUI/src/com/android/systemui/decor/RoundedCornerResDelegate.kt201
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/ScreenDecorationsTest.java60
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/decor/RoundedCornerResDelegateTest.kt139
4 files changed, 431 insertions, 198 deletions
diff --git a/packages/SystemUI/src/com/android/systemui/ScreenDecorations.java b/packages/SystemUI/src/com/android/systemui/ScreenDecorations.java
index ae41cae10bba..2f5292cec909 100644
--- a/packages/SystemUI/src/com/android/systemui/ScreenDecorations.java
+++ b/packages/SystemUI/src/com/android/systemui/ScreenDecorations.java
@@ -37,13 +37,11 @@ import android.content.pm.ActivityInfo;
import android.content.res.ColorStateList;
import android.content.res.Configuration;
import android.content.res.Resources;
-import android.content.res.TypedArray;
import android.graphics.Color;
import android.graphics.Matrix;
import android.graphics.Paint;
import android.graphics.Path;
import android.graphics.PixelFormat;
-import android.graphics.Point;
import android.graphics.Rect;
import android.graphics.drawable.Drawable;
import android.hardware.display.DisplayManager;
@@ -53,14 +51,12 @@ import android.os.Handler;
import android.os.SystemProperties;
import android.os.UserHandle;
import android.provider.Settings.Secure;
-import android.util.DisplayMetrics;
-import android.util.DisplayUtils;
import android.util.Log;
+import android.util.Size;
import android.view.DisplayCutout;
import android.view.DisplayCutout.BoundsPosition;
import android.view.Gravity;
import android.view.LayoutInflater;
-import android.view.RoundedCorners;
import android.view.View;
import android.view.View.OnLayoutChangeListener;
import android.view.ViewGroup;
@@ -81,6 +77,7 @@ import com.android.systemui.decor.DecorProviderFactory;
import com.android.systemui.decor.DecorProviderKt;
import com.android.systemui.decor.OverlayWindow;
import com.android.systemui.decor.PrivacyDotDecorProviderFactory;
+import com.android.systemui.decor.RoundedCornerResDelegate;
import com.android.systemui.qs.SettingObserver;
import com.android.systemui.settings.UserTracker;
import com.android.systemui.statusbar.events.PrivacyDotViewController;
@@ -139,11 +136,7 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
// corners. for now it is only supposed when reading the intrinsic size from the drawables with
// mIsRoundedCornerMultipleRadius is set
@VisibleForTesting
- protected Point mRoundedDefault = new Point(0, 0);
- @VisibleForTesting
- protected Point mRoundedDefaultTop = new Point(0, 0);
- @VisibleForTesting
- protected Point mRoundedDefaultBottom = new Point(0, 0);
+ protected RoundedCornerResDelegate mRoundedCornerResDelegate;
@VisibleForTesting
protected OverlayWindow[] mOverlays = null;
@Nullable
@@ -152,17 +145,12 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
ViewGroup mScreenDecorHwcWindow;
@VisibleForTesting
ScreenDecorHwcLayer mScreenDecorHwcLayer;
- private float mDensity;
private WindowManager mWindowManager;
private int mRotation;
private SettingObserver mColorInversionSetting;
private DelayableExecutor mExecutor;
private Handler mHandler;
boolean mPendingRotationChange;
- private boolean mIsRoundedCornerMultipleRadius;
- private Drawable mRoundedCornerDrawable;
- private Drawable mRoundedCornerDrawableTop;
- private Drawable mRoundedCornerDrawableBottom;
@VisibleForTesting
String mDisplayUniqueId;
private int mTintColor = Color.BLACK;
@@ -302,7 +290,8 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
private void startOnScreenDecorationsThread() {
mRotation = mContext.getDisplay().getRotation();
mDisplayUniqueId = mContext.getDisplay().getUniqueId();
- mIsRoundedCornerMultipleRadius = isRoundedCornerMultipleRadius(mContext, mDisplayUniqueId);
+ mRoundedCornerResDelegate = new RoundedCornerResDelegate(mContext.getResources(),
+ mDisplayUniqueId);
mWindowManager = mContext.getSystemService(WindowManager.class);
mDisplayManager = mContext.getSystemService(DisplayManager.class);
mHwcScreenDecorationSupport = mContext.getDisplay().getDisplayDecorationSupport();
@@ -359,8 +348,7 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
final String newUniqueId = mContext.getDisplay().getUniqueId();
if (!Objects.equals(newUniqueId, mDisplayUniqueId)) {
mDisplayUniqueId = newUniqueId;
- mIsRoundedCornerMultipleRadius =
- isRoundedCornerMultipleRadius(mContext, mDisplayUniqueId);
+ mRoundedCornerResDelegate.reloadAll(newUniqueId);
final DisplayDecorationSupport newScreenDecorationSupport =
mContext.getDisplay().getDisplayDecorationSupport();
// When the value of mSupportHwcScreenDecoration is changed, re-setup the whole
@@ -457,9 +445,6 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
if (mIsRegistered) {
return;
}
- DisplayMetrics metrics = new DisplayMetrics();
- mContext.getDisplay().getMetrics(metrics);
- mDensity = metrics.density;
mMainExecutor.execute(() -> mTunerService.addTunable(this, SIZE));
@@ -606,8 +591,8 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
mScreenDecorHwcWindow.addView(mScreenDecorHwcLayer, new FrameLayout.LayoutParams(
MATCH_PARENT, MATCH_PARENT, Gravity.TOP | Gravity.START));
mWindowManager.addView(mScreenDecorHwcWindow, getHwcWindowLayoutParams());
- updateRoundedCornerSize(mRoundedDefault, mRoundedDefaultTop, mRoundedDefaultBottom);
- updateRoundedCornerImageView();
+ updateHwLayerRoundedCornerSize();
+ updateHwLayerRoundedCornerDrawable();
mScreenDecorHwcWindow.getViewTreeObserver().addOnPreDrawListener(
new ValidatingPreDrawListener(mScreenDecorHwcWindow));
}
@@ -640,7 +625,9 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
// update rounded corner view rotation
updateRoundedCornerView(pos, R.id.left, cutout);
updateRoundedCornerView(pos, R.id.right, cutout);
- updateRoundedCornerSize(mRoundedDefault, mRoundedDefaultTop, mRoundedDefaultBottom);
+ updateRoundedCornerSize(
+ mRoundedCornerResDelegate.getTopRoundedSize(),
+ mRoundedCornerResDelegate.getBottomRoundedSize());
updateRoundedCornerImageView();
// update cutout view rotation
@@ -844,7 +831,6 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
public void dump(@NonNull FileDescriptor fd, @NonNull PrintWriter pw, @NonNull String[] args) {
pw.println("ScreenDecorations state:");
pw.println(" DEBUG_DISABLE_SCREEN_DECORATIONS:" + DEBUG_DISABLE_SCREEN_DECORATIONS);
- pw.println(" mIsRoundedCornerMultipleRadius:" + mIsRoundedCornerMultipleRadius);
pw.println(" mIsPrivacyDotEnabled:" + isPrivacyDotEnabled());
pw.println(" mPendingRotationChange:" + mPendingRotationChange);
if (mHwcScreenDecorationSupport != null) {
@@ -862,16 +848,12 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
} else {
pw.println(" mScreenDecorHwcLayer: null");
}
- pw.println(" mRoundedDefault(x,y)=(" + mRoundedDefault.x + "," + mRoundedDefault.y + ")");
- pw.println(" mRoundedDefaultTop(x,y)=(" + mRoundedDefaultTop.x + "," + mRoundedDefaultTop.y
- + ")");
- pw.println(" mRoundedDefaultBottom(x,y)=(" + mRoundedDefaultBottom.x + ","
- + mRoundedDefaultBottom.y + ")");
pw.println(" mOverlays(left,top,right,bottom)=("
+ (mOverlays != null && mOverlays[BOUNDS_POSITION_LEFT] != null) + ","
+ (mOverlays != null && mOverlays[BOUNDS_POSITION_TOP] != null) + ","
+ (mOverlays != null && mOverlays[BOUNDS_POSITION_RIGHT] != null) + ","
+ (mOverlays != null && mOverlays[BOUNDS_POSITION_BOTTOM] != null) + ")");
+ mRoundedCornerResDelegate.dump(fd, pw, args);
}
private void updateOrientation() {
@@ -912,119 +894,18 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
// upgrading all of the configs to contain (width, height) pairs. Instead assume that a
// device configured using the single integer config value is okay with drawing the corners
// as a square
- final int newRoundedDefault = RoundedCorners.getRoundedCornerRadius(
- mContext.getResources(), mDisplayUniqueId);
- final int newRoundedDefaultTop = RoundedCorners.getRoundedCornerTopRadius(
- mContext.getResources(), mDisplayUniqueId);
- final int newRoundedDefaultBottom = RoundedCorners.getRoundedCornerBottomRadius(
- mContext.getResources(), mDisplayUniqueId);
-
- final boolean changed = mRoundedDefault.x != newRoundedDefault
- || mRoundedDefaultTop.x != newRoundedDefaultTop
- || mRoundedDefaultBottom.x != newRoundedDefaultBottom;
-
- if (changed) {
- // If config_roundedCornerMultipleRadius set as true, ScreenDecorations respect the
- // (width, height) size of drawable/rounded.xml instead of rounded_corner_radius
- if (mIsRoundedCornerMultipleRadius) {
- mRoundedDefault.set(mRoundedCornerDrawable.getIntrinsicWidth(),
- mRoundedCornerDrawable.getIntrinsicHeight());
- mRoundedDefaultTop.set(mRoundedCornerDrawableTop.getIntrinsicWidth(),
- mRoundedCornerDrawableTop.getIntrinsicHeight());
- mRoundedDefaultBottom.set(mRoundedCornerDrawableBottom.getIntrinsicWidth(),
- mRoundedCornerDrawableBottom.getIntrinsicHeight());
- } else {
- mRoundedDefault.set(newRoundedDefault, newRoundedDefault);
- mRoundedDefaultTop.set(newRoundedDefaultTop, newRoundedDefaultTop);
- mRoundedDefaultBottom.set(newRoundedDefaultBottom, newRoundedDefaultBottom);
- }
+ final Size oldRoundedDefaultTop = mRoundedCornerResDelegate.getTopRoundedSize();
+ final Size oldRoundedDefaultBottom = mRoundedCornerResDelegate.getBottomRoundedSize();
+ mRoundedCornerResDelegate.reloadAll(mDisplayUniqueId);
+ final Size newRoundedDefaultTop = mRoundedCornerResDelegate.getTopRoundedSize();
+ final Size newRoundedDefaultBottom = mRoundedCornerResDelegate.getBottomRoundedSize();
+
+ if (oldRoundedDefaultTop.getWidth() != newRoundedDefaultTop.getWidth()
+ || oldRoundedDefaultBottom.getWidth() != newRoundedDefaultBottom.getWidth()) {
onTuningChanged(SIZE, null);
}
}
- /**
- * Gets whether the rounded corners are multiple radii for current display.
- *
- * Loads the default config {@link R.bool#config_roundedCornerMultipleRadius} if
- * {@link com.android.internal.R.array#config_displayUniqueIdArray} is not set.
- */
- private static boolean isRoundedCornerMultipleRadius(Context context, String displayUniqueId) {
- final Resources res = context.getResources();
- final int index = DisplayUtils.getDisplayUniqueIdConfigIndex(res, displayUniqueId);
- final TypedArray array = res.obtainTypedArray(
- R.array.config_roundedCornerMultipleRadiusArray);
- boolean isMultipleRadius;
- if (index >= 0 && index < array.length()) {
- isMultipleRadius = array.getBoolean(index, false);
- } else {
- isMultipleRadius = res.getBoolean(R.bool.config_roundedCornerMultipleRadius);
- }
- array.recycle();
- return isMultipleRadius;
- }
-
- /**
- * Gets the rounded corner drawable for current display.
- *
- * Loads the default config {@link R.drawable#rounded} if
- * {@link com.android.internal.R.array#config_displayUniqueIdArray} is not set.
- */
- private static Drawable getRoundedCornerDrawable(Context context, String displayUniqueId) {
- final Resources res = context.getResources();
- final int index = DisplayUtils.getDisplayUniqueIdConfigIndex(res, displayUniqueId);
- final TypedArray array = res.obtainTypedArray(R.array.config_roundedCornerDrawableArray);
- Drawable drawable;
- if (index >= 0 && index < array.length()) {
- drawable = array.getDrawable(index);
- } else {
- drawable = context.getDrawable(R.drawable.rounded);
- }
- array.recycle();
- return drawable;
- }
-
- /**
- * Gets the rounded corner top drawable for current display.
- *
- * Loads the default config {@link R.drawable#rounded_corner_top} if
- * {@link com.android.internal.R.array#config_displayUniqueIdArray} is not set.
- */
- private static Drawable getRoundedCornerTopDrawable(Context context, String displayUniqueId) {
- final Resources res = context.getResources();
- final int index = DisplayUtils.getDisplayUniqueIdConfigIndex(res, displayUniqueId);
- final TypedArray array = res.obtainTypedArray(R.array.config_roundedCornerTopDrawableArray);
- Drawable drawable;
- if (index >= 0 && index < array.length()) {
- drawable = array.getDrawable(index);
- } else {
- drawable = context.getDrawable(R.drawable.rounded_corner_top);
- }
- array.recycle();
- return drawable;
- }
-
- /**
- * Gets the rounded corner bottom drawable for current display.
- *
- * Loads the default config {@link R.drawable#rounded_corner_bottom} if
- * {@link com.android.internal.R.array#config_displayUniqueIdArray} is not set.
- */
- private static Drawable getRoundedCornerBottomDrawable(
- Context context, String displayUniqueId) {
- final Resources res = context.getResources();
- final int index = DisplayUtils.getDisplayUniqueIdConfigIndex(res, displayUniqueId);
- final TypedArray array = res.obtainTypedArray(
- R.array.config_roundedCornerBottomDrawableArray);
- Drawable drawable;
- if (index >= 0 && index < array.length()) {
- drawable = array.getDrawable(index);
- } else {
- drawable = context.getDrawable(R.drawable.rounded_corner_bottom);
- }
- array.recycle();
- return drawable;
- }
-
private void updateRoundedCornerView(@BoundsPosition int pos, int id,
@Nullable DisplayCutout cutout) {
final View rounded = mOverlays[pos].getRootView().findViewById(id);
@@ -1085,10 +966,9 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
}
}
private boolean hasRoundedCorners() {
- return mRoundedDefault.x > 0
- || mRoundedDefaultBottom.x > 0
- || mRoundedDefaultTop.x > 0
- || mIsRoundedCornerMultipleRadius;
+ return mRoundedCornerResDelegate.getBottomRoundedSize().getWidth() > 0
+ || mRoundedCornerResDelegate.getTopRoundedSize().getWidth() > 0
+ || mRoundedCornerResDelegate.isMultipleRadius();
}
private boolean isDefaultShownOverlayPos(@BoundsPosition int pos,
@@ -1154,33 +1034,28 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
mExecutor.execute(() -> {
if (mOverlays == null) return;
if (SIZE.equals(key)) {
- Point size = mRoundedDefault;
- Point sizeTop = mRoundedDefaultTop;
- Point sizeBottom = mRoundedDefaultBottom;
if (newValue != null) {
try {
- int s = (int) (Integer.parseInt(newValue) * mDensity);
- size = new Point(s, s);
+ mRoundedCornerResDelegate.updateTuningSizeFactor(
+ Integer.parseInt(newValue));
} catch (Exception e) {
}
}
- updateRoundedCornerSize(size, sizeTop, sizeBottom);
+ updateRoundedCornerSize(
+ mRoundedCornerResDelegate.getTopRoundedSize(),
+ mRoundedCornerResDelegate.getBottomRoundedSize());
}
});
}
private void updateRoundedCornerDrawable() {
- mRoundedCornerDrawable = getRoundedCornerDrawable(mContext, mDisplayUniqueId);
- mRoundedCornerDrawableTop = getRoundedCornerTopDrawable(mContext, mDisplayUniqueId);
- mRoundedCornerDrawableBottom = getRoundedCornerBottomDrawable(mContext, mDisplayUniqueId);
+ mRoundedCornerResDelegate.reloadAll(mDisplayUniqueId);
updateRoundedCornerImageView();
}
private void updateRoundedCornerImageView() {
- final Drawable top = mRoundedCornerDrawableTop != null
- ? mRoundedCornerDrawableTop : mRoundedCornerDrawable;
- final Drawable bottom = mRoundedCornerDrawableBottom != null
- ? mRoundedCornerDrawableBottom : mRoundedCornerDrawable;
+ final Drawable top = mRoundedCornerResDelegate.getTopRoundedDrawable();
+ final Drawable bottom = mRoundedCornerResDelegate.getBottomRoundedDrawable();
if (mScreenDecorHwcLayer != null) {
mScreenDecorHwcLayer.updateRoundedCornerDrawable(top, bottom);
@@ -1205,6 +1080,20 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
}
}
+ private void updateHwLayerRoundedCornerDrawable() {
+ if (mScreenDecorHwcLayer == null) {
+ return;
+ }
+
+ final Drawable topDrawable = mRoundedCornerResDelegate.getTopRoundedDrawable();
+ final Drawable bottomDrawable = mRoundedCornerResDelegate.getBottomRoundedDrawable();
+
+ if (topDrawable == null || bottomDrawable == null) {
+ return;
+ }
+ mScreenDecorHwcLayer.updateRoundedCornerDrawable(topDrawable, bottomDrawable);
+ }
+
@VisibleForTesting
boolean isTopRoundedCorner(@BoundsPosition int pos, int id) {
switch (pos) {
@@ -1224,19 +1113,21 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
}
}
- private void updateRoundedCornerSize(
- Point sizeDefault,
- Point sizeTop,
- Point sizeBottom) {
- if (sizeTop.x == 0) {
- sizeTop = sizeDefault;
- }
- if (sizeBottom.x == 0) {
- sizeBottom = sizeDefault;
+ private void updateHwLayerRoundedCornerSize() {
+ if (mScreenDecorHwcLayer == null) {
+ return;
}
+ final int topWidth = mRoundedCornerResDelegate.getTopRoundedSize().getWidth();
+ final int bottomWidth = mRoundedCornerResDelegate.getBottomRoundedSize().getWidth();
+
+ mScreenDecorHwcLayer.updateRoundedCornerSize(topWidth, bottomWidth);
+ }
+
+ private void updateRoundedCornerSize(Size sizeTop, Size sizeBottom) {
+
if (mScreenDecorHwcLayer != null) {
- mScreenDecorHwcLayer.updateRoundedCornerSize(sizeTop.x, sizeBottom.x);
+ mScreenDecorHwcLayer.updateRoundedCornerSize(sizeTop.getWidth(), sizeBottom.getWidth());
return;
}
@@ -1256,10 +1147,10 @@ public class ScreenDecorations extends CoreStartable implements Tunable , Dumpab
}
@VisibleForTesting
- protected void setSize(View view, Point pixelSize) {
+ protected void setSize(View view, Size pixelSize) {
LayoutParams params = view.getLayoutParams();
- params.width = pixelSize.x;
- params.height = pixelSize.y;
+ params.width = pixelSize.getWidth();
+ params.height = pixelSize.getHeight();
view.setLayoutParams(params);
}
diff --git a/packages/SystemUI/src/com/android/systemui/decor/RoundedCornerResDelegate.kt b/packages/SystemUI/src/com/android/systemui/decor/RoundedCornerResDelegate.kt
new file mode 100644
index 000000000000..c817f89c7a9b
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/decor/RoundedCornerResDelegate.kt
@@ -0,0 +1,201 @@
+/*
+ * Copyright (C) 2022 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.systemui.decor
+
+import android.annotation.ArrayRes
+import android.annotation.DrawableRes
+import android.content.res.Resources
+import android.graphics.drawable.Drawable
+import android.util.DisplayUtils
+import android.util.Size
+import android.view.RoundedCorners
+import com.android.systemui.Dumpable
+import com.android.systemui.R
+import java.io.FileDescriptor
+import java.io.PrintWriter
+
+class RoundedCornerResDelegate(
+ private val res: Resources,
+ private var displayUniqueId: String?
+) : Dumpable {
+
+ private val density: Float
+ get() = res.displayMetrics.density
+
+ var isMultipleRadius: Boolean = false
+ private set
+
+ private var roundedDrawable: Drawable? = null
+
+ var topRoundedDrawable: Drawable? = null
+ private set
+
+ var bottomRoundedDrawable: Drawable? = null
+ private set
+
+ private var roundedSize = Size(0, 0)
+
+ var topRoundedSize = Size(0, 0)
+ private set
+
+ var bottomRoundedSize = Size(0, 0)
+ private set
+
+ init {
+ reloadDrawables()
+ reloadMeasures()
+ }
+
+ fun reloadAll(newDisplayUniqueId: String?) {
+ displayUniqueId = newDisplayUniqueId
+ reloadDrawables()
+ reloadMeasures()
+ }
+
+ private fun reloadDrawables() {
+ val configIdx = DisplayUtils.getDisplayUniqueIdConfigIndex(res, displayUniqueId)
+ isMultipleRadius = getIsMultipleRadius(configIdx)
+
+ roundedDrawable = getDrawable(
+ displayConfigIndex = configIdx,
+ arrayResId = R.array.config_roundedCornerDrawableArray,
+ backupDrawableId = R.drawable.rounded
+ )
+ topRoundedDrawable = getDrawable(
+ displayConfigIndex = configIdx,
+ arrayResId = R.array.config_roundedCornerTopDrawableArray,
+ backupDrawableId = R.drawable.rounded_corner_top
+ ) ?: roundedDrawable
+ bottomRoundedDrawable = getDrawable(
+ displayConfigIndex = configIdx,
+ arrayResId = R.array.config_roundedCornerBottomDrawableArray,
+ backupDrawableId = R.drawable.rounded_corner_bottom
+ ) ?: roundedDrawable
+
+ // If config_roundedCornerMultipleRadius set as true, ScreenDecorations respect the
+ // (width, height) size of drawable/rounded.xml instead of rounded_corner_radius
+ if (isMultipleRadius) {
+ roundedSize = Size(
+ roundedDrawable?.intrinsicWidth ?: 0,
+ roundedDrawable?.intrinsicHeight ?: 0)
+ topRoundedDrawable?.let {
+ topRoundedSize = Size(it.intrinsicWidth, it.intrinsicHeight)
+ }
+ bottomRoundedDrawable?.let {
+ bottomRoundedSize = Size(it.intrinsicWidth, it.intrinsicHeight)
+ }
+ } else {
+ val defaultRadius = RoundedCorners.getRoundedCornerRadius(res, displayUniqueId)
+ val topRadius = RoundedCorners.getRoundedCornerTopRadius(res, displayUniqueId)
+ val bottomRadius = RoundedCorners.getRoundedCornerBottomRadius(res, displayUniqueId)
+ roundedSize = Size(defaultRadius, defaultRadius)
+ topRoundedSize = Size(topRadius, topRadius)
+ bottomRoundedSize = Size(bottomRadius, bottomRadius)
+ }
+
+ if (topRoundedSize.width == 0) {
+ topRoundedSize = roundedSize
+ }
+ if (bottomRoundedSize.width == 0) {
+ bottomRoundedSize = roundedSize
+ }
+ }
+
+ private fun reloadMeasures(roundedSizeFactor: Int? = null) {
+ // If config_roundedCornerMultipleRadius set as true, ScreenDecorations respect the
+ // (width, height) size of drawable/rounded.xml instead of rounded_corner_radius
+ if (isMultipleRadius) {
+ roundedSize = Size(
+ roundedDrawable?.intrinsicWidth ?: 0,
+ roundedDrawable?.intrinsicHeight ?: 0)
+ topRoundedDrawable?.let {
+ topRoundedSize = Size(it.intrinsicWidth, it.intrinsicHeight)
+ }
+ bottomRoundedDrawable?.let {
+ bottomRoundedSize = Size(it.intrinsicWidth, it.intrinsicHeight)
+ }
+ } else {
+ val defaultRadius = RoundedCorners.getRoundedCornerRadius(res, displayUniqueId)
+ val topRadius = RoundedCorners.getRoundedCornerTopRadius(res, displayUniqueId)
+ val bottomRadius = RoundedCorners.getRoundedCornerBottomRadius(res, displayUniqueId)
+ roundedSize = Size(defaultRadius, defaultRadius)
+ topRoundedSize = Size(topRadius, topRadius)
+ bottomRoundedSize = Size(bottomRadius, bottomRadius)
+ }
+
+ roundedSizeFactor ?.let {
+ val length: Int = (it * density).toInt()
+ roundedSize = Size(length, length)
+ }
+
+ if (topRoundedSize.width == 0) {
+ topRoundedSize = roundedSize
+ }
+ if (bottomRoundedSize.width == 0) {
+ bottomRoundedSize = roundedSize
+ }
+ }
+
+ fun updateTuningSizeFactor(factor: Int) {
+ reloadMeasures(factor)
+ }
+
+ /**
+ * Gets whether the rounded corners are multiple radii for current display.
+ *
+ * Loads the default config {@link R.bool#config_roundedCornerMultipleRadius} if
+ * {@link com.android.internal.R.array#config_displayUniqueIdArray} is not set.
+ */
+ private fun getIsMultipleRadius(displayConfigIndex: Int): Boolean {
+ val isMultipleRadius: Boolean
+ res.obtainTypedArray(R.array.config_roundedCornerMultipleRadiusArray).let { array ->
+ isMultipleRadius = if (displayConfigIndex >= 0 && displayConfigIndex < array.length()) {
+ array.getBoolean(displayConfigIndex, false)
+ } else {
+ res.getBoolean(R.bool.config_roundedCornerMultipleRadius)
+ }
+ array.recycle()
+ }
+ return isMultipleRadius
+ }
+
+ private fun getDrawable(
+ displayConfigIndex: Int,
+ @ArrayRes arrayResId: Int,
+ @DrawableRes backupDrawableId: Int
+ ): Drawable? {
+ val drawable: Drawable?
+ res.obtainTypedArray(arrayResId).let { array ->
+ drawable = if (displayConfigIndex >= 0 && displayConfigIndex < array.length()) {
+ array.getDrawable(displayConfigIndex)
+ } else {
+ res.getDrawable(backupDrawableId, null)
+ }
+ array.recycle()
+ }
+ return drawable
+ }
+
+ override fun dump(fd: FileDescriptor, pw: PrintWriter, args: Array<out String>) {
+ pw.println("RoundedCornerResDelegate state:")
+ pw.println(" isMultipleRadius:$isMultipleRadius")
+ pw.println(" roundedSize(w,h)=(${roundedSize.width},${roundedSize.height})")
+ pw.println(" topRoundedSize(w,h)=(${topRoundedSize.width},${topRoundedSize.height})")
+ pw.println(" bottomRoundedSize(w,h)=(${bottomRoundedSize.width}," +
+ "${bottomRoundedSize.height})")
+ }
+} \ No newline at end of file
diff --git a/packages/SystemUI/tests/src/com/android/systemui/ScreenDecorationsTest.java b/packages/SystemUI/tests/src/com/android/systemui/ScreenDecorationsTest.java
index 70f325158624..ec92adb0f48c 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/ScreenDecorationsTest.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/ScreenDecorationsTest.java
@@ -48,7 +48,6 @@ import android.content.res.Configuration;
import android.content.res.TypedArray;
import android.graphics.Insets;
import android.graphics.PixelFormat;
-import android.graphics.Point;
import android.graphics.Rect;
import android.graphics.drawable.VectorDrawable;
import android.hardware.display.DisplayManager;
@@ -58,6 +57,7 @@ import android.testing.AndroidTestingRunner;
import android.testing.TestableLooper;
import android.testing.TestableLooper.RunWithLooper;
import android.util.RotationUtils;
+import android.util.Size;
import android.view.Display;
import android.view.DisplayCutout;
import android.view.View;
@@ -73,6 +73,7 @@ import com.android.systemui.decor.DecorProvider;
import com.android.systemui.decor.OverlayWindow;
import com.android.systemui.decor.PrivacyDotCornerDecorProviderImpl;
import com.android.systemui.decor.PrivacyDotDecorProviderFactory;
+import com.android.systemui.decor.RoundedCornerResDelegate;
import com.android.systemui.settings.UserTracker;
import com.android.systemui.statusbar.events.PrivacyDotViewController;
import com.android.systemui.tuner.TunerService;
@@ -95,8 +96,6 @@ import java.util.ArrayList;
@SmallTest
public class ScreenDecorationsTest extends SysuiTestCase {
- private static final Rect ZERO_RECT = new Rect();
-
private ScreenDecorations mScreenDecorations;
private WindowManager mWindowManager;
private DisplayManager mDisplayManager;
@@ -424,7 +423,7 @@ public class ScreenDecorationsTest extends SysuiTestCase {
@Test
public void testRoundingRadius_NoCutout() {
- final Point testRadiusPoint = new Point(1, 1);
+ final Size testRadiusPoint = new Size(1, 1);
setupResources(1 /* radius */, 1 /* radiusTop */, 1 /* radiusBottom */,
0 /* roundedPadding */, false /* multipleRadius */,
false /* fillCutout */, true /* privacyDot */);
@@ -433,9 +432,9 @@ public class ScreenDecorationsTest extends SysuiTestCase {
mScreenDecorations.start();
// Size of corner view should same as rounded_corner_radius{_top|_bottom}
- assertThat(mScreenDecorations.mRoundedDefault).isEqualTo(testRadiusPoint);
- assertThat(mScreenDecorations.mRoundedDefaultTop).isEqualTo(testRadiusPoint);
- assertThat(mScreenDecorations.mRoundedDefaultBottom).isEqualTo(testRadiusPoint);
+ final RoundedCornerResDelegate resDelegate = mScreenDecorations.mRoundedCornerResDelegate;
+ assertThat(resDelegate.getTopRoundedSize()).isEqualTo(testRadiusPoint);
+ assertThat(resDelegate.getBottomRoundedSize()).isEqualTo(testRadiusPoint);
}
@Test
@@ -454,17 +453,17 @@ public class ScreenDecorationsTest extends SysuiTestCase {
View rightRoundedCorner = mScreenDecorations.mOverlays[BOUNDS_POSITION_TOP].getRootView()
.findViewById(R.id.right);
verify(mScreenDecorations, atLeastOnce())
- .setSize(leftRoundedCorner, new Point(testTopRadius, testTopRadius));
+ .setSize(leftRoundedCorner, new Size(testTopRadius, testTopRadius));
verify(mScreenDecorations, atLeastOnce())
- .setSize(rightRoundedCorner, new Point(testTopRadius, testTopRadius));
+ .setSize(rightRoundedCorner, new Size(testTopRadius, testTopRadius));
leftRoundedCorner = mScreenDecorations.mOverlays[BOUNDS_POSITION_BOTTOM].getRootView()
.findViewById(R.id.left);
rightRoundedCorner = mScreenDecorations.mOverlays[BOUNDS_POSITION_BOTTOM].getRootView()
.findViewById(R.id.right);
verify(mScreenDecorations, atLeastOnce())
- .setSize(leftRoundedCorner, new Point(testBottomRadius, testBottomRadius));
+ .setSize(leftRoundedCorner, new Size(testBottomRadius, testBottomRadius));
verify(mScreenDecorations, atLeastOnce())
- .setSize(rightRoundedCorner, new Point(testBottomRadius, testBottomRadius));
+ .setSize(rightRoundedCorner, new Size(testBottomRadius, testBottomRadius));
}
@Test
@@ -480,8 +479,8 @@ public class ScreenDecorationsTest extends SysuiTestCase {
.when(mScreenDecorations).getCutout();
mScreenDecorations.start();
- final Point topRadius = new Point(testTopRadius, testTopRadius);
- final Point bottomRadius = new Point(testBottomRadius, testBottomRadius);
+ final Size topRadius = new Size(testTopRadius, testTopRadius);
+ final Size bottomRadius = new Size(testBottomRadius, testBottomRadius);
View leftRoundedCorner = mScreenDecorations.mOverlays[BOUNDS_POSITION_LEFT].getRootView()
.findViewById(R.id.left);
boolean isTop = mScreenDecorations.isTopRoundedCorner(BOUNDS_POSITION_LEFT, R.id.left);
@@ -510,7 +509,7 @@ public class ScreenDecorationsTest extends SysuiTestCase {
@Test
public void testRoundingMultipleRadius_NoCutout_NoPrivacyDot() {
final VectorDrawable d = (VectorDrawable) mContext.getDrawable(R.drawable.rounded);
- final Point multipleRadiusSize = new Point(d.getIntrinsicWidth(), d.getIntrinsicHeight());
+ final Size multipleRadiusSize = new Size(d.getIntrinsicWidth(), d.getIntrinsicHeight());
setupResources(9999 /* radius */, 0 /* radiusTop */, 0 /* radiusBottom */,
9999 /* roundedPadding */, true /* multipleRadius */,
false /* fillCutout */, false /* privacyDot */);
@@ -536,15 +535,15 @@ public class ScreenDecorationsTest extends SysuiTestCase {
verify(mDotViewController, never()).initialize(any(), any(), any(), any());
// Size of corner view should exactly match max(width, height) of R.drawable.rounded
- assertThat(mScreenDecorations.mRoundedDefault).isEqualTo(multipleRadiusSize);
- assertThat(mScreenDecorations.mRoundedDefaultTop).isEqualTo(multipleRadiusSize);
- assertThat(mScreenDecorations.mRoundedDefaultBottom).isEqualTo(multipleRadiusSize);
+ final RoundedCornerResDelegate resDelegate = mScreenDecorations.mRoundedCornerResDelegate;
+ assertThat(resDelegate.getTopRoundedSize()).isEqualTo(multipleRadiusSize);
+ assertThat(resDelegate.getBottomRoundedSize()).isEqualTo(multipleRadiusSize);
}
@Test
public void testRoundingMultipleRadius_NoCutout_PrivacyDot() {
final VectorDrawable d = (VectorDrawable) mContext.getDrawable(R.drawable.rounded);
- final Point multipleRadiusSize = new Point(d.getIntrinsicWidth(), d.getIntrinsicHeight());
+ final Size multipleRadiusSize = new Size(d.getIntrinsicWidth(), d.getIntrinsicHeight());
setupResources(9999 /* radius */, 0 /* radiusTop */, 0 /* radiusBottom */,
9999 /* roundedPadding */, true /* multipleRadius */,
false /* fillCutout */, true /* privacyDot */);
@@ -571,9 +570,9 @@ public class ScreenDecorationsTest extends SysuiTestCase {
isA(View.class), isA(View.class), isA(View.class), isA(View.class));
// Size of corner view should exactly match max(width, height) of R.drawable.rounded
- assertThat(mScreenDecorations.mRoundedDefault).isEqualTo(multipleRadiusSize);
- assertThat(mScreenDecorations.mRoundedDefaultTop).isEqualTo(multipleRadiusSize);
- assertThat(mScreenDecorations.mRoundedDefaultBottom).isEqualTo(multipleRadiusSize);
+ final RoundedCornerResDelegate resDelegate = mScreenDecorations.mRoundedCornerResDelegate;
+ assertThat(resDelegate.getTopRoundedSize()).isEqualTo(multipleRadiusSize);
+ assertThat(resDelegate.getBottomRoundedSize()).isEqualTo(multipleRadiusSize);
}
@Test
@@ -944,12 +943,15 @@ public class ScreenDecorationsTest extends SysuiTestCase {
false /* fillCutout */, true /* privacyDot */);
mScreenDecorations.start();
- assertEquals(mScreenDecorations.mRoundedDefault, new Point(20, 20));
+ final RoundedCornerResDelegate resDelegate = mScreenDecorations.mRoundedCornerResDelegate;
+ assertEquals(resDelegate.getTopRoundedSize(), new Size(20, 20));
+ assertEquals(resDelegate.getBottomRoundedSize(), new Size(20, 20));
when(mContext.getResources().getDimensionPixelSize(
com.android.internal.R.dimen.rounded_corner_radius)).thenReturn(5);
mScreenDecorations.onConfigurationChanged(null);
- assertEquals(mScreenDecorations.mRoundedDefault, new Point(5, 5));
+ assertEquals(resDelegate.getTopRoundedSize(), new Size(5, 5));
+ assertEquals(resDelegate.getBottomRoundedSize(), new Size(5, 5));
}
@Test
@@ -959,9 +961,9 @@ public class ScreenDecorationsTest extends SysuiTestCase {
false /* fillCutout */, true /* privacyDot */);
mScreenDecorations.start();
- assertEquals(new Point(0, 0), mScreenDecorations.mRoundedDefault);
- assertEquals(new Point(10, 10), mScreenDecorations.mRoundedDefaultTop);
- assertEquals(new Point(0, 0), mScreenDecorations.mRoundedDefaultBottom);
+ final RoundedCornerResDelegate resDelegate = mScreenDecorations.mRoundedCornerResDelegate;
+ assertEquals(new Size(10, 10), resDelegate.getTopRoundedSize());
+ assertEquals(new Size(0, 0), resDelegate.getBottomRoundedSize());
}
@Test
@@ -971,9 +973,9 @@ public class ScreenDecorationsTest extends SysuiTestCase {
false /* fillCutout */, true /* privacyDot */);
mScreenDecorations.start();
- assertEquals(new Point(0, 0), mScreenDecorations.mRoundedDefault);
- assertEquals(new Point(0, 0), mScreenDecorations.mRoundedDefaultTop);
- assertEquals(new Point(20, 20), mScreenDecorations.mRoundedDefaultBottom);
+ final RoundedCornerResDelegate resDelegate = mScreenDecorations.mRoundedCornerResDelegate;
+ assertEquals(new Size(0, 0), resDelegate.getTopRoundedSize());
+ assertEquals(new Size(20, 20), resDelegate.getBottomRoundedSize());
}
@Test
diff --git a/packages/SystemUI/tests/src/com/android/systemui/decor/RoundedCornerResDelegateTest.kt b/packages/SystemUI/tests/src/com/android/systemui/decor/RoundedCornerResDelegateTest.kt
new file mode 100644
index 000000000000..b536bfdb944e
--- /dev/null
+++ b/packages/SystemUI/tests/src/com/android/systemui/decor/RoundedCornerResDelegateTest.kt
@@ -0,0 +1,139 @@
+/*
+ * Copyright (C) 2022 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.systemui.decor
+
+import android.content.res.TypedArray
+import android.graphics.drawable.VectorDrawable
+import android.testing.AndroidTestingRunner
+import android.testing.TestableResources
+import android.util.Size
+import androidx.test.filters.SmallTest
+import com.android.systemui.R
+import com.android.systemui.SysuiTestCase
+import org.junit.Assert.assertEquals
+import org.junit.Before
+import org.junit.Test
+
+import org.junit.runner.RunWith
+import org.mockito.Mock
+import org.mockito.MockitoAnnotations
+
+@RunWith(AndroidTestingRunner::class)
+@SmallTest
+class RoundedCornerResDelegateTest : SysuiTestCase() {
+
+ private lateinit var roundedCornerResDelegate: RoundedCornerResDelegate
+ @Mock private lateinit var mockTypedArray: TypedArray
+
+ @Before
+ fun setUp() {
+ MockitoAnnotations.initMocks(this)
+ }
+
+ @Test
+ fun testReloadAllAndDefaultRadius() {
+ mContext.orCreateTestableResources.addOverrides(
+ mockTypeArray = mockTypedArray,
+ radius = 3,
+ radiusTop = 0,
+ radiusBottom = 4,
+ multipleRadius = false)
+
+ roundedCornerResDelegate = RoundedCornerResDelegate(mContext.resources, null)
+
+ assertEquals(Size(3, 3), roundedCornerResDelegate.topRoundedSize)
+ assertEquals(Size(4, 4), roundedCornerResDelegate.bottomRoundedSize)
+ assertEquals(false, roundedCornerResDelegate.isMultipleRadius)
+
+ mContext.orCreateTestableResources.addOverrides(
+ mockTypeArray = mockTypedArray,
+ radius = 5,
+ radiusTop = 6,
+ radiusBottom = 0)
+
+ roundedCornerResDelegate.reloadAll("test")
+
+ assertEquals(Size(6, 6), roundedCornerResDelegate.topRoundedSize)
+ assertEquals(Size(5, 5), roundedCornerResDelegate.bottomRoundedSize)
+ }
+
+ @Test
+ fun testUpdateTuningSizeFactor() {
+ mContext.orCreateTestableResources.addOverrides(
+ mockTypeArray = mockTypedArray,
+ radiusTop = 0,
+ radiusBottom = 0,
+ multipleRadius = false)
+
+ roundedCornerResDelegate = RoundedCornerResDelegate(mContext.resources, null)
+
+ val factor = 5
+ roundedCornerResDelegate.updateTuningSizeFactor(factor)
+ val length = (factor * mContext.resources.displayMetrics.density).toInt()
+
+ assertEquals(Size(length, length), roundedCornerResDelegate.topRoundedSize)
+ assertEquals(Size(length, length), roundedCornerResDelegate.bottomRoundedSize)
+ }
+
+ @Test
+ fun testReadDefaultRadiusWhen0() {
+ mContext.orCreateTestableResources.addOverrides(
+ mockTypeArray = mockTypedArray,
+ radius = 3,
+ radiusTop = 0,
+ radiusBottom = 0,
+ multipleRadius = false)
+
+ roundedCornerResDelegate = RoundedCornerResDelegate(mContext.resources, null)
+
+ assertEquals(Size(3, 3), roundedCornerResDelegate.topRoundedSize)
+ assertEquals(Size(3, 3), roundedCornerResDelegate.bottomRoundedSize)
+ }
+
+ @Test
+ fun testReadMultipleRadius() {
+ val d = mContext.getDrawable(R.drawable.rounded) as VectorDrawable
+ val multipleRadiusSize = Size(d.intrinsicWidth, d.intrinsicHeight)
+ mContext.orCreateTestableResources.addOverrides(
+ mockTypeArray = mockTypedArray,
+ multipleRadius = true)
+ roundedCornerResDelegate = RoundedCornerResDelegate(mContext.resources, null)
+ assertEquals(multipleRadiusSize, roundedCornerResDelegate.topRoundedSize)
+ assertEquals(multipleRadiusSize, roundedCornerResDelegate.bottomRoundedSize)
+ }
+}
+
+private fun TestableResources.addOverrides(
+ mockTypeArray: TypedArray,
+ radius: Int? = null,
+ radiusTop: Int? = null,
+ radiusBottom: Int? = null,
+ multipleRadius: Boolean? = null
+) {
+ addOverride(com.android.internal.R.array.config_displayUniqueIdArray, arrayOf<String>())
+ addOverride(com.android.internal.R.array.config_roundedCornerRadiusArray, mockTypeArray)
+ addOverride(com.android.internal.R.array.config_roundedCornerTopRadiusArray, mockTypeArray)
+ addOverride(com.android.internal.R.array.config_roundedCornerBottomRadiusArray, mockTypeArray)
+ addOverride(R.array.config_roundedCornerDrawableArray, mockTypeArray)
+ addOverride(R.array.config_roundedCornerTopDrawableArray, mockTypeArray)
+ addOverride(R.array.config_roundedCornerBottomDrawableArray, mockTypeArray)
+ addOverride(R.array.config_roundedCornerMultipleRadiusArray, mockTypeArray)
+ radius?.let { addOverride(com.android.internal.R.dimen.rounded_corner_radius, it) }
+ radiusTop?.let { addOverride(com.android.internal.R.dimen.rounded_corner_radius_top, it) }
+ radiusBottom?.let { addOverride(com.android.internal.R.dimen.rounded_corner_radius_bottom, it) }
+ multipleRadius?.let { addOverride(R.bool.config_roundedCornerMultipleRadius, it) }
+} \ No newline at end of file