Bind color option selection border color (2/2)

Flag: com.android.systemui.shared.new_customization_picker_ui
Test: manually verified
Bug: 363018910
Change-Id: I96c78a320f896d2cd40ca8878ebebbc4f0113c98
diff --git a/src/com/android/customization/picker/color/ui/binder/ColorOptionIconBinder2.kt b/src/com/android/customization/picker/color/ui/binder/ColorOptionIconBinder2.kt
index 2c197ad..4758619 100644
--- a/src/com/android/customization/picker/color/ui/binder/ColorOptionIconBinder2.kt
+++ b/src/com/android/customization/picker/color/ui/binder/ColorOptionIconBinder2.kt
@@ -17,14 +17,36 @@
 
 package com.android.customization.picker.color.ui.binder
 
+import androidx.lifecycle.LifecycleOwner
 import com.android.customization.picker.color.ui.view.ColorOptionIconView2
 import com.android.customization.picker.color.ui.viewmodel.ColorOptionIconViewModel
+import com.android.wallpaper.picker.customization.ui.binder.ColorUpdateBinder
+import com.android.wallpaper.picker.customization.ui.viewmodel.ColorUpdateViewModel
 
 object ColorOptionIconBinder2 {
-    fun bind(view: ColorOptionIconView2, viewModel: ColorOptionIconViewModel, darkTheme: Boolean) {
+
+    interface Binding {
+        /** Destroys the color update binding, in spite of lifecycle state. */
+        fun destroy()
+    }
+
+    fun bind(
+        view: ColorOptionIconView2,
+        viewModel: ColorOptionIconViewModel,
+        darkTheme: Boolean,
+        colorUpdateViewModel: ColorUpdateViewModel,
+        shouldAnimateColor: () -> Boolean,
+        lifecycleOwner: LifecycleOwner,
+    ): Binding {
+        val binding =
+            ColorUpdateBinder.bind(
+                setColor = { color -> view.bindStrokeColor(color) },
+                color = colorUpdateViewModel.colorPrimary,
+                shouldAnimate = shouldAnimateColor,
+                lifecycleOwner = lifecycleOwner,
+            )
         if (darkTheme) {
             view.bindColor(
-                view.resources.getColor(android.R.color.system_primary_dark, view.context.theme),
                 viewModel.darkThemeColor0,
                 viewModel.darkThemeColor1,
                 viewModel.darkThemeColor2,
@@ -32,12 +54,16 @@
             )
         } else {
             view.bindColor(
-                view.resources.getColor(android.R.color.system_primary_light, view.context.theme),
                 viewModel.lightThemeColor0,
                 viewModel.lightThemeColor1,
                 viewModel.lightThemeColor2,
                 viewModel.lightThemeColor3,
             )
         }
+        return object : Binding {
+            override fun destroy() {
+                binding.destroy()
+            }
+        }
     }
 }
diff --git a/src/com/android/customization/picker/color/ui/view/ColorOptionIconView2.kt b/src/com/android/customization/picker/color/ui/view/ColorOptionIconView2.kt
index 3fc6324..ea20af3 100644
--- a/src/com/android/customization/picker/color/ui/view/ColorOptionIconView2.kt
+++ b/src/com/android/customization/picker/color/ui/view/ColorOptionIconView2.kt
@@ -55,13 +55,11 @@
      * @param color3 the color in the bottom right quadrant
      */
     fun bindColor(
-        @ColorInt strokeColor: Int,
         @ColorInt color0: Int,
         @ColorInt color1: Int,
         @ColorInt color2: Int,
         @ColorInt color3: Int,
     ) {
-        this.strokeColor = strokeColor
         this.color0 = color0
         this.color1 = color1
         this.color2 = color2
@@ -69,6 +67,11 @@
         invalidate()
     }
 
+    fun bindStrokeColor(@ColorInt strokeColor: Int) {
+        this.strokeColor = strokeColor
+        invalidate()
+    }
+
     override fun onSizeChanged(w: Int, h: Int, oldw: Int, oldh: Int) {
         this.w = w
         this.h = h
diff --git a/src/com/android/wallpaper/customization/ui/binder/ClockFloatingSheetBinder.kt b/src/com/android/wallpaper/customization/ui/binder/ClockFloatingSheetBinder.kt
index a7f1c67..18a4c53 100644
--- a/src/com/android/wallpaper/customization/ui/binder/ClockFloatingSheetBinder.kt
+++ b/src/com/android/wallpaper/customization/ui/binder/ClockFloatingSheetBinder.kt
@@ -488,10 +488,16 @@
                         com.android.wallpaper.R.id.background
                     )
                 val night = uiMode and UI_MODE_NIGHT_MASK == UI_MODE_NIGHT_YES
-                ColorOptionIconBinder2.bind(colorOptionIconView, colorIcon, night)
-                // Return null since it does not need the lifecycleOwner to launch any job for later
-                // disposal when rebind.
-                return@OptionItemAdapter2 null
+                val binding =
+                    ColorOptionIconBinder2.bind(
+                        view = colorOptionIconView,
+                        viewModel = colorIcon,
+                        darkTheme = night,
+                        colorUpdateViewModel = colorUpdateViewModel,
+                        shouldAnimateColor = shouldAnimateColor,
+                        lifecycleOwner = lifecycleOwner,
+                    )
+                return@OptionItemAdapter2 DisposableHandle { binding.destroy() }
             },
             colorUpdateViewModel = WeakReference(colorUpdateViewModel),
             shouldAnimateColor = shouldAnimateColor,
