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

Commit 2c60dbac authored by Caitlin Shkuratov's avatar Caitlin Shkuratov Committed by Automerger Merge Worker
Browse files

Merge "[SB Refactor] Implement the wifi icon flow in the new pipeline." into...

Merge "[SB Refactor] Implement the wifi icon flow in the new pipeline." into tm-qpr-dev am: a9b3416a

Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/19700880



Change-Id: I77913eb0cc04f28271c96618c96b7b4397195f06
Signed-off-by: default avatarAutomerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>
parents 1dc44962 a9b3416a
Loading
Loading
Loading
Loading
+2 −2
Original line number Original line Diff line number Diff line
@@ -31,7 +31,7 @@ public class WifiIcons {
            com.android.internal.R.drawable.ic_wifi_signal_4
            com.android.internal.R.drawable.ic_wifi_signal_4
    };
    };


    private static final int[] WIFI_NO_INTERNET_ICONS = {
    public static final int[] WIFI_NO_INTERNET_ICONS = {
            R.drawable.ic_no_internet_wifi_signal_0,
            R.drawable.ic_no_internet_wifi_signal_0,
            R.drawable.ic_no_internet_wifi_signal_1,
            R.drawable.ic_no_internet_wifi_signal_1,
            R.drawable.ic_no_internet_wifi_signal_2,
            R.drawable.ic_no_internet_wifi_signal_2,
@@ -48,7 +48,7 @@ public class WifiIcons {


    public static final int QS_WIFI_DISABLED = com.android.internal.R.drawable.ic_wifi_signal_0;
    public static final int QS_WIFI_DISABLED = com.android.internal.R.drawable.ic_wifi_signal_0;
    public static final int QS_WIFI_NO_NETWORK = com.android.internal.R.drawable.ic_wifi_signal_0;
    public static final int QS_WIFI_NO_NETWORK = com.android.internal.R.drawable.ic_wifi_signal_0;
    static final int WIFI_NO_NETWORK = QS_WIFI_NO_NETWORK;
    public static final int WIFI_NO_NETWORK = QS_WIFI_NO_NETWORK;


    static final int WIFI_LEVEL_COUNT = WIFI_SIGNAL_STRENGTH[0].length;
    static final int WIFI_LEVEL_COUNT = WIFI_SIGNAL_STRENGTH[0].length;


+38 −2
Original line number Original line Diff line number Diff line
@@ -16,13 +16,23 @@


package com.android.systemui.statusbar.pipeline.wifi.data.model
package com.android.systemui.statusbar.pipeline.wifi.data.model


import androidx.annotation.VisibleForTesting

/** Provides information about the current wifi network. */
/** Provides information about the current wifi network. */
sealed class WifiNetworkModel {
sealed class WifiNetworkModel {
    /** A model representing that we have no active wifi network. */
    /** A model representing that we have no active wifi network. */
    object Inactive : WifiNetworkModel()
    object Inactive : WifiNetworkModel()


    /**
     * A model representing that our wifi network is actually a carrier merged network, meaning it's
     * treated as more of a mobile network.
     *
     * See [android.net.wifi.WifiInfo.isCarrierMerged] for more information.
     */
    object CarrierMerged : WifiNetworkModel()

    /** Provides information about an active wifi network. */
    /** Provides information about an active wifi network. */
    class Active(
    data class Active(
        /**
        /**
         * The [android.net.Network.netId] we received from
         * The [android.net.Network.netId] we received from
         * [android.net.ConnectivityManager.NetworkCallback] in association with this wifi network.
         * [android.net.ConnectivityManager.NetworkCallback] in association with this wifi network.
@@ -31,6 +41,19 @@ sealed class WifiNetworkModel {
         */
         */
        val networkId: Int,
        val networkId: Int,


        /** See [android.net.NetworkCapabilities.NET_CAPABILITY_VALIDATED]. */
        val isValidated: Boolean = false,

        /**
         * The wifi signal level, guaranteed to be 0 <= level <= 4.
         *
         * Null if we couldn't fetch the level for some reason.
         *
         * TODO(b/238425913): The level will only be null if we have a null WifiManager. Is there a
         *   way we can guarantee a non-null WifiManager?
         */
        val level: Int? = null,

        /** See [android.net.wifi.WifiInfo.ssid]. */
        /** See [android.net.wifi.WifiInfo.ssid]. */
        val ssid: String? = null,
        val ssid: String? = null,


@@ -42,5 +65,18 @@ sealed class WifiNetworkModel {


        /** See [android.net.wifi.WifiInfo.passpointProviderFriendlyName]. */
        /** See [android.net.wifi.WifiInfo.passpointProviderFriendlyName]. */
        val passpointProviderFriendlyName: String? = null,
        val passpointProviderFriendlyName: String? = null,
    ) : WifiNetworkModel()
    ) : WifiNetworkModel() {
        init {
            require(level == null || level in MIN_VALID_LEVEL..MAX_VALID_LEVEL) {
                "0 <= wifi level <= 4 required; level was $level"
            }
        }

        companion object {
            @VisibleForTesting
            internal const val MIN_VALID_LEVEL = 0
            @VisibleForTesting
            internal const val MAX_VALID_LEVEL = 4
        }
    }
}
}
+36 −13
Original line number Original line Diff line number Diff line
@@ -21,6 +21,7 @@ import android.net.ConnectivityManager
import android.net.Network
import android.net.Network
import android.net.NetworkCapabilities
import android.net.NetworkCapabilities
import android.net.NetworkCapabilities.NET_CAPABILITY_NOT_VPN
import android.net.NetworkCapabilities.NET_CAPABILITY_NOT_VPN
import android.net.NetworkCapabilities.NET_CAPABILITY_VALIDATED
import android.net.NetworkCapabilities.TRANSPORT_CELLULAR
import android.net.NetworkCapabilities.TRANSPORT_CELLULAR
import android.net.NetworkCapabilities.TRANSPORT_WIFI
import android.net.NetworkCapabilities.TRANSPORT_WIFI
import android.net.NetworkRequest
import android.net.NetworkRequest
@@ -31,6 +32,7 @@ import android.util.Log
import com.android.settingslib.Utils
import com.android.settingslib.Utils
import com.android.systemui.common.coroutine.ConflatedCallbackFlow.conflatedCallbackFlow
import com.android.systemui.common.coroutine.ConflatedCallbackFlow.conflatedCallbackFlow
import com.android.systemui.dagger.SysUISingleton
import com.android.systemui.dagger.SysUISingleton
import com.android.systemui.dagger.qualifiers.Application
import com.android.systemui.dagger.qualifiers.Main
import com.android.systemui.dagger.qualifiers.Main
import com.android.systemui.statusbar.pipeline.shared.ConnectivityPipelineLogger
import com.android.systemui.statusbar.pipeline.shared.ConnectivityPipelineLogger
import com.android.systemui.statusbar.pipeline.shared.ConnectivityPipelineLogger.Companion.SB_LOGGING_TAG
import com.android.systemui.statusbar.pipeline.shared.ConnectivityPipelineLogger.Companion.SB_LOGGING_TAG
@@ -38,10 +40,13 @@ import com.android.systemui.statusbar.pipeline.wifi.data.model.WifiActivityModel
import com.android.systemui.statusbar.pipeline.wifi.data.model.WifiNetworkModel
import com.android.systemui.statusbar.pipeline.wifi.data.model.WifiNetworkModel
import java.util.concurrent.Executor
import java.util.concurrent.Executor
import javax.inject.Inject
import javax.inject.Inject
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.ExperimentalCoroutinesApi
import kotlinx.coroutines.ExperimentalCoroutinesApi
import kotlinx.coroutines.channels.awaitClose
import kotlinx.coroutines.channels.awaitClose
import kotlinx.coroutines.flow.Flow
import kotlinx.coroutines.flow.Flow
import kotlinx.coroutines.flow.SharingStarted
import kotlinx.coroutines.flow.flowOf
import kotlinx.coroutines.flow.flowOf
import kotlinx.coroutines.flow.shareIn


/**
/**
 * Provides data related to the wifi state.
 * Provides data related to the wifi state.
@@ -64,9 +69,10 @@ interface WifiRepository {
@SuppressLint("MissingPermission")
@SuppressLint("MissingPermission")
class WifiRepositoryImpl @Inject constructor(
class WifiRepositoryImpl @Inject constructor(
    connectivityManager: ConnectivityManager,
    connectivityManager: ConnectivityManager,
        wifiManager: WifiManager?,
        @Main mainExecutor: Executor,
    logger: ConnectivityPipelineLogger,
    logger: ConnectivityPipelineLogger,
    @Main mainExecutor: Executor,
    @Application scope: CoroutineScope,
    wifiManager: WifiManager?,
) : WifiRepository {
) : WifiRepository {
    override val wifiNetwork: Flow<WifiNetworkModel> = conflatedCallbackFlow {
    override val wifiNetwork: Flow<WifiNetworkModel> = conflatedCallbackFlow {
        var currentWifi: WifiNetworkModel = WIFI_NETWORK_DEFAULT
        var currentWifi: WifiNetworkModel = WIFI_NETWORK_DEFAULT
@@ -80,7 +86,12 @@ class WifiRepositoryImpl @Inject constructor(


                val wifiInfo = networkCapabilitiesToWifiInfo(networkCapabilities)
                val wifiInfo = networkCapabilitiesToWifiInfo(networkCapabilities)
                if (wifiInfo?.isPrimary == true) {
                if (wifiInfo?.isPrimary == true) {
                    val wifiNetworkModel = wifiInfoToModel(wifiInfo, network.getNetId())
                    val wifiNetworkModel = createWifiNetworkModel(
                        wifiInfo,
                        network,
                        networkCapabilities,
                        wifiManager,
                    )
                    logger.logTransformation(
                    logger.logTransformation(
                        WIFI_NETWORK_CALLBACK_NAME,
                        WIFI_NETWORK_CALLBACK_NAME,
                        oldValue = currentWifi,
                        oldValue = currentWifi,
@@ -112,6 +123,7 @@ class WifiRepositoryImpl @Inject constructor(


        awaitClose { connectivityManager.unregisterNetworkCallback(callback) }
        awaitClose { connectivityManager.unregisterNetworkCallback(callback) }
    }
    }
        .shareIn(scope, started = SharingStarted.WhileSubscribed())


    override val wifiActivity: Flow<WifiActivityModel> =
    override val wifiActivity: Flow<WifiActivityModel> =
            if (wifiManager == null) {
            if (wifiManager == null) {
@@ -164,15 +176,26 @@ class WifiRepositoryImpl @Inject constructor(
            }
            }
        }
        }


        private fun wifiInfoToModel(wifiInfo: WifiInfo, networkId: Int): WifiNetworkModel {
        private fun createWifiNetworkModel(
            return WifiNetworkModel.Active(
            wifiInfo: WifiInfo,
                networkId,
            network: Network,
            networkCapabilities: NetworkCapabilities,
            wifiManager: WifiManager?,
        ): WifiNetworkModel {
            return if (wifiInfo.isCarrierMerged) {
                WifiNetworkModel.CarrierMerged
            } else {
                WifiNetworkModel.Active(
                        network.getNetId(),
                        isValidated = networkCapabilities.hasCapability(NET_CAPABILITY_VALIDATED),
                        level = wifiManager?.calculateSignalLevel(wifiInfo.rssi),
                        wifiInfo.ssid,
                        wifiInfo.ssid,
                        wifiInfo.isPasspointAp,
                        wifiInfo.isPasspointAp,
                        wifiInfo.isOsuAp,
                        wifiInfo.isOsuAp,
                        wifiInfo.passpointProviderFriendlyName
                        wifiInfo.passpointProviderFriendlyName
                )
                )
            }
            }
        }


        private fun prettyPrintActivity(activity: Int): String {
        private fun prettyPrintActivity(activity: Int): String {
            return when (activity) {
            return when (activity) {
+6 −1
Original line number Original line Diff line number Diff line
@@ -38,6 +38,7 @@ class WifiInteractor @Inject constructor(
    private val ssid: Flow<String?> = repository.wifiNetwork.map { info ->
    private val ssid: Flow<String?> = repository.wifiNetwork.map { info ->
        when (info) {
        when (info) {
            is WifiNetworkModel.Inactive -> null
            is WifiNetworkModel.Inactive -> null
            is WifiNetworkModel.CarrierMerged -> null
            is WifiNetworkModel.Active -> when {
            is WifiNetworkModel.Active -> when {
                info.isPasspointAccessPoint || info.isOnlineSignUpForPasspointAccessPoint ->
                info.isPasspointAccessPoint || info.isOnlineSignUpForPasspointAccessPoint ->
                    info.passpointProviderFriendlyName
                    info.passpointProviderFriendlyName
@@ -47,6 +48,10 @@ class WifiInteractor @Inject constructor(
        }
        }
    }
    }


    /** Our current wifi network. See [WifiNetworkModel]. */
    val wifiNetwork: Flow<WifiNetworkModel> = repository.wifiNetwork

    /** True if our wifi network has activity in (download), and false otherwise. */
    val hasActivityIn: Flow<Boolean> = combine(repository.wifiActivity, ssid) { activity, ssid ->
    val hasActivityIn: Flow<Boolean> = combine(repository.wifiActivity, ssid) { activity, ssid ->
            activity.hasActivityIn && ssid != null
            activity.hasActivityIn && ssid != null
        }
        }
+13 −2
Original line number Original line Diff line number Diff line
@@ -25,10 +25,10 @@ import androidx.lifecycle.Lifecycle
import androidx.lifecycle.repeatOnLifecycle
import androidx.lifecycle.repeatOnLifecycle
import com.android.systemui.R
import com.android.systemui.R
import com.android.systemui.lifecycle.repeatWhenAttached
import com.android.systemui.lifecycle.repeatWhenAttached
import com.android.systemui.statusbar.connectivity.WifiIcons.WIFI_FULL_ICONS
import com.android.systemui.statusbar.pipeline.wifi.ui.viewmodel.WifiViewModel
import com.android.systemui.statusbar.pipeline.wifi.ui.viewmodel.WifiViewModel
import kotlinx.coroutines.InternalCoroutinesApi
import kotlinx.coroutines.InternalCoroutinesApi
import kotlinx.coroutines.flow.collect
import kotlinx.coroutines.flow.collect
import kotlinx.coroutines.flow.distinctUntilChanged
import kotlinx.coroutines.launch
import kotlinx.coroutines.launch


/**
/**
@@ -50,10 +50,21 @@ object WifiViewBinder {


        view.isVisible = true
        view.isVisible = true
        iconView.isVisible = true
        iconView.isVisible = true
        iconView.setImageDrawable(view.context.getDrawable(WIFI_FULL_ICONS[2]))


        view.repeatWhenAttached {
        view.repeatWhenAttached {
            repeatOnLifecycle(Lifecycle.State.STARTED) {
            repeatOnLifecycle(Lifecycle.State.STARTED) {
                launch {
                    viewModel.wifiIconResId.distinctUntilChanged().collect { iconResId ->
                        iconView.setImageDrawable(
                            if (iconResId != null && iconResId > 0) {
                                iconView.context.getDrawable(iconResId)
                            } else {
                                null
                            }
                        )
                    }
                }

                launch {
                launch {
                    viewModel.tint.collect { tint ->
                    viewModel.tint.collect { tint ->
                        iconView.imageTintList = ColorStateList.valueOf(tint)
                        iconView.imageTintList = ColorStateList.valueOf(tint)
Loading