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

Commit 318d6ebd authored by Darrell Shi's avatar Darrell Shi
Browse files

Remove stopwatch widget

Fix: 288276738
Fix: 306471933
Test: presubmit
Flag: NA
Change-Id: Ibf4a21dbf408b569809d6b9f4ede2b01ce3307c9
parent a41c20a7
Loading
Loading
Loading
Loading
+0 −50
Original line number Diff line number Diff line
@@ -18,13 +18,11 @@ package com.android.systemui.communal.data.repository

import android.appwidget.AppWidgetHost
import android.appwidget.AppWidgetManager
import android.appwidget.AppWidgetProviderInfo
import android.content.BroadcastReceiver
import android.content.ComponentName
import android.content.Context
import android.content.Intent
import android.content.IntentFilter
import android.content.pm.PackageManager
import android.os.UserManager
import com.android.systemui.broadcast.BroadcastDispatcher
import com.android.systemui.common.coroutine.ChannelExt.trySendWithFailureLogging
@@ -32,13 +30,10 @@ import com.android.systemui.communal.data.db.CommunalItemRank
import com.android.systemui.communal.data.db.CommunalWidgetDao
import com.android.systemui.communal.data.db.CommunalWidgetItem
import com.android.systemui.communal.shared.CommunalWidgetHost
import com.android.systemui.communal.shared.model.CommunalAppWidgetInfo
import com.android.systemui.communal.shared.model.CommunalWidgetContentModel
import com.android.systemui.dagger.SysUISingleton
import com.android.systemui.dagger.qualifiers.Application
import com.android.systemui.dagger.qualifiers.Background
import com.android.systemui.flags.FeatureFlagsClassic
import com.android.systemui.flags.Flags
import com.android.systemui.log.LogBuffer
import com.android.systemui.log.core.Logger
import com.android.systemui.log.dagger.CommunalLog
@@ -58,9 +53,6 @@ import kotlinx.coroutines.launch

/** Encapsulates the state of widgets for communal mode. */
interface CommunalWidgetRepository {
    /** A flow of provider info for the stopwatch widget, or null if widget is unavailable. */
    val stopwatchAppWidgetInfo: Flow<CommunalAppWidgetInfo?>

