compose: blacklist: Switch to new search appbar API
Signed-off-by: Aayush Gupta <aayushgupta219@gmail.com>
This commit is contained in:
@@ -1,107 +0,0 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2025 The Calyx Institute
|
||||
* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*/
|
||||
|
||||
package com.aurora.store.compose.composables
|
||||
|
||||
import androidx.annotation.StringRes
|
||||
import androidx.compose.foundation.layout.RowScope
|
||||
import androidx.compose.foundation.layout.fillMaxWidth
|
||||
import androidx.compose.foundation.text.KeyboardActions
|
||||
import androidx.compose.foundation.text.KeyboardOptions
|
||||
import androidx.compose.material3.Icon
|
||||
import androidx.compose.material3.IconButton
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.material3.TextField
|
||||
import androidx.compose.material3.TextFieldDefaults
|
||||
import androidx.compose.material3.TopAppBar
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
import androidx.compose.runtime.saveable.rememberSaveable
|
||||
import androidx.compose.runtime.setValue
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.graphics.Color
|
||||
import androidx.compose.ui.platform.LocalFocusManager
|
||||
import androidx.compose.ui.res.painterResource
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.text.input.ImeAction
|
||||
import androidx.compose.ui.tooling.preview.Preview
|
||||
import com.aurora.store.R
|
||||
|
||||
/**
|
||||
* A top app bar composable to be used with Scaffold in different Screen
|
||||
* @param modifier The modifier to be applied to the composable
|
||||
* @param searchHint Hint to show to the user in search bar
|
||||
* @param onNavigateUp Action when user clicks the navigation icon
|
||||
* @param onSearch Callback for a search
|
||||
* @param actions Actions to display on the top app bar (for e.g. menu)
|
||||
*/
|
||||
@Composable
|
||||
fun SearchAppBarComposable(
|
||||
modifier: Modifier = Modifier,
|
||||
@StringRes searchHint: Int? = null,
|
||||
onNavigateUp: () -> Unit,
|
||||
onSearch: (query: String) -> Unit,
|
||||
actions: @Composable (RowScope.() -> Unit) = {}
|
||||
) {
|
||||
val focusManager = LocalFocusManager.current
|
||||
var query by rememberSaveable { mutableStateOf("") }
|
||||
|
||||
TopAppBar(
|
||||
modifier = modifier,
|
||||
title = {
|
||||
TextField(
|
||||
modifier = Modifier.fillMaxWidth(),
|
||||
value = query,
|
||||
onValueChange = { newQuery ->
|
||||
query = newQuery.trim()
|
||||
onSearch(query)
|
||||
},
|
||||
maxLines = 1,
|
||||
placeholder = { if (searchHint != null) Text(text = stringResource(searchHint)) },
|
||||
colors = TextFieldDefaults.colors(
|
||||
focusedContainerColor = Color.Transparent,
|
||||
focusedIndicatorColor = Color.Transparent,
|
||||
unfocusedContainerColor = Color.Transparent,
|
||||
unfocusedIndicatorColor = Color.Transparent
|
||||
),
|
||||
keyboardOptions = KeyboardOptions(imeAction = ImeAction.Search),
|
||||
keyboardActions = KeyboardActions(onSearch = { focusManager.clearFocus() })
|
||||
)
|
||||
},
|
||||
navigationIcon = {
|
||||
IconButton(onClick = onNavigateUp) {
|
||||
Icon(
|
||||
painter = painterResource(R.drawable.ic_arrow_back),
|
||||
contentDescription = null
|
||||
)
|
||||
}
|
||||
},
|
||||
actions = {
|
||||
if (query.isNotBlank()) {
|
||||
IconButton(
|
||||
onClick = {
|
||||
query = ""
|
||||
onSearch(query)
|
||||
focusManager.clearFocus(force = true)
|
||||
}
|
||||
) {
|
||||
Icon(painter = painterResource(R.drawable.ic_cancel), contentDescription = null)
|
||||
}
|
||||
}
|
||||
actions()
|
||||
}
|
||||
)
|
||||
}
|
||||
|
||||
@Preview(showBackground = true)
|
||||
@Composable
|
||||
private fun SearchAppBarComposablePreview() {
|
||||
SearchAppBarComposable(
|
||||
searchHint = R.string.search_hint,
|
||||
onNavigateUp = {},
|
||||
onSearch = {}
|
||||
)
|
||||
}
|
||||
@@ -14,12 +14,30 @@ import androidx.compose.foundation.layout.fillMaxWidth
|
||||
import androidx.compose.foundation.layout.padding
|
||||
import androidx.compose.foundation.lazy.LazyColumn
|
||||
import androidx.compose.foundation.lazy.items
|
||||
import androidx.compose.foundation.text.input.clearText
|
||||
import androidx.compose.foundation.text.input.rememberTextFieldState
|
||||
import androidx.compose.foundation.text.input.setTextAndPlaceCursorAtEnd
|
||||
import androidx.compose.material3.AppBarWithSearch
|
||||
import androidx.compose.material3.Icon
|
||||
import androidx.compose.material3.IconButton
|
||||
import androidx.compose.material3.Scaffold
|
||||
import androidx.compose.material3.SearchBarDefaults
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.material3.rememberSearchBarState
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.LaunchedEffect
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.remember
|
||||
import androidx.compose.runtime.rememberCoroutineScope
|
||||
import androidx.compose.runtime.snapshotFlow
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.focus.FocusRequester
|
||||
import androidx.compose.ui.focus.focusRequester
|
||||
import androidx.compose.ui.platform.LocalContext
|
||||
import androidx.compose.ui.res.dimensionResource
|
||||
import androidx.compose.ui.res.painterResource
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.text.style.TextOverflow
|
||||
import androidx.compose.ui.tooling.preview.Preview
|
||||
import androidx.core.content.pm.PackageInfoCompat
|
||||
import androidx.hilt.lifecycle.viewmodel.compose.hiltViewModel
|
||||
@@ -28,11 +46,12 @@ import com.aurora.Constants
|
||||
import com.aurora.extensions.toast
|
||||
import com.aurora.store.R
|
||||
import com.aurora.store.compose.composables.BlackListComposable
|
||||
import com.aurora.store.compose.composables.SearchAppBarComposable
|
||||
import com.aurora.store.compose.menu.BlacklistMenu
|
||||
import com.aurora.store.compose.menu.items.BlacklistMenuItem
|
||||
import com.aurora.store.util.PackageUtil
|
||||
import com.aurora.store.viewmodel.all.BlacklistViewModel
|
||||
import kotlinx.coroutines.flow.collectLatest
|
||||
import kotlinx.coroutines.launch
|
||||
import java.util.Calendar
|
||||
|
||||
@Composable
|
||||
@@ -75,8 +94,12 @@ private fun ScreenContent(
|
||||
onWhitelistAll: () -> Unit = {},
|
||||
onSearch: (query: String) -> Unit = {}
|
||||
) {
|
||||
|
||||
val context = LocalContext.current
|
||||
val textFieldState = rememberTextFieldState()
|
||||
val searchBarState = rememberSearchBarState()
|
||||
val focusRequester = remember { FocusRequester() }
|
||||
val coroutineScope = rememberCoroutineScope()
|
||||
|
||||
val docImportLauncher = rememberLauncherForActivityResult(
|
||||
contract = ActivityResultContracts.OpenDocument(),
|
||||
onResult = {
|
||||
@@ -98,6 +121,11 @@ private fun ScreenContent(
|
||||
}
|
||||
)
|
||||
|
||||
LaunchedEffect(key1 = textFieldState) {
|
||||
snapshotFlow { textFieldState.text.toString() }
|
||||
.collectLatest { query -> onSearch(query) }
|
||||
}
|
||||
|
||||
@Composable
|
||||
fun SetupMenu() {
|
||||
BlacklistMenu { menuItem ->
|
||||
@@ -117,16 +145,67 @@ private fun ScreenContent(
|
||||
}
|
||||
}
|
||||
|
||||
Scaffold(
|
||||
topBar = {
|
||||
SearchAppBarComposable(
|
||||
onNavigateUp = onNavigateUp,
|
||||
actions = { if (!packages.isNullOrEmpty()) SetupMenu() },
|
||||
searchHint = R.string.search_hint,
|
||||
onSearch = { query -> onSearch(query) }
|
||||
fun onRequestSearch(query: String) {
|
||||
textFieldState.setTextAndPlaceCursorAtEnd(query.trim())
|
||||
coroutineScope.launch { searchBarState.animateToCollapsed() }
|
||||
onSearch(textFieldState.text.toString())
|
||||
}
|
||||
|
||||
@Composable
|
||||
fun SearchBar() {
|
||||
val inputField = @Composable {
|
||||
SearchBarDefaults.InputField(
|
||||
modifier = Modifier.focusRequester(focusRequester),
|
||||
searchBarState = searchBarState,
|
||||
textFieldState = textFieldState,
|
||||
onSearch = { query -> onRequestSearch(query) },
|
||||
placeholder = {
|
||||
Text(
|
||||
text = stringResource(R.string.search_hint),
|
||||
maxLines = 1,
|
||||
overflow = TextOverflow.Ellipsis
|
||||
)
|
||||
},
|
||||
leadingIcon = {
|
||||
Icon(
|
||||
painter = painterResource(R.drawable.ic_round_search),
|
||||
contentDescription = stringResource(R.string.action_search)
|
||||
)
|
||||
},
|
||||
trailingIcon = {
|
||||
if (textFieldState.text.isNotBlank()) {
|
||||
IconButton(
|
||||
onClick = {
|
||||
textFieldState.clearText()
|
||||
focusRequester.requestFocus()
|
||||
}
|
||||
) {
|
||||
Icon(
|
||||
painter = painterResource(R.drawable.ic_cancel),
|
||||
contentDescription = stringResource(R.string.action_clear)
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
)
|
||||
}
|
||||
) { paddingValues ->
|
||||
|
||||
AppBarWithSearch(
|
||||
state = searchBarState,
|
||||
inputField = inputField,
|
||||
navigationIcon = {
|
||||
IconButton(onClick = onNavigateUp) {
|
||||
Icon(
|
||||
painter = painterResource(R.drawable.ic_arrow_back),
|
||||
contentDescription = stringResource(R.string.action_back)
|
||||
)
|
||||
}
|
||||
},
|
||||
actions = { if (!packages.isNullOrEmpty()) SetupMenu() }
|
||||
)
|
||||
}
|
||||
|
||||
Scaffold(topBar = { SearchBar() }) { paddingValues ->
|
||||
LazyColumn(
|
||||
modifier = Modifier
|
||||
.fillMaxWidth()
|
||||
|
||||
@@ -49,6 +49,7 @@ import androidx.compose.ui.res.dimensionResource
|
||||
import androidx.compose.ui.res.painterResource
|
||||
import androidx.compose.ui.res.stringArrayResource
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.text.style.TextOverflow
|
||||
import androidx.compose.ui.tooling.preview.PreviewParameter
|
||||
import androidx.compose.ui.tooling.preview.PreviewScreenSizes
|
||||
import androidx.hilt.lifecycle.viewmodel.compose.hiltViewModel
|
||||
@@ -142,7 +143,13 @@ private fun ScreenContent(
|
||||
searchBarState = searchBarState,
|
||||
textFieldState = textFieldState,
|
||||
onSearch = { query -> onRequestSearch(query) },
|
||||
placeholder = { Text(text = stringResource(R.string.search_hint)) },
|
||||
placeholder = {
|
||||
Text(
|
||||
text = stringResource(R.string.search_hint),
|
||||
maxLines = 1,
|
||||
overflow = TextOverflow.Ellipsis
|
||||
)
|
||||
},
|
||||
leadingIcon = {
|
||||
IconButton(onClick = onNavigateUp) {
|
||||
Icon(
|
||||
|
||||
Reference in New Issue
Block a user