Update: Revamp PackageState to taxonomical ComponentStates

This commit is contained in:
machiav3lli 2022-06-02 03:58:44 +02:00
parent 9a74e003d9
commit 4a323ded0b
6 changed files with 53 additions and 44 deletions

View File

@ -89,34 +89,37 @@ enum class AntiFeature(val key: String, @StringRes val titleResId: Int) {
NSFW("NSFW", R.string.not_safe_for_work) NSFW("NSFW", R.string.not_safe_for_work)
} }
sealed interface PackageState { sealed interface ComponentState {
val icon: ImageVector val icon: ImageVector
val textId: Int val textId: Int
} }
sealed class Cancelable( sealed class DownloadState(
@StringRes override val textId: Int, @StringRes override val textId: Int,
override val icon: ImageVector = Icons.Rounded.Close override val icon: ImageVector = Icons.Rounded.Close
) : PackageState ) : ComponentState {
object Pending : Cancelable(R.string.pending) object Pending : DownloadState(R.string.pending)
object Connecting : Cancelable(R.string.connecting) object Connecting : DownloadState(R.string.connecting)
class Downloading(val downloaded: Long, val total: Long?) : class Downloading(val downloaded: Long, val total: Long?) :
Cancelable(R.string.downloading) DownloadState(R.string.downloading)
object Installing : Cancelable(R.string.installing) object Installing : DownloadState(R.string.installing)
}
sealed class ButtonWork( sealed class ActionState(
@StringRes override val textId: Int, @StringRes override val textId: Int,
override val icon: ImageVector = Icons.Rounded.Download override val icon: ImageVector = Icons.Rounded.Download
) : PackageState ) : ComponentState {
object Install : ButtonWork(R.string.install, Icons.Rounded.Download) object Install : ActionState(R.string.install, Icons.Rounded.Download)
object Update : ButtonWork(R.string.update, Icons.Rounded.Download) object Update : ActionState(R.string.update, Icons.Rounded.Download)
object Uninstall : ButtonWork(R.string.uninstall, Icons.Rounded.Delete) object Uninstall : ActionState(R.string.uninstall, Icons.Rounded.Delete)
object Launch : ButtonWork(R.string.launch, Icons.Rounded.Launch) object Launch : ActionState(R.string.launch, Icons.Rounded.Launch)
object Details : ButtonWork(R.string.details, Icons.Rounded.Tune) object Details : ActionState(R.string.details, Icons.Rounded.Tune)
object Share : ButtonWork(R.string.share, Icons.Rounded.Share) object Share : ActionState(R.string.share, Icons.Rounded.Share)
class Cancel(@StringRes stateId: Int) : ActionState(stateId, Icons.Rounded.Close)
}
open class LinkType( open class LinkType(
@DrawableRes val iconResId: Int, @DrawableRes val iconResId: Int,

View File

@ -17,18 +17,21 @@ import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier import androidx.compose.ui.Modifier
import androidx.compose.ui.res.stringResource import androidx.compose.ui.res.stringResource
import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.dp
import com.looker.droidify.entity.PackageState import com.looker.droidify.entity.ActionState
import com.looker.droidify.entity.ComponentState
import com.looker.droidify.entity.DownloadState
@OptIn(ExperimentalAnimationApi::class) @OptIn(ExperimentalAnimationApi::class)
@Composable @Composable
fun MainActionButton( fun MainActionButton(
modifier: Modifier = Modifier, modifier: Modifier = Modifier,
packageState: PackageState, actionState: ActionState,
onClick: (PackageState) -> Unit downloadState: DownloadState?,
onClick: (ComponentState) -> Unit
) { ) {
ElevatedButton( ElevatedButton(
modifier = modifier, modifier = modifier,
onClick = { onClick(packageState) } onClick = { onClick(actionState) }
) { ) {
AnimatedContent( AnimatedContent(
targetState = packageState, targetState = packageState,
@ -66,7 +69,7 @@ fun MainActionButton(
@Composable @Composable
fun SecondaryActionButton( fun SecondaryActionButton(
modifier: Modifier = Modifier, modifier: Modifier = Modifier,
packageState: PackageState?, packageState: ComponentState?,
onClick: () -> Unit onClick: () -> Unit
) { ) {
packageState?.let { packageState?.let {

View File

@ -32,8 +32,7 @@ import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.dp
import com.looker.droidify.database.entity.Installed import com.looker.droidify.database.entity.Installed
import com.looker.droidify.database.entity.Repository import com.looker.droidify.database.entity.Repository
import com.looker.droidify.entity.Install import com.looker.droidify.entity.ActionState
import com.looker.droidify.entity.Launch
import com.looker.droidify.entity.ProductItem import com.looker.droidify.entity.ProductItem
import com.looker.droidify.network.CoilDownloader import com.looker.droidify.network.CoilDownloader
import com.looker.droidify.ui.compose.utils.ExpandableCard import com.looker.droidify.ui.compose.utils.ExpandableCard
@ -155,8 +154,8 @@ fun ExpandedItemContent(
onClick = { onActionClicked(item) } onClick = { onActionClicked(item) }
) { ) {
val action = when { val action = when {
installed != null -> Launch installed != null -> ActionState.Launch
else -> Install else -> ActionState.Install
} }
Icon( Icon(
imageVector = action.icon, imageVector = action.icon,

View File

@ -26,10 +26,9 @@ import androidx.compose.ui.draw.clip
import androidx.compose.ui.res.stringResource import androidx.compose.ui.res.stringResource
import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.dp
import com.looker.droidify.R import com.looker.droidify.R
import com.looker.droidify.entity.Cancelable import com.looker.droidify.entity.ActionState
import com.looker.droidify.entity.Downloading import com.looker.droidify.entity.ComponentState
import com.looker.droidify.entity.Install import com.looker.droidify.entity.DownloadState
import com.looker.droidify.entity.PackageState
import com.looker.droidify.ui.compose.components.MainActionButton import com.looker.droidify.ui.compose.components.MainActionButton
import com.looker.droidify.ui.compose.components.SecondaryActionButton import com.looker.droidify.ui.compose.components.SecondaryActionButton
import com.looker.droidify.ui.compose.utils.NetworkImage import com.looker.droidify.ui.compose.utils.NetworkImage
@ -41,8 +40,9 @@ fun AppInfoHeader(
versionCode: String, versionCode: String,
appSize: String, appSize: String,
appDev: String, appDev: String,
state: PackageState? = Install, mainAction: ActionState? = ActionState.Install,
secondaryAction: PackageState? = null, downloadState: DownloadState?,
secondaryAction: ComponentState? = null,
onSource: () -> Unit = { }, onSource: () -> Unit = { },
onSourceLong: () -> Unit = { }, onSourceLong: () -> Unit = { },
onAction: () -> Unit = { }, onAction: () -> Unit = { },
@ -73,10 +73,12 @@ fun AppInfoHeader(
}) })
MainActionButton( MainActionButton(
modifier = Modifier.weight(1f), modifier = Modifier.weight(1f),
packageState = state ?: Install, actionState = mainAction ?: ActionState.Install,
downloadState = downloadState,
onClick = { onClick = {
onAction() onAction()
}) }
)
} }
} }
} }
@ -88,7 +90,7 @@ fun TopBarHeader(
icon: String? = null, icon: String? = null,
appName: String, appName: String,
packageName: String, packageName: String,
state: PackageState? = Install, state: DownloadState? = null,
actions: @Composable () -> Unit = {} actions: @Composable () -> Unit = {}
) { ) {
Surface( Surface(
@ -118,12 +120,12 @@ fun TopBarHeader(
Box { actions() } Box { actions() }
} }
AnimatedVisibility(visible = state is Cancelable) { AnimatedVisibility(visible = state is DownloadState) {
DownloadProgress( DownloadProgress(
modifier = Modifier.padding(horizontal = 12.dp), modifier = Modifier.padding(horizontal = 12.dp),
totalSize = if (state is Downloading) state.total ?: 1L else 1L, totalSize = if (state is DownloadState.Downloading) state.total ?: 1L else 1L,
isIndeterminate = state !is Downloading, isIndeterminate = state !is DownloadState.Downloading,
downloaded = if (state is Downloading) state.downloaded else 0L, downloaded = if (state is DownloadState.Downloading) state.downloaded else 0L,
) )
} }
} }

View File

@ -2,12 +2,12 @@ package com.looker.droidify.ui.compose.utils
import android.net.Uri import android.net.Uri
import com.looker.droidify.database.entity.Release import com.looker.droidify.database.entity.Release
import com.looker.droidify.entity.PackageState import com.looker.droidify.entity.ComponentState
import com.looker.droidify.entity.ProductPreference import com.looker.droidify.entity.ProductPreference
import com.looker.droidify.entity.Screenshot import com.looker.droidify.entity.Screenshot
interface Callbacks { interface Callbacks {
fun onActionClick(action: PackageState?) fun onActionClick(action: ComponentState?)
fun onPreferenceChanged(preference: ProductPreference) fun onPreferenceChanged(preference: ProductPreference)
fun onPermissionsClick(group: String?, permissions: List<String>) fun onPermissionsClick(group: String?, permissions: List<String>)
fun onScreenshotClick(screenshot: Screenshot) fun onScreenshotClick(screenshot: Screenshot)

View File

@ -8,7 +8,8 @@ import com.looker.droidify.database.DatabaseX
import com.looker.droidify.database.entity.Installed import com.looker.droidify.database.entity.Installed
import com.looker.droidify.database.entity.Product import com.looker.droidify.database.entity.Product
import com.looker.droidify.database.entity.Repository import com.looker.droidify.database.entity.Repository
import com.looker.droidify.entity.PackageState import com.looker.droidify.entity.ActionState
import com.looker.droidify.entity.DownloadState
class AppViewModelX(val db: DatabaseX, val packageName: String) : ViewModel() { class AppViewModelX(val db: DatabaseX, val packageName: String) : ViewModel() {
@ -21,9 +22,10 @@ class AppViewModelX(val db: DatabaseX, val packageName: String) : ViewModel() {
set(value) { set(value) {
_productRepos.value = value _productRepos.value = value
} }
val state = MutableLiveData<PackageState>() val downloadState = MutableLiveData<DownloadState>()
val actions = MutableLiveData<Set<PackageState>>() val mainAction = MutableLiveData<ActionState>()
val secondaryAction = MutableLiveData<PackageState>() val actions = MutableLiveData<Set<ActionState>>()
val secondaryAction = MutableLiveData<ActionState>()
init { init {
products.addSource(db.productDao.getLive(packageName)) { products.setValue(it.filterNotNull()) } products.addSource(db.productDao.getLive(packageName)) { products.setValue(it.filterNotNull()) }