    /** A flow of information about active communal widgets stored in database. */
    val communalWidgets: Flow<List<CommunalWidgetContentModel>>

@@ -84,15 +76,12 @@ constructor(
    communalRepository: CommunalRepository,
    private val communalWidgetHost: CommunalWidgetHost,
    private val communalWidgetDao: CommunalWidgetDao,
    private val packageManager: PackageManager,
    private val userManager: UserManager,
    private val userTracker: UserTracker,
    @CommunalLog logBuffer: LogBuffer,
    featureFlags: FeatureFlagsClassic,
) : CommunalWidgetRepository {
    companion object {
        const val TAG = "CommunalWidgetRepository"
        const val WIDGET_LABEL = "Stopwatch"
    }

    private val logger = Logger(logBuffer, TAG)
@@ -100,9 +89,6 @@ constructor(
    // Whether the [AppWidgetHost] is listening for updates.
    private var isHostListening = false

    // Widgets that should be rendered in communal mode.
    private val widgets: HashMap<Int, CommunalAppWidgetInfo> = hashMapOf()

    private val isUserUnlocked: Flow<Boolean> =
        callbackFlow {
                if (!communalRepository.isCommunalEnabled) {
@@ -149,25 +135,6 @@ constructor(
            }
        }

    override val stopwatchAppWidgetInfo: Flow<CommunalAppWidgetInfo?> =
        isHostActive.map { isHostActive ->
            if (!isHostActive || !featureFlags.isEnabled(Flags.WIDGET_ON_KEYGUARD)) {
                return@map null
            }

            val providerInfo =
                appWidgetManager.installedProviders.find {
                    it.loadLabel(packageManager).equals(WIDGET_LABEL)
                }

            if (providerInfo == null) {
                logger.w("Cannot find app widget: $WIDGET_LABEL")
                return@map null
            }

            return@map addStopWatchWidget(providerInfo)
        }

    override val communalWidgets: Flow<List<CommunalWidgetContentModel>> =
        isHostActive.flatMapLatest { isHostActive ->
            if (!isHostActive) {
@@ -226,21 +193,4 @@ constructor(
        appWidgetHost.stopListening()
        isHostListening = false
    }

    // TODO(b/306471933): remove this prototype that shows a stopwatch in the communal blueprint
    private fun addStopWatchWidget(providerInfo: AppWidgetProviderInfo): CommunalAppWidgetInfo {
        val existing = widgets.values.firstOrNull { it.providerInfo == providerInfo }
        if (existing != null) {
            return existing
        }

        val appWidgetId = appWidgetHost.allocateAppWidgetId()
        val widget =
            CommunalAppWidgetInfo(
                providerInfo,
                appWidgetId,
            )
        widgets[appWidgetId] = widget
        return widget
    }
}
+0 −4
Original line number Diff line number Diff line
@@ -23,7 +23,6 @@ import com.android.systemui.communal.data.repository.CommunalMediaRepository
import com.android.systemui.communal.data.repository.CommunalRepository
import com.android.systemui.communal.data.repository.CommunalWidgetRepository
import com.android.systemui.communal.domain.model.CommunalContentModel
import com.android.systemui.communal.shared.model.CommunalAppWidgetInfo
import com.android.systemui.communal.shared.model.CommunalContentSize
import com.android.systemui.communal.shared.model.CommunalSceneKey
import com.android.systemui.dagger.SysUISingleton
@@ -55,9 +54,6 @@ constructor(
    val isCommunalEnabled: Boolean
        get() = communalRepository.isCommunalEnabled

    /** A flow of info about the widget to be displayed, or null if widget is unavailable. */
    val appWidgetInfo: Flow<CommunalAppWidgetInfo?> = widgetRepository.stopwatchAppWidgetInfo

    /**
     * Target scene as requested by the underlying [SceneTransitionLayout] or through
     * [onSceneChanged].
+0 −70
Original line number Diff line number Diff line
/*
 * Copyright (C) 2023 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.communal.ui.binder

import androidx.lifecycle.Lifecycle
import androidx.lifecycle.repeatOnLifecycle
import com.android.systemui.res.R
import com.android.systemui.communal.ui.adapter.CommunalWidgetViewAdapter
import com.android.systemui.communal.ui.view.CommunalWidgetWrapper
import com.android.systemui.communal.ui.viewmodel.CommunalWidgetViewModel
import com.android.systemui.keyguard.domain.interactor.KeyguardBlueprintInteractor
import com.android.systemui.keyguard.ui.view.KeyguardRootView
import com.android.systemui.lifecycle.repeatWhenAttached
import kotlinx.coroutines.launch

/** Binds [CommunalWidgetViewModel] to the keyguard root view. */
object CommunalWidgetViewBinder {

    @JvmStatic
    fun bind(
        rootView: KeyguardRootView,
        viewModel: CommunalWidgetViewModel,
        adapter: CommunalWidgetViewAdapter,
        keyguardBlueprintInteractor: KeyguardBlueprintInteractor,
    ) {
        rootView.repeatWhenAttached {
            repeatOnLifecycle(Lifecycle.State.STARTED) {
                launch {
                    adapter.adapt(viewModel.appWidgetInfo).collect {
                        val oldView =
                            rootView.findViewById<CommunalWidgetWrapper>(
                                R.id.communal_widget_wrapper
                            )
                        var dirty = false

                        if (oldView != null) {
                            rootView.removeView(oldView)
                            dirty = true
                        }

                        if (it != null) {
                            rootView.addView(it)
                            dirty = true
                        }

                        if (dirty) {
                            keyguardBlueprintInteractor.refreshBlueprint()
                        }
                    }
                }

                launch { viewModel.alpha.collect { rootView.alpha = it } }
            }
        }
    }
}
+0 −3
Original line number Diff line number Diff line
@@ -17,7 +17,6 @@
package com.android.systemui.communal.ui.view.layout.blueprints

import com.android.systemui.communal.ui.view.layout.sections.DefaultCommunalHubSection
import com.android.systemui.communal.ui.view.layout.sections.DefaultCommunalWidgetSection
import com.android.systemui.dagger.SysUISingleton
import com.android.systemui.keyguard.shared.model.KeyguardBlueprint
import com.android.systemui.keyguard.shared.model.KeyguardSection
@@ -30,13 +29,11 @@ class DefaultCommunalBlueprint
@Inject
constructor(
    defaultCommunalHubSection: DefaultCommunalHubSection,
    defaultCommunalWidgetSection: DefaultCommunalWidgetSection,
) : KeyguardBlueprint {
    override val id: String = COMMUNAL
    override val sections: List<KeyguardSection> =
        listOf(
            defaultCommunalHubSection,
            defaultCommunalWidgetSection,
        )

    companion object {
+0 −73
Original line number Diff line number Diff line
/*
 * Copyright (C) 2023 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.communal.ui.view.layout.sections

import android.view.ViewGroup.LayoutParams.WRAP_CONTENT
import androidx.constraintlayout.widget.ConstraintLayout
import androidx.constraintlayout.widget.ConstraintSet
import androidx.constraintlayout.widget.ConstraintSet.BOTTOM
import androidx.constraintlayout.widget.ConstraintSet.END
import androidx.constraintlayout.widget.ConstraintSet.PARENT_ID
import com.android.systemui.res.R
import com.android.systemui.communal.ui.adapter.CommunalWidgetViewAdapter
import com.android.systemui.communal.ui.binder.CommunalWidgetViewBinder
import com.android.systemui.communal.ui.viewmodel.CommunalWidgetViewModel
import com.android.systemui.flags.FeatureFlags
import com.android.systemui.flags.Flags
import com.android.systemui.keyguard.domain.interactor.KeyguardBlueprintInteractor
import com.android.systemui.keyguard.shared.model.KeyguardSection
import com.android.systemui.keyguard.ui.view.KeyguardRootView
import dagger.Lazy
import javax.inject.Inject

class DefaultCommunalWidgetSection
@Inject
constructor(
    private val featureFlags: FeatureFlags,
    private val keyguardRootView: KeyguardRootView,
    private val communalWidgetViewModel: CommunalWidgetViewModel,
    private val communalWidgetViewAdapter: CommunalWidgetViewAdapter,
    private val keyguardBlueprintInteractor: Lazy<KeyguardBlueprintInteractor>,
) : KeyguardSection() {
    private val widgetAreaViewId = R.id.communal_widget_wrapper

    override fun addViews(constraintLayout: ConstraintLayout) {}

    override fun bindData(constraintLayout: ConstraintLayout) {
        if (!featureFlags.isEnabled(Flags.WIDGET_ON_KEYGUARD)) {
            return
        }

        CommunalWidgetViewBinder.bind(
            keyguardRootView,
            communalWidgetViewModel,
            communalWidgetViewAdapter,
            keyguardBlueprintInteractor.get(),
        )
    }

    override fun applyConstraints(constraintSet: ConstraintSet) {
        constraintSet.apply {
            constrainWidth(widgetAreaViewId, WRAP_CONTENT)
            constrainHeight(widgetAreaViewId, WRAP_CONTENT)
            connect(widgetAreaViewId, BOTTOM, PARENT_ID, BOTTOM)
            connect(widgetAreaViewId, END, PARENT_ID, END)
        }
    }

    override fun removeViews(constraintLayout: ConstraintLayout) {}
}
Loading