Show appropriate empty states for autofill flow (#843)

This commit is contained in:
Brian Yencho
2024-01-28 22:42:13 -06:00
committed by Álison Fernandes
parent 9a8aca9fe1
commit 82ef39e15d
8 changed files with 214 additions and 71 deletions

View File

@@ -9,10 +9,8 @@ import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.text.style.TextAlign
import androidx.compose.ui.unit.dp
import com.x8bit.bitwarden.R
import com.x8bit.bitwarden.ui.vault.feature.vault.VaultNoItems
/**
@@ -20,31 +18,21 @@ import com.x8bit.bitwarden.ui.vault.feature.vault.VaultNoItems
*/
@Composable
fun VaultItemListingEmpty(
itemListingType: VaultItemListingState.ItemListingType,
state: VaultItemListingState.ViewState.NoItems,
addItemClickAction: () -> Unit,
modifier: Modifier = Modifier,
) {
when (itemListingType) {
is VaultItemListingState.ItemListingType.Vault.Folder -> {
GenericNoItems(
modifier = modifier,
text = stringResource(id = R.string.no_items_folder),
)
}
is VaultItemListingState.ItemListingType.Vault.Trash -> {
GenericNoItems(
modifier = modifier,
text = stringResource(id = R.string.no_items_trash),
)
}
else -> {
VaultNoItems(
modifier = modifier,
addItemClickAction = addItemClickAction,
)
}
if (state.shouldShowAddButton) {
VaultNoItems(
message = state.message(),
modifier = modifier,
addItemClickAction = addItemClickAction,
)
} else {
GenericNoItems(
text = state.message(),
modifier = modifier,
)
}
}

View File

@@ -242,7 +242,7 @@ private fun VaultItemListingScaffold(
is VaultItemListingState.ViewState.NoItems -> {
VaultItemListingEmpty(
itemListingType = state.itemListingType,
state = state.viewState,
addItemClickAction = vaultItemListingHandlers.addVaultItemClick,
modifier = modifier,
)

View File

@@ -545,8 +545,10 @@ class VaultItemListingViewModel @Inject constructor(
}
.toFilteredList(state.vaultFilterType)
.toViewState(
itemListingType = listingType,
baseIconUrl = state.baseIconUrl,
isIconLoadingDisabled = state.isIconLoadingDisabled,
autofillSelectionData = state.autofillSelectionData,
)
}
@@ -702,7 +704,10 @@ data class VaultItemListingState(
/**
* Represents a state where the [VaultItemListingScreen] has no items to display.
*/
data object NoItems : ViewState() {
data class NoItems(
val message: Text,
val shouldShowAddButton: Boolean,
) : ViewState() {
override val isPullToRefreshEnabled: Boolean get() = true
}

View File

@@ -8,7 +8,10 @@ import com.bitwarden.core.FolderView
import com.bitwarden.core.SendType
import com.bitwarden.core.SendView
import com.x8bit.bitwarden.R
import com.x8bit.bitwarden.data.autofill.model.AutofillSelectionData
import com.x8bit.bitwarden.data.platform.util.subtitle
import com.x8bit.bitwarden.ui.platform.base.util.asText
import com.x8bit.bitwarden.ui.platform.base.util.toHostOrPathOrNull
import com.x8bit.bitwarden.ui.platform.components.model.IconData
import com.x8bit.bitwarden.ui.platform.util.toFormattedPattern
import com.x8bit.bitwarden.ui.tools.feature.send.util.toLabelIcons
@@ -78,8 +81,10 @@ fun SendView.determineListingPredicate(
* Transforms a list of [CipherView] into [VaultItemListingState.ViewState].
*/
fun List<CipherView>.toViewState(
itemListingType: VaultItemListingState.ItemListingType.Vault,
baseIconUrl: String,
isIconLoadingDisabled: Boolean,
autofillSelectionData: AutofillSelectionData?,
): VaultItemListingState.ViewState =
if (isNotEmpty()) {
VaultItemListingState.ViewState.Content(
@@ -89,7 +94,36 @@ fun List<CipherView>.toViewState(
),
)
} else {
VaultItemListingState.ViewState.NoItems
// Use the autofill empty message if necessary, otherwise use normal type-specific message
val message = autofillSelectionData
?.uri
?.toHostOrPathOrNull()
?.let { R.string.no_items_for_uri.asText(it) }
?: run {
when (itemListingType) {
is VaultItemListingState.ItemListingType.Vault.Folder -> {
R.string.no_items_folder
}
VaultItemListingState.ItemListingType.Vault.Trash -> {
R.string.no_items_trash
}
else -> R.string.no_items
}
.asText()
}
val shouldShowAddButton = when (itemListingType) {
is VaultItemListingState.ItemListingType.Vault.Folder,
VaultItemListingState.ItemListingType.Vault.Trash,
-> false
else -> true
}
VaultItemListingState.ViewState.NoItems(
message = message,
shouldShowAddButton = shouldShowAddButton,
)
}
/**
@@ -107,7 +141,10 @@ fun List<SendView>.toViewState(
),
)
} else {
VaultItemListingState.ViewState.NoItems
VaultItemListingState.ViewState.NoItems(
message = R.string.no_items.asText(),
shouldShowAddButton = true,
)
}
/** * Updates a [VaultItemListingState.ItemListingType] with the given data if necessary. */

View File

@@ -25,6 +25,7 @@ import com.x8bit.bitwarden.R
fun VaultNoItems(
addItemClickAction: () -> Unit,
modifier: Modifier = Modifier,
message: String = stringResource(id = R.string.no_items),
) {
Column(
modifier = modifier,
@@ -36,7 +37,7 @@ fun VaultNoItems(
modifier = Modifier
.fillMaxWidth()
.padding(horizontal = 16.dp),
text = stringResource(id = R.string.no_items),
text = message,
style = MaterialTheme.typography.bodyMedium,
)