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

Commit 706706fd authored by Austin Wang's avatar Austin Wang
Browse files

Make ClockRegistry and its provider singleton

`ClockRegistry`, 'ClockRegistryProvider` and `PluginManager` should all
be singleton. Considering ag/23407197, keep a set of `LifecycleOwner`
whenever the registry associated with a new owner, and only unregister
listeners when the last owner leaves.

Bug: 284535120
Test: set small/dynamic clock with WPP resume/destroy
Change-Id: I8c8d2899c1d223fb3171506f6f316393086e02ca
parent a0636139
Loading
Loading
Loading
Loading
+9 −24
Original line number Diff line number Diff line
@@ -98,11 +98,6 @@ open class ThemePickerInjector : WallpaperPicker2Injector(), CustomizationInject
    private var keyguardQuickAffordanceSnapshotRestorer: KeyguardQuickAffordanceSnapshotRestorer? =
        null
    private var notificationsSnapshotRestorer: NotificationsSnapshotRestorer? = null
    /**
     * Mapping from LifeCycleOwner's hashcode to ClockRegistry as we need to keep different
     * ClockRegistries per LifeCycle to ensure proper cleanup
     */
    private var clockRegistries: MutableMap<Int, ClockRegistry> = HashMap()
    private var clockPickerInteractor: ClockPickerInteractor? = null
    private var clockSectionViewModel: ClockSectionViewModel? = null
    private var clockCarouselViewModelFactory: ClockCarouselViewModel.Factory? = null
@@ -120,6 +115,7 @@ open class ThemePickerInjector : WallpaperPicker2Injector(), CustomizationInject
    private var gridInteractor: GridInteractor? = null
    private var gridSnapshotRestorer: GridSnapshotRestorer? = null
    private var gridScreenViewModelFactory: GridScreenViewModel.Factory? = null
    private var clockRegistryProvider: ClockRegistryProvider? = null

    override fun getCustomizationSections(activity: ComponentActivity): CustomizationSections {
        return customizationSections
@@ -318,26 +314,15 @@ open class ThemePickerInjector : WallpaperPicker2Injector(), CustomizationInject
    }

    override fun getClockRegistry(context: Context, lifecycleOwner: LifecycleOwner): ClockRegistry {
        return clockRegistries[lifecycleOwner.hashCode()]
        return (clockRegistryProvider
                ?: ClockRegistryProvider(
                        context = context,
                        coroutineScope = getApplicationCoroutineScope(),
                        mainDispatcher = Dispatchers.Main,
                        backgroundDispatcher = Dispatchers.IO,
                    )
                .get()
                .also {
                    clockRegistries[lifecycleOwner.hashCode()] = it
                    lifecycleOwner.lifecycle.addObserver(
                        object : DefaultLifecycleObserver {
                            override fun onDestroy(owner: LifecycleOwner) {
                                super.onDestroy(owner)
                                clockRegistries[lifecycleOwner.hashCode()]?.unregisterListeners()
                                clockRegistries.remove(lifecycleOwner.hashCode())
                            }
                        }
                    )
                }
                    .also { clockRegistryProvider = it })
            .getForOwner(lifecycleOwner)
    }

    override fun getClockPickerInteractor(
+26 −1
Original line number Diff line number Diff line
@@ -19,6 +19,8 @@ import android.app.NotificationManager
import android.content.ComponentName
import android.content.Context
import android.view.LayoutInflater
import androidx.lifecycle.DefaultLifecycleObserver
import androidx.lifecycle.LifecycleOwner
import com.android.systemui.plugins.Plugin
import com.android.systemui.plugins.PluginManager
import com.android.systemui.shared.clocks.ClockRegistry
@@ -43,6 +45,7 @@ class ClockRegistryProvider(
    private val mainDispatcher: CoroutineDispatcher,
    private val backgroundDispatcher: CoroutineDispatcher,
) {
    private val lifecycleOwners = mutableSetOf<Int>()
    private val pluginManager: PluginManager by lazy { createPluginManager(context) }
    private val clockRegistry: ClockRegistry by lazy {
        ClockRegistry(
@@ -60,10 +63,32 @@ class ClockRegistryProvider(
            .apply { registerListeners() }
    }

    fun get(): ClockRegistry {
    fun getForOwner(lifecycleOwner: LifecycleOwner): ClockRegistry {
        registerLifecycleOwner(lifecycleOwner)
        return clockRegistry
    }

    private fun registerLifecycleOwner(lifecycleOwner: LifecycleOwner) {
        lifecycleOwners.add(lifecycleOwner.hashCode())

        lifecycleOwner.lifecycle.addObserver(
            object : DefaultLifecycleObserver {
                override fun onDestroy(owner: LifecycleOwner) {
                    super.onDestroy(owner)
                    unregisterLifecycleOwner(owner)
                }
            }
        )
    }

    private fun unregisterLifecycleOwner(lifecycleOwner: LifecycleOwner) {
        lifecycleOwners.remove(lifecycleOwner.hashCode())

        if (lifecycleOwners.isEmpty()) {
            clockRegistry.unregisterListeners()
        }
    }

    private fun createPluginManager(context: Context): PluginManager {
        val privilegedPlugins = listOf<String>()
        val isDebugDevice = true