From 24ba675fe406c32e07a03be9483a8a71ffd98177 Mon Sep 17 00:00:00 2001 From: Yuri Lin Date: Mon, 12 Aug 2024 17:45:49 -0400 Subject: [PATCH] Add images for interstitial pages. This change removes the custom rounding of corners, as the provided images already have rounded corners. Bug: 332730534 Test: manual (light & dark mode, various font/display sizes) Flag: android.app.modes_ui Change-Id: I71d0707554e5bc638add6a2907874e18e833da08 --- .../modes_interstitial_bedtime.xml | 62 +++++++++ .../modes_interstitial_driving.xml | 81 +++++++++++ .../modes_interstitial_immersive.xml | 83 +++++++++++ .../modes_interstitial_managed.xml | 56 ++++++++ .../modes_interstitial_other.xml | 118 ++++++++++++++++ .../modes_interstitial_theater.xml | 69 ++++++++++ .../modes_interstitial_unknown.xml | 65 +++++++++ res/drawable/modes_interstitial_bedtime.xml | 62 +++++++++ res/drawable/modes_interstitial_driving.xml | 81 +++++++++++ res/drawable/modes_interstitial_immersive.xml | 83 +++++++++++ res/drawable/modes_interstitial_managed.xml | 57 ++++++++ res/drawable/modes_interstitial_other.xml | 118 ++++++++++++++++ res/drawable/modes_interstitial_theater.xml | 77 +++++++++++ res/drawable/modes_interstitial_unknown.xml | 65 +++++++++ res/layout-land/mode_interstitial_layout.xml | 2 +- res/layout/mode_interstitial_layout.xml | 4 +- res/values/dimens.xml | 2 - .../modes/SetupInterstitialActivity.java | 109 +++------------ .../modes/SetupInterstitialActivityTest.java | 130 ------------------ 19 files changed, 1096 insertions(+), 228 deletions(-) create mode 100644 res/drawable-night/modes_interstitial_bedtime.xml create mode 100644 res/drawable-night/modes_interstitial_driving.xml create mode 100644 res/drawable-night/modes_interstitial_immersive.xml create mode 100644 res/drawable-night/modes_interstitial_managed.xml create mode 100644 res/drawable-night/modes_interstitial_other.xml create mode 100644 res/drawable-night/modes_interstitial_theater.xml create mode 100644 res/drawable-night/modes_interstitial_unknown.xml create mode 100644 res/drawable/modes_interstitial_bedtime.xml create mode 100644 res/drawable/modes_interstitial_driving.xml create mode 100644 res/drawable/modes_interstitial_immersive.xml create mode 100644 res/drawable/modes_interstitial_managed.xml create mode 100644 res/drawable/modes_interstitial_other.xml create mode 100644 res/drawable/modes_interstitial_theater.xml create mode 100644 res/drawable/modes_interstitial_unknown.xml diff --git a/res/drawable-night/modes_interstitial_bedtime.xml b/res/drawable-night/modes_interstitial_bedtime.xml new file mode 100644 index 00000000000..f28bb017170 --- /dev/null +++ b/res/drawable-night/modes_interstitial_bedtime.xml @@ -0,0 +1,62 @@ + + + + + + + + + + + + + + + diff --git a/res/drawable-night/modes_interstitial_driving.xml b/res/drawable-night/modes_interstitial_driving.xml new file mode 100644 index 00000000000..6edbfe51aad --- /dev/null +++ b/res/drawable-night/modes_interstitial_driving.xml @@ -0,0 +1,81 @@ + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/drawable-night/modes_interstitial_immersive.xml b/res/drawable-night/modes_interstitial_immersive.xml new file mode 100644 index 00000000000..a29c4743174 --- /dev/null +++ b/res/drawable-night/modes_interstitial_immersive.xml @@ -0,0 +1,83 @@ + + + + + + + + + + + + + + + + + + + + diff --git a/res/drawable-night/modes_interstitial_managed.xml b/res/drawable-night/modes_interstitial_managed.xml new file mode 100644 index 00000000000..05f8f6a3ceb --- /dev/null +++ b/res/drawable-night/modes_interstitial_managed.xml @@ -0,0 +1,56 @@ + + + + + + + + + + + + + + diff --git a/res/drawable-night/modes_interstitial_other.xml b/res/drawable-night/modes_interstitial_other.xml new file mode 100644 index 00000000000..2bbed99d5ff --- /dev/null +++ b/res/drawable-night/modes_interstitial_other.xml @@ -0,0 +1,118 @@ + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/drawable-night/modes_interstitial_theater.xml b/res/drawable-night/modes_interstitial_theater.xml new file mode 100644 index 00000000000..d17b167d2b0 --- /dev/null +++ b/res/drawable-night/modes_interstitial_theater.xml @@ -0,0 +1,69 @@ + + + + + + + + + + + + + + + + + + diff --git a/res/drawable-night/modes_interstitial_unknown.xml b/res/drawable-night/modes_interstitial_unknown.xml new file mode 100644 index 00000000000..4047e13c7e3 --- /dev/null +++ b/res/drawable-night/modes_interstitial_unknown.xml @@ -0,0 +1,65 @@ + + + + + + + + + + + + + + + + + + + diff --git a/res/drawable/modes_interstitial_bedtime.xml b/res/drawable/modes_interstitial_bedtime.xml new file mode 100644 index 00000000000..24061ca85cc --- /dev/null +++ b/res/drawable/modes_interstitial_bedtime.xml @@ -0,0 +1,62 @@ + + + + + + + + + + + + + + + diff --git a/res/drawable/modes_interstitial_driving.xml b/res/drawable/modes_interstitial_driving.xml new file mode 100644 index 00000000000..eba51f476bf --- /dev/null +++ b/res/drawable/modes_interstitial_driving.xml @@ -0,0 +1,81 @@ + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/drawable/modes_interstitial_immersive.xml b/res/drawable/modes_interstitial_immersive.xml new file mode 100644 index 00000000000..d901e232226 --- /dev/null +++ b/res/drawable/modes_interstitial_immersive.xml @@ -0,0 +1,83 @@ + + + + + + + + + + + + + + + + + + + + diff --git a/res/drawable/modes_interstitial_managed.xml b/res/drawable/modes_interstitial_managed.xml new file mode 100644 index 00000000000..c54aeaec4d9 --- /dev/null +++ b/res/drawable/modes_interstitial_managed.xml @@ -0,0 +1,57 @@ + + + + + + + + + + + + + + diff --git a/res/drawable/modes_interstitial_other.xml b/res/drawable/modes_interstitial_other.xml new file mode 100644 index 00000000000..096de3918c7 --- /dev/null +++ b/res/drawable/modes_interstitial_other.xml @@ -0,0 +1,118 @@ + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/res/drawable/modes_interstitial_theater.xml b/res/drawable/modes_interstitial_theater.xml new file mode 100644 index 00000000000..78356b47803 --- /dev/null +++ b/res/drawable/modes_interstitial_theater.xml @@ -0,0 +1,77 @@ + + + + + + + + + + + + + + + + + + diff --git a/res/drawable/modes_interstitial_unknown.xml b/res/drawable/modes_interstitial_unknown.xml new file mode 100644 index 00000000000..a68f71a8ca1 --- /dev/null +++ b/res/drawable/modes_interstitial_unknown.xml @@ -0,0 +1,65 @@ + + + + + + + + + + + + + + + + + + + diff --git a/res/layout-land/mode_interstitial_layout.xml b/res/layout-land/mode_interstitial_layout.xml index 14201853c88..597196cbb8d 100644 --- a/res/layout-land/mode_interstitial_layout.xml +++ b/res/layout-land/mode_interstitial_layout.xml @@ -114,7 +114,7 @@ android:layout_width="match_parent" android:layout_height="match_parent" android:adjustViewBounds="true" - android:scaleType="centerCrop" + android:scaleType="fitCenter" android:layout_gravity="center" /> diff --git a/res/layout/mode_interstitial_layout.xml b/res/layout/mode_interstitial_layout.xml index d0f80a77af7..2deaf9f6321 100644 --- a/res/layout/mode_interstitial_layout.xml +++ b/res/layout/mode_interstitial_layout.xml @@ -56,7 +56,7 @@ android:layout_height="match_parent" android:adjustViewBounds="true" android:clickable="false" - android:scaleType="centerCrop" + android:scaleType="fitCenter" android:layout_gravity="center" /> @@ -78,7 +78,7 @@ android:clickable="false" android:text="@string/zen_mode_setup_page_summary" android:textSize="18sp" - android:paddingBottom="12dp" + android:paddingBottom="18dp" android:textAppearance="@*android:style/TextAppearance.DeviceDefault.Body1" app:layout_constraintBottom_toTopOf="@+id/enable_mode_button" /> diff --git a/res/values/dimens.xml b/res/values/dimens.xml index 3a327c98a12..689262fa3e8 100755 --- a/res/values/dimens.xml +++ b/res/values/dimens.xml @@ -519,6 +519,4 @@ 4dp 8dp 18dp - - 30dp diff --git a/src/com/android/settings/notification/modes/SetupInterstitialActivity.java b/src/com/android/settings/notification/modes/SetupInterstitialActivity.java index 225ded0632b..f26de76844b 100644 --- a/src/com/android/settings/notification/modes/SetupInterstitialActivity.java +++ b/src/com/android/settings/notification/modes/SetupInterstitialActivity.java @@ -16,25 +16,21 @@ package com.android.settings.notification.modes; -import static android.graphics.drawable.GradientDrawable.LINEAR_GRADIENT; -import static android.graphics.drawable.GradientDrawable.Orientation.BL_TR; +import static android.app.AutomaticZenRule.TYPE_BEDTIME; +import static android.app.AutomaticZenRule.TYPE_DRIVING; +import static android.app.AutomaticZenRule.TYPE_IMMERSIVE; +import static android.app.AutomaticZenRule.TYPE_MANAGED; +import static android.app.AutomaticZenRule.TYPE_OTHER; +import static android.app.AutomaticZenRule.TYPE_THEATER; import static android.provider.Settings.EXTRA_AUTOMATIC_ZEN_RULE_ID; import android.app.ActionBar; import android.content.Context; import android.content.Intent; -import android.graphics.Color; -import android.graphics.Outline; -import android.graphics.drawable.Drawable; -import android.graphics.drawable.GradientDrawable; import android.os.Bundle; import android.util.Log; import android.view.View; -import android.view.ViewGroup; -import android.view.ViewOutlineProvider; -import android.view.ViewTreeObserver; import android.widget.Button; -import android.widget.FrameLayout; import android.widget.ImageView; import android.widget.TextView; import android.widget.Toast; @@ -58,17 +54,6 @@ public class SetupInterstitialActivity extends FragmentActivity { private static final String TAG = "ModeSetupInterstitial"; private ZenModesBackend mBackend; - private final ViewOutlineProvider mOutlineProvider = new ViewOutlineProvider() { - @Override - public void getOutline(View view, Outline outline) { - // Provides a rounded rectangle outline whose width & height matches the View. - float cornerRadius = getResources().getDimensionPixelSize( - R.dimen.zen_mode_interstitial_corner_radius); - outline.setRoundRect(0, 0, view.getMeasuredWidth(), view.getMeasuredHeight(), - cornerRadius); - } - }; - /** * Returns an intent leading to this page for the given mode and context. */ @@ -150,79 +135,17 @@ public class SetupInterstitialActivity extends FragmentActivity { } private void setImage(@NonNull ImageView img, @NonNull ZenMode mode) { - img.setImageDrawable(getModeDrawable(mode)); - img.setClipToOutline(true); - img.setOutlineProvider(mOutlineProvider); + int drawableRes = switch (mode.getType()) { + case TYPE_BEDTIME -> R.drawable.modes_interstitial_bedtime; + case TYPE_DRIVING -> R.drawable.modes_interstitial_driving; + case TYPE_IMMERSIVE -> R.drawable.modes_interstitial_immersive; + case TYPE_THEATER -> R.drawable.modes_interstitial_theater; + case TYPE_MANAGED -> R.drawable.modes_interstitial_managed; + case TYPE_OTHER -> R.drawable.modes_interstitial_other; + default -> R.drawable.modes_interstitial_unknown; + }; - FrameLayout frame = findViewById(R.id.image_frame); - if (frame == null) { - return; - } - if (img.getMeasuredWidth() == 0) { - // set up to resize after the global layout occurs - img.getViewTreeObserver().addOnGlobalLayoutListener( - new ViewTreeObserver.OnGlobalLayoutListener() { - @Override - public void onGlobalLayout() { - img.getViewTreeObserver().removeOnGlobalLayoutListener(this); - sizeImageToFrame(img, frame); - } - }); - } else { - // measured already, resize it now - sizeImageToFrame(img, frame); - } - } - - private Drawable getModeDrawable(@NonNull ZenMode mode) { - // TODO: b/332730534 - set actual images depending on mode type (asynchronously?) - GradientDrawable placeholder = new GradientDrawable(); - placeholder.setSize(40, 60); // 4x6 rectangle, slightly taller than wide - placeholder.setGradientType(LINEAR_GRADIENT); - placeholder.setOrientation(BL_TR); - placeholder.setColors(new int[]{Color.BLACK, Color.WHITE}); - return placeholder; - } - - @VisibleForTesting - protected void sizeImageToFrame(ImageView img, FrameLayout frame) { - // width of the space we have available = overall size of frame - relevant padding - int frameHeight = - frame.getMeasuredHeight() - frame.getPaddingTop() - frame.getPaddingBottom(); - int frameWidth = - frame.getMeasuredWidth() - frame.getPaddingLeft() - frame.getPaddingRight(); - - int imgHeight = img.getDrawable().getIntrinsicHeight(); - int imgWidth = img.getDrawable().getIntrinsicWidth(); - - // if any of these are 0, give up because we won't be able to do the relevant math (and - // we probably don't have the relevant data set up) - if (frameHeight == 0 || frameWidth == 0 || imgHeight == 0 || imgWidth == 0) { - Log.w(TAG, "image or frame has invalid size parameters"); - return; - } - float frameHWRatio = ((float) frameHeight) / frameWidth; - float imgHWRatio = ((float) imgHeight) / imgWidth; - - // fit horizontal dimension if the frame has a taller ratio (height/width) than the image; - // otherwise, fit the vertical direction - boolean fitHorizontal = frameHWRatio > imgHWRatio; - - ViewGroup.LayoutParams layoutParams = img.getLayoutParams(); - if (layoutParams == null) { - Log.w(TAG, "image has null LayoutParams"); - return; - } - if (fitHorizontal) { - layoutParams.width = frameWidth; - float scaledHeight = imgHWRatio * frameWidth; - layoutParams.height = (int) scaledHeight; - } else { - layoutParams.height = frameHeight; - float scaledWidth = /* w/h ratio */ (1 / imgHWRatio) * frameHeight; - layoutParams.width = (int) scaledWidth; - } - img.setLayoutParams(layoutParams); + img.setImageResource(drawableRes); } private void setupButton(Button button, @NonNull ZenMode mode) { diff --git a/tests/robotests/src/com/android/settings/notification/modes/SetupInterstitialActivityTest.java b/tests/robotests/src/com/android/settings/notification/modes/SetupInterstitialActivityTest.java index 129e56e548c..40bf1c725e9 100644 --- a/tests/robotests/src/com/android/settings/notification/modes/SetupInterstitialActivityTest.java +++ b/tests/robotests/src/com/android/settings/notification/modes/SetupInterstitialActivityTest.java @@ -150,134 +150,4 @@ public class SetupInterstitialActivityTest { }); scenario.close(); } - - @Test - public void setImageToFrame_sizeZero() { - ActivityScenario scenario = - ActivityScenario.launch(new Intent(Intent.ACTION_MAIN) - .setClass(RuntimeEnvironment.getApplication(), - SetupInterstitialActivity.class) - .putExtra(EXTRA_AUTOMATIC_ZEN_RULE_ID, MODE_ID)); - scenario.onActivity(activity -> { - // when either the image or the frame has a size 0, we do nothing - when(mDrawable.getIntrinsicWidth()).thenReturn(0); - when(mDrawable.getIntrinsicHeight()).thenReturn(25); - when(mFrame.getMeasuredWidth()).thenReturn(40); - when(mFrame.getMeasuredHeight()).thenReturn(50); - - activity.sizeImageToFrame(mImage, mFrame); - verify(mImage, never()).setLayoutParams(any()); - }); - scenario.close(); - } - - @Test - public void setImageToFrame_imageLargerThanFrame() { - ActivityScenario scenario = - ActivityScenario.launch(new Intent(Intent.ACTION_MAIN) - .setClass(RuntimeEnvironment.getApplication(), - SetupInterstitialActivity.class) - .putExtra(EXTRA_AUTOMATIC_ZEN_RULE_ID, MODE_ID)); - scenario.onActivity(activity -> { - // image: 900(w)x1500(h); frame: 600(w)x500(h) - // image expected to be scaled down to match the height of the frame -> 300(w)x500(h) - when(mDrawable.getIntrinsicWidth()).thenReturn(900); - when(mDrawable.getIntrinsicHeight()).thenReturn(1500); - when(mFrame.getMeasuredWidth()).thenReturn(600); - when(mFrame.getMeasuredHeight()).thenReturn(500); - - ArgumentCaptor captor = ArgumentCaptor.forClass( - ViewGroup.LayoutParams.class); - activity.sizeImageToFrame(mImage, mFrame); - verify(mImage).setLayoutParams(captor.capture()); - ViewGroup.LayoutParams out = captor.getValue(); - assertThat(out.width).isEqualTo(300); - assertThat(out.height).isEqualTo(500); - }); - scenario.close(); - } - - @Test - public void setImageToFrame_imageSmallerThanFrame() { - ActivityScenario scenario = - ActivityScenario.launch(new Intent(Intent.ACTION_MAIN) - .setClass(RuntimeEnvironment.getApplication(), - SetupInterstitialActivity.class) - .putExtra(EXTRA_AUTOMATIC_ZEN_RULE_ID, MODE_ID)); - scenario.onActivity(activity -> { - // image: 300(w)x200(h); frame: 900(w)x1200(h) - // image expected to be scaled up to match the width of the frame -> 900(w)x600(h) - when(mDrawable.getIntrinsicWidth()).thenReturn(300); - when(mDrawable.getIntrinsicHeight()).thenReturn(200); - when(mFrame.getMeasuredWidth()).thenReturn(900); - when(mFrame.getMeasuredHeight()).thenReturn(1200); - - ArgumentCaptor captor = ArgumentCaptor.forClass( - ViewGroup.LayoutParams.class); - activity.sizeImageToFrame(mImage, mFrame); - verify(mImage).setLayoutParams(captor.capture()); - ViewGroup.LayoutParams out = captor.getValue(); - assertThat(out.width).isEqualTo(900); - assertThat(out.height).isEqualTo(600); - }); - scenario.close(); - } - - @Test - public void setImageToFrame_horizontalImageNarrowerThanFrame() { - ActivityScenario scenario = - ActivityScenario.launch(new Intent(Intent.ACTION_MAIN) - .setClass(RuntimeEnvironment.getApplication(), - SetupInterstitialActivity.class) - .putExtra(EXTRA_AUTOMATIC_ZEN_RULE_ID, MODE_ID)); - scenario.onActivity(activity -> { - // image: 600(w)x400(h); frame: 1000(w)x100(h) - // both image and frame are wider than tall, but frame is much narrower - // so should fit image to height of frame -> 150(w)x100(h) - when(mDrawable.getIntrinsicWidth()).thenReturn(600); - when(mDrawable.getIntrinsicHeight()).thenReturn(400); - when(mFrame.getMeasuredWidth()).thenReturn(1000); - when(mFrame.getMeasuredHeight()).thenReturn(100); - - ArgumentCaptor captor = ArgumentCaptor.forClass( - ViewGroup.LayoutParams.class); - activity.sizeImageToFrame(mImage, mFrame); - verify(mImage).setLayoutParams(captor.capture()); - ViewGroup.LayoutParams out = captor.getValue(); - assertThat(out.width).isEqualTo(150); - assertThat(out.height).isEqualTo(100); - }); - scenario.close(); - } - - @Test - public void setImageToFrame_accountsForPadding() { - ActivityScenario scenario = - ActivityScenario.launch(new Intent(Intent.ACTION_MAIN) - .setClass(RuntimeEnvironment.getApplication(), - SetupInterstitialActivity.class) - .putExtra(EXTRA_AUTOMATIC_ZEN_RULE_ID, MODE_ID)); - scenario.onActivity(activity -> { - // image: 200(w)x300(h); frame: 1000(w)x1000(h), 50 top/bottom padding, 100 l/r padding - // effective size of frame is therefore 800(w)x900(h) - // scale image to the height of the effective frame -> 600(w)x900(h) - when(mDrawable.getIntrinsicWidth()).thenReturn(200); - when(mDrawable.getIntrinsicHeight()).thenReturn(300); - when(mFrame.getMeasuredWidth()).thenReturn(1000); - when(mFrame.getMeasuredHeight()).thenReturn(1000); - when(mFrame.getPaddingTop()).thenReturn(50); - when(mFrame.getPaddingBottom()).thenReturn(50); - when(mFrame.getPaddingLeft()).thenReturn(100); - when(mFrame.getPaddingRight()).thenReturn(100); - - ArgumentCaptor captor = ArgumentCaptor.forClass( - ViewGroup.LayoutParams.class); - activity.sizeImageToFrame(mImage, mFrame); - verify(mImage).setLayoutParams(captor.capture()); - ViewGroup.LayoutParams out = captor.getValue(); - assertThat(out.width).isEqualTo(600); - assertThat(out.height).isEqualTo(900); - }); - scenario.close(); - } }