Add search only scaffold for assistant activity
This commit is contained in:
parent
2d60797830
commit
8be8875462
@ -0,0 +1,151 @@
|
|||||||
|
package de.mm20.launcher2.ui.assistant
|
||||||
|
|
||||||
|
import androidx.compose.animation.core.animateDpAsState
|
||||||
|
import androidx.compose.foundation.layout.*
|
||||||
|
import androidx.compose.foundation.lazy.rememberLazyListState
|
||||||
|
import androidx.compose.material3.MaterialTheme
|
||||||
|
import androidx.compose.runtime.*
|
||||||
|
import androidx.compose.runtime.livedata.observeAsState
|
||||||
|
import androidx.compose.ui.Alignment
|
||||||
|
import androidx.compose.ui.Modifier
|
||||||
|
import androidx.compose.ui.graphics.Color
|
||||||
|
import androidx.compose.ui.unit.dp
|
||||||
|
import androidx.lifecycle.viewmodel.compose.viewModel
|
||||||
|
import com.google.accompanist.systemuicontroller.rememberSystemUiController
|
||||||
|
import de.mm20.launcher2.preferences.Settings
|
||||||
|
import de.mm20.launcher2.ui.launcher.LauncherScaffoldVM
|
||||||
|
import de.mm20.launcher2.ui.launcher.search.SearchBar
|
||||||
|
import de.mm20.launcher2.ui.launcher.search.SearchBarLevel
|
||||||
|
import de.mm20.launcher2.ui.launcher.search.SearchColumn
|
||||||
|
import de.mm20.launcher2.ui.launcher.search.SearchVM
|
||||||
|
import kotlinx.coroutines.flow.map
|
||||||
|
|
||||||
|
@Composable
|
||||||
|
fun AssistantScaffold(
|
||||||
|
modifier: Modifier = Modifier,
|
||||||
|
darkStatusBarIcons: Boolean = false,
|
||||||
|
darkNavBarIcons: Boolean = false,
|
||||||
|
) {
|
||||||
|
val viewModel: LauncherScaffoldVM = viewModel()
|
||||||
|
|
||||||
|
val bottomSearchBar by remember {
|
||||||
|
viewModel.dataStore.data.map { it.appearance.layout != Settings.AppearanceSettings.Layout.PullDown }
|
||||||
|
}.collectAsState(null)
|
||||||
|
|
||||||
|
val reverseResults by remember {
|
||||||
|
viewModel.dataStore.data.map { it.appearance.layout != Settings.AppearanceSettings.Layout.PullDown }
|
||||||
|
}.collectAsState(null)
|
||||||
|
|
||||||
|
val searchBarFocused by viewModel.searchBarFocused.observeAsState(false)
|
||||||
|
|
||||||
|
val searchState = rememberLazyListState()
|
||||||
|
|
||||||
|
val isSearchAtStart by remember {
|
||||||
|
derivedStateOf {
|
||||||
|
searchState.firstVisibleItemIndex == 0 && searchState.firstVisibleItemScrollOffset == 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
val isSearchAtEnd by remember {
|
||||||
|
derivedStateOf {
|
||||||
|
val lastItem = searchState.layoutInfo.visibleItemsInfo.lastOrNull() ?: return@derivedStateOf true
|
||||||
|
lastItem.offset + lastItem.size <= searchState.layoutInfo.viewportEndOffset - searchState.layoutInfo.afterContentPadding
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (reverseResults == null || bottomSearchBar == null) return
|
||||||
|
|
||||||
|
|
||||||
|
val searchBarLevel by remember {
|
||||||
|
derivedStateOf {
|
||||||
|
when {
|
||||||
|
reverseResults == bottomSearchBar && isSearchAtStart -> SearchBarLevel.Active
|
||||||
|
reverseResults != bottomSearchBar && isSearchAtEnd -> SearchBarLevel.Active
|
||||||
|
else -> SearchBarLevel.Raised
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
val systemUiController = rememberSystemUiController()
|
||||||
|
val showStatusBarScrim by remember {
|
||||||
|
derivedStateOf {
|
||||||
|
if (reverseResults == true) {
|
||||||
|
!isSearchAtEnd
|
||||||
|
} else {
|
||||||
|
!isSearchAtStart
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
val showNavBarScrim by remember {
|
||||||
|
derivedStateOf {
|
||||||
|
if (reverseResults == true) {
|
||||||
|
!isSearchAtStart
|
||||||
|
} else {
|
||||||
|
!isSearchAtEnd
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
val colorSurface = MaterialTheme.colorScheme.surface
|
||||||
|
LaunchedEffect(darkStatusBarIcons, colorSurface, showStatusBarScrim) {
|
||||||
|
if (showStatusBarScrim) {
|
||||||
|
systemUiController.setStatusBarColor(
|
||||||
|
colorSurface.copy(0.7f),
|
||||||
|
)
|
||||||
|
} else {
|
||||||
|
systemUiController.setStatusBarColor(
|
||||||
|
Color.Transparent,
|
||||||
|
darkIcons = darkStatusBarIcons
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
LaunchedEffect(darkNavBarIcons, showNavBarScrim) {
|
||||||
|
if (showNavBarScrim) {
|
||||||
|
systemUiController.setNavigationBarColor(
|
||||||
|
colorSurface.copy(0.7f),
|
||||||
|
)
|
||||||
|
} else {
|
||||||
|
systemUiController.setNavigationBarColor(
|
||||||
|
Color.Transparent,
|
||||||
|
darkIcons = darkNavBarIcons,
|
||||||
|
navigationBarContrastEnforced = false
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
val searchVM: SearchVM = viewModel()
|
||||||
|
val websearches by searchVM.websearchResults.observeAsState(emptyList())
|
||||||
|
val webSearchPadding by animateDpAsState(
|
||||||
|
if (websearches.isEmpty()) 0.dp else 48.dp
|
||||||
|
)
|
||||||
|
val windowInsets = WindowInsets.safeDrawing.asPaddingValues()
|
||||||
|
Box(modifier = Modifier.fillMaxSize()) {
|
||||||
|
SearchColumn(
|
||||||
|
modifier = Modifier.fillMaxSize(),
|
||||||
|
paddingValues = PaddingValues(
|
||||||
|
top = (if (bottomSearchBar == true) 0.dp else 56.dp + webSearchPadding) + 4.dp + windowInsets.calculateTopPadding(),
|
||||||
|
bottom = (if (bottomSearchBar == true) 56.dp + webSearchPadding else 0.dp) + 4.dp + windowInsets.calculateBottomPadding()
|
||||||
|
),
|
||||||
|
reverse = reverseResults == true,
|
||||||
|
state = searchState
|
||||||
|
)
|
||||||
|
|
||||||
|
SearchBar(
|
||||||
|
level = { searchBarLevel },
|
||||||
|
modifier = Modifier
|
||||||
|
.fillMaxWidth()
|
||||||
|
.wrapContentHeight()
|
||||||
|
.align(if (bottomSearchBar == true) Alignment.BottomCenter else Alignment.TopCenter)
|
||||||
|
.windowInsetsPadding(WindowInsets.safeDrawing)
|
||||||
|
.padding(8.dp),
|
||||||
|
focused = searchBarFocused,
|
||||||
|
onFocusChange = {
|
||||||
|
if (it) viewModel.openSearch()
|
||||||
|
viewModel.setSearchbarFocus(it)
|
||||||
|
},
|
||||||
|
reverse = bottomSearchBar == true
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -73,7 +73,7 @@ fun PagerScaffold(
|
|||||||
|
|
||||||
val isSearchAtEnd by remember {
|
val isSearchAtEnd by remember {
|
||||||
derivedStateOf {
|
derivedStateOf {
|
||||||
val lastItem = searchState.layoutInfo.visibleItemsInfo.last()
|
val lastItem = searchState.layoutInfo.visibleItemsInfo.lastOrNull() ?: return@derivedStateOf true
|
||||||
lastItem.offset + lastItem.size <= searchState.layoutInfo.viewportEndOffset - searchState.layoutInfo.afterContentPadding
|
lastItem.offset + lastItem.size <= searchState.layoutInfo.viewportEndOffset - searchState.layoutInfo.afterContentPadding
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -69,7 +69,7 @@ fun PullDownScaffold(
|
|||||||
|
|
||||||
val isSearchAtEnd by remember {
|
val isSearchAtEnd by remember {
|
||||||
derivedStateOf {
|
derivedStateOf {
|
||||||
val lastItem = searchState.layoutInfo.visibleItemsInfo.last()
|
val lastItem = searchState.layoutInfo.visibleItemsInfo.lastOrNull() ?: return@derivedStateOf true
|
||||||
lastItem.offset + lastItem.size <= searchState.layoutInfo.viewportEndOffset - searchState.layoutInfo.afterContentPadding
|
lastItem.offset + lastItem.size <= searchState.layoutInfo.viewportEndOffset - searchState.layoutInfo.afterContentPadding
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -36,6 +36,7 @@ import com.android.launcher3.GestureNavContract
|
|||||||
import com.google.accompanist.systemuicontroller.rememberSystemUiController
|
import com.google.accompanist.systemuicontroller.rememberSystemUiController
|
||||||
import de.mm20.launcher2.preferences.Settings
|
import de.mm20.launcher2.preferences.Settings
|
||||||
import de.mm20.launcher2.ui.R
|
import de.mm20.launcher2.ui.R
|
||||||
|
import de.mm20.launcher2.ui.assistant.AssistantScaffold
|
||||||
import de.mm20.launcher2.ui.base.BaseActivity
|
import de.mm20.launcher2.ui.base.BaseActivity
|
||||||
import de.mm20.launcher2.ui.base.ProvideCurrentTime
|
import de.mm20.launcher2.ui.base.ProvideCurrentTime
|
||||||
import de.mm20.launcher2.ui.base.ProvideSettings
|
import de.mm20.launcher2.ui.base.ProvideSettings
|
||||||
@ -127,36 +128,45 @@ abstract class SharedLauncherActivity(
|
|||||||
contentAlignment = Alignment.BottomCenter
|
contentAlignment = Alignment.BottomCenter
|
||||||
) {
|
) {
|
||||||
NavBarEffects(modifier = Modifier.fillMaxSize())
|
NavBarEffects(modifier = Modifier.fillMaxSize())
|
||||||
when (layout) {
|
if (mode == LauncherActivityMode.Assistant) {
|
||||||
Settings.AppearanceSettings.Layout.PullDown -> {
|
AssistantScaffold(
|
||||||
PullDownScaffold(
|
modifier = Modifier
|
||||||
modifier = Modifier
|
.fillMaxSize(),
|
||||||
.fillMaxSize()
|
darkStatusBarIcons = lightStatus,
|
||||||
.graphicsLayer {
|
darkNavBarIcons = lightNav,
|
||||||
scaleX = 0.5f + enterTransition.value * 0.5f
|
)
|
||||||
scaleY = 0.5f + enterTransition.value * 0.5f
|
} else {
|
||||||
alpha = enterTransition.value
|
when (layout) {
|
||||||
},
|
Settings.AppearanceSettings.Layout.PullDown -> {
|
||||||
darkStatusBarIcons = lightStatus,
|
PullDownScaffold(
|
||||||
darkNavBarIcons = lightNav,
|
modifier = Modifier
|
||||||
)
|
.fillMaxSize()
|
||||||
|
.graphicsLayer {
|
||||||
|
scaleX = 0.5f + enterTransition.value * 0.5f
|
||||||
|
scaleY = 0.5f + enterTransition.value * 0.5f
|
||||||
|
alpha = enterTransition.value
|
||||||
|
},
|
||||||
|
darkStatusBarIcons = lightStatus,
|
||||||
|
darkNavBarIcons = lightNav,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
Settings.AppearanceSettings.Layout.Pager,
|
||||||
|
Settings.AppearanceSettings.Layout.PagerReversed -> {
|
||||||
|
PagerScaffold(
|
||||||
|
modifier = Modifier
|
||||||
|
.fillMaxSize()
|
||||||
|
.graphicsLayer {
|
||||||
|
scaleX = enterTransition.value
|
||||||
|
scaleY = enterTransition.value
|
||||||
|
alpha = enterTransition.value
|
||||||
|
},
|
||||||
|
darkStatusBarIcons = lightStatus,
|
||||||
|
darkNavBarIcons = lightNav,
|
||||||
|
reverse = layout == Settings.AppearanceSettings.Layout.PagerReversed
|
||||||
|
)
|
||||||
|
}
|
||||||
|
else -> {}
|
||||||
}
|
}
|
||||||
Settings.AppearanceSettings.Layout.Pager,
|
|
||||||
Settings.AppearanceSettings.Layout.PagerReversed -> {
|
|
||||||
PagerScaffold(
|
|
||||||
modifier = Modifier
|
|
||||||
.fillMaxSize()
|
|
||||||
.graphicsLayer {
|
|
||||||
scaleX = enterTransition.value
|
|
||||||
scaleY = enterTransition.value
|
|
||||||
alpha = enterTransition.value
|
|
||||||
},
|
|
||||||
darkStatusBarIcons = lightStatus,
|
|
||||||
darkNavBarIcons = lightNav,
|
|
||||||
reverse = layout == Settings.AppearanceSettings.Layout.PagerReversed
|
|
||||||
)
|
|
||||||
}
|
|
||||||
else -> {}
|
|
||||||
}
|
}
|
||||||
SnackbarHost(
|
SnackbarHost(
|
||||||
snackbarHostState,
|
snackbarHostState,
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user