From aa1576b0d3cef00268b793d1266e560892643b24 Mon Sep 17 00:00:00 2001 From: MrSluffy Date: Wed, 12 Feb 2025 19:08:37 +0800 Subject: [PATCH] feat : re-impliment AccentColorExtractor - closes : #5243 --- .../app/lawnchair/AccentColorExtractor.java | 20 +++++++++++++++---- .../graphics/LauncherPreviewRenderer.java | 9 ++++++--- .../graphics/PreviewSurfaceRenderer.java | 9 +++++++-- .../widget/BaseLauncherAppWidgetHostView.java | 16 ++++++++++++++- .../widget/LauncherAppWidgetHostView.java | 5 +++++ .../launcher3/widget/LocalColorExtractor.java | 20 +++++++++++++++++++ 6 files changed, 69 insertions(+), 10 deletions(-) diff --git a/lawnchair/src/app/lawnchair/AccentColorExtractor.java b/lawnchair/src/app/lawnchair/AccentColorExtractor.java index 98c51992b5a..8853cf8f8b8 100644 --- a/lawnchair/src/app/lawnchair/AccentColorExtractor.java +++ b/lawnchair/src/app/lawnchair/AccentColorExtractor.java @@ -18,11 +18,8 @@ import android.app.WallpaperColors; import android.content.Context; -import android.graphics.Rect; -import android.graphics.RectF; import android.os.Build; import android.util.SparseIntArray; -import android.view.View; import android.widget.RemoteViews; import androidx.annotation.Keep; @@ -42,12 +39,19 @@ public class AccentColorExtractor extends LocalColorExtractor implements ThemeProvider.ColorSchemeChangeListener { private final ThemeProvider mThemeProvider; + private Listener mListener; @Keep public AccentColorExtractor(Context context) { mThemeProvider = ThemeProvider.INSTANCE.get(context); } + @Override + public void setListener(@Nullable Listener listener) { + mListener = listener; + notifyListener(); + } + @Nullable protected SparseIntArray generateColorsOverride(ColorScheme colorScheme) { SparseIntArray colorRes = new SparseIntArray(5 * 13); @@ -71,7 +75,15 @@ public void applyColorsOverride(Context base, WallpaperColors colors) { } @Override - public void onColorSchemeChanged() {} + public void onColorSchemeChanged() { + notifyListener(); + } + + protected void notifyListener() { + if (mListener != null) { + mListener.onColorsChanged(generateColorsOverride(mThemeProvider.getColorScheme())); + } + } // Shade number -> color resource ID maps private static final SparseIntArray ACCENT1_RES = new SparseIntArray(13); diff --git a/src/com/android/launcher3/graphics/LauncherPreviewRenderer.java b/src/com/android/launcher3/graphics/LauncherPreviewRenderer.java index ccfd484842c..f8a7fca136d 100644 --- a/src/com/android/launcher3/graphics/LauncherPreviewRenderer.java +++ b/src/com/android/launcher3/graphics/LauncherPreviewRenderer.java @@ -451,9 +451,7 @@ private void inflateAndAddWidgets( mContext, info.appWidgetId, providerInfo); if (mWallpaperColorResources != null) { - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) { - view.setColorResources(mWallpaperColorResources); - } + view.setColorResources(mWallpaperColorResources); } view.setTag(info); @@ -615,6 +613,11 @@ private LauncherPreviewAppWidgetHostView(Context context) { protected boolean shouldAllowDirectClick() { return false; } + + @Override + public void onColorsChanged(SparseIntArray colors) { + post(() -> setColorResources(colors)); + } } /** Root layout for launcher preview that intercepts all touch events. */ diff --git a/src/com/android/launcher3/graphics/PreviewSurfaceRenderer.java b/src/com/android/launcher3/graphics/PreviewSurfaceRenderer.java index 2b70f33f697..409189ed6d2 100644 --- a/src/com/android/launcher3/graphics/PreviewSurfaceRenderer.java +++ b/src/com/android/launcher3/graphics/PreviewSurfaceRenderer.java @@ -37,6 +37,7 @@ import android.view.SurfaceControlViewHost; import android.view.SurfaceControlViewHost.SurfacePackage; import android.view.View; +import android.view.WindowManager; import android.view.animation.AccelerateDecelerateInterpolator; import androidx.annotation.NonNull; @@ -48,6 +49,7 @@ import com.android.launcher3.InvariantDeviceProfile; import com.android.launcher3.LauncherAppState; import com.android.launcher3.LauncherSettings; +import com.android.launcher3.Utilities; import com.android.launcher3.Workspace; import com.android.launcher3.graphics.LauncherPreviewRenderer.PreviewContext; import com.android.launcher3.model.BaseLauncherBinder; @@ -66,7 +68,6 @@ import java.util.Map; import java.util.concurrent.TimeUnit; -import app.lawnchair.AccentColorExtractor; /** Render preview using surface view. */ @SuppressWarnings("NewApi") @@ -218,7 +219,11 @@ private Context getPreviewContext() { return new ContextThemeWrapper(context, Themes.getActivityThemeRes(context)); } - AccentColorExtractor.newInstance(context) + if (Utilities.ATLEAST_R) { + context = context.createWindowContext( + WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY, null); + } + LocalColorExtractor.newInstance(mContext) .applyColorsOverride(context, mWallpaperColors); return new ContextThemeWrapper(context, Themes.getActivityThemeRes(context, mWallpaperColors.getColorHints())); diff --git a/src/com/android/launcher3/widget/BaseLauncherAppWidgetHostView.java b/src/com/android/launcher3/widget/BaseLauncherAppWidgetHostView.java index 104209ef53c..466d9f0a7b5 100644 --- a/src/com/android/launcher3/widget/BaseLauncherAppWidgetHostView.java +++ b/src/com/android/launcher3/widget/BaseLauncherAppWidgetHostView.java @@ -32,7 +32,7 @@ /** * Launcher AppWidgetHostView with support for rounded corners and a fallback View. */ -public abstract class BaseLauncherAppWidgetHostView extends NavigableAppWidgetHostView { +public abstract class BaseLauncherAppWidgetHostView extends NavigableAppWidgetHostView implements LocalColorExtractor.Listener { private static final ViewOutlineProvider VIEW_OUTLINE_PROVIDER = new ViewOutlineProvider() { @Override @@ -61,6 +61,7 @@ public void getOutline(View view, Outline outline) { }; private boolean mIsCornerRadiusEnforced; + private final LocalColorExtractor mColorExtractor; public BaseLauncherAppWidgetHostView(Context context) { super(context); @@ -70,6 +71,7 @@ public BaseLauncherAppWidgetHostView(Context context) { mInflater = LayoutInflater.from(context); mEnforcedCornerRadius = RoundedCornerEnforcement.computeEnforcedRadius(getContext()); + mColorExtractor = LocalColorExtractor.newInstance(getContext()); } @Override @@ -85,6 +87,18 @@ public void switchToErrorView() { updateAppWidget(new RemoteViews(getAppWidgetInfo().provider.getPackageName(), 0)); } + @Override + protected void onAttachedToWindow() { + super.onAttachedToWindow(); + mColorExtractor.setListener(this); + } + + @Override + protected void onDetachedFromWindow() { + super.onDetachedFromWindow(); + mColorExtractor.setListener(null); + } + @Override protected void onLayout(boolean changed, int left, int top, int right, int bottom) { try { diff --git a/src/com/android/launcher3/widget/LauncherAppWidgetHostView.java b/src/com/android/launcher3/widget/LauncherAppWidgetHostView.java index 1f4419bb7e0..48c07c9c9a7 100644 --- a/src/com/android/launcher3/widget/LauncherAppWidgetHostView.java +++ b/src/com/android/launcher3/widget/LauncherAppWidgetHostView.java @@ -379,6 +379,11 @@ protected boolean shouldAllowDirectClick() { return false; } + @Override + public void onColorsChanged(SparseIntArray colors) { + post(() -> setColorResources(colors)); + } + /** * Listener interface to be called when {@code CellLayout} is about to layout this child view */ diff --git a/src/com/android/launcher3/widget/LocalColorExtractor.java b/src/com/android/launcher3/widget/LocalColorExtractor.java index 7b500c72c43..2f7a3ca4eae 100644 --- a/src/com/android/launcher3/widget/LocalColorExtractor.java +++ b/src/com/android/launcher3/widget/LocalColorExtractor.java @@ -17,8 +17,11 @@ package com.android.launcher3.widget; import android.app.WallpaperColors; +import android.appwidget.AppWidgetHostView; import android.content.Context; +import android.graphics.Rect; import android.util.SparseIntArray; +import android.view.View; import androidx.annotation.Nullable; @@ -28,6 +31,18 @@ /** Extracts the colors we need from the wallpaper at given locations. */ public class LocalColorExtractor implements ResourceBasedOverride { + /** Listener for color changes on a screen location. */ + public interface Listener { + /** + * Method called when the colors on a registered location has changed. + * + * {@code extractedColors} maps the color resources {@code android.R.colors.system_*} to + * their value, in a format that can be passed directly to + * {@link AppWidgetHostView#setColorResources(SparseIntArray)}. + */ + void onColorsChanged(SparseIntArray extractedColors); + } + /** * Creates a new instance of LocalColorExtractor */ @@ -36,6 +51,11 @@ public static LocalColorExtractor newInstance(Context context) { R.string.local_colors_extraction_class); } + /** Sets the object that will receive the color changes. */ + public void setListener(@Nullable Listener listener) { + // no-op + } + /** * Updates the base context to contain the colors override */