diff --git a/src/com/android/wallpaper/customization/ui/binder/ColorsFloatingSheetBinder.kt b/src/com/android/wallpaper/customization/ui/binder/ColorsFloatingSheetBinder.kt
index 4f5adab..a097828 100644
--- a/src/com/android/wallpaper/customization/ui/binder/ColorsFloatingSheetBinder.kt
+++ b/src/com/android/wallpaper/customization/ui/binder/ColorsFloatingSheetBinder.kt
@@ -41,6 +41,7 @@
 import com.android.wallpaper.picker.customization.ui.viewmodel.ColorUpdateViewModel
 import com.android.wallpaper.picker.option.ui.adapter.OptionItemAdapter2
 import java.lang.ref.WeakReference
+import kotlinx.coroutines.DisposableHandle
 import kotlinx.coroutines.launch
 
 object ColorsFloatingSheetBinder {
@@ -158,10 +159,16 @@
                         com.android.wallpaper.R.id.background
                     )
                 val night = uiMode and UI_MODE_NIGHT_MASK == UI_MODE_NIGHT_YES
-                ColorOptionIconBinder2.bind(colorOptionIconView, colorIcon, night)
-                // Return null since it does not need the lifecycleOwner to launch any job for later
-                // disposal when rebind.
-                return@OptionItemAdapter2 null
+                val binding =
+                    ColorOptionIconBinder2.bind(
+                        view = colorOptionIconView,
+                        viewModel = colorIcon,
+                        darkTheme = night,
+                        colorUpdateViewModel = colorUpdateViewModel,
+                        shouldAnimateColor = shouldAnimateColor,
+                        lifecycleOwner = lifecycleOwner,
+                    )
+                return@OptionItemAdapter2 DisposableHandle { binding.destroy() }
             },
             colorUpdateViewModel = WeakReference(colorUpdateViewModel),
             shouldAnimateColor = shouldAnimateColor,
diff --git a/src/com/android/wallpaper/customization/ui/binder/ThemePickerCustomizationOptionBinder.kt b/src/com/android/wallpaper/customization/ui/binder/ThemePickerCustomizationOptionBinder.kt
index efa922b..4eb0940 100644
--- a/src/com/android/wallpaper/customization/ui/binder/ThemePickerCustomizationOptionBinder.kt
+++ b/src/com/android/wallpaper/customization/ui/binder/ThemePickerCustomizationOptionBinder.kt
@@ -93,6 +93,11 @@
             navigateToLockScreenNotificationsSettingsActivity,
         )
 
+        val optionsViewModel =
+            viewModel.customizationOptionsViewModel as ThemePickerCustomizationOptionsViewModel
+
+        val isOnMainScreen = { optionsViewModel.selectedOption.value == null }
+
         val optionClock: View =
             lockScreenCustomizationOptionEntries
                 .first { it.first == ThemePickerLockCustomizationOption.CLOCK }
@@ -159,8 +164,6 @@
         val optionThemedIconsSwitch =
             optionThemedIcons?.findViewById<Switch>(R.id.option_entry_themed_icons_switch)
 
-        val optionsViewModel =
-            viewModel.customizationOptionsViewModel as ThemePickerCustomizationOptionsViewModel
         lifecycleOwner.lifecycleScope.launch {
             lifecycleOwner.repeatOnLifecycle(Lifecycle.State.STARTED) {
                 launch {
@@ -250,14 +253,21 @@
                 }
 
                 launch {
+                    var binding: ColorOptionIconBinder2.Binding? = null
                     optionsViewModel.colorPickerViewModel2.selectedColorOption.collect { colorOption
                         ->
                         (colorOption as? ColorOptionImpl)?.let {
-                            ColorOptionIconBinder2.bind(
-                                view = optionColorsIcon,
-                                viewModel = ColorOptionIconViewModel.fromColorOption(colorOption),
-                                darkTheme = view.resources.configuration.isNightModeActive,
-                            )
+                            binding?.destroy()
+                            binding =
+                                ColorOptionIconBinder2.bind(
+                                    view = optionColorsIcon,
+                                    viewModel =
+                                        ColorOptionIconViewModel.fromColorOption(colorOption),
+                                    darkTheme = view.resources.configuration.isNightModeActive,
+                                    colorUpdateViewModel = colorUpdateViewModel,
+                                    shouldAnimateColor = isOnMainScreen,
+                                    lifecycleOwner = lifecycleOwner,
+                                )
                         }
                     }
                 }