Reset search filters when query is cleared

This commit is contained in:
MM20 2024-04-21 20:30:55 +02:00
parent eda57aea2b
commit ee83b87f39
No known key found for this signature in database
GPG Key ID: 0B61A8F2DEAFA389
12 changed files with 91 additions and 55 deletions

View File

@ -5,7 +5,6 @@ import androidx.compose.foundation.layout.*
import androidx.compose.foundation.lazy.rememberLazyListState import androidx.compose.foundation.lazy.rememberLazyListState
import androidx.compose.material3.MaterialTheme import androidx.compose.material3.MaterialTheme
import androidx.compose.runtime.* import androidx.compose.runtime.*
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier import androidx.compose.ui.Modifier
import androidx.compose.ui.geometry.Offset import androidx.compose.ui.geometry.Offset
import androidx.compose.ui.graphics.Color import androidx.compose.ui.graphics.Color
@ -13,7 +12,6 @@ import androidx.compose.ui.input.nestedscroll.NestedScrollConnection
import androidx.compose.ui.input.nestedscroll.NestedScrollSource import androidx.compose.ui.input.nestedscroll.NestedScrollSource
import androidx.compose.ui.input.nestedscroll.nestedScroll import androidx.compose.ui.input.nestedscroll.nestedScroll
import androidx.compose.ui.platform.* import androidx.compose.ui.platform.*
import androidx.compose.ui.unit.IntOffset
import androidx.compose.ui.unit.dp import androidx.compose.ui.unit.dp
import androidx.lifecycle.Lifecycle import androidx.lifecycle.Lifecycle
import androidx.lifecycle.repeatOnLifecycle import androidx.lifecycle.repeatOnLifecycle
@ -184,12 +182,9 @@ fun AssistantScaffold(
LauncherSearchBar( LauncherSearchBar(
modifier = Modifier modifier = Modifier
.fillMaxSize(), .fillMaxSize(),
searchBarOffset = { style = searchBarStyle,
(if (searchBarFocused || fixedSearchBar) 0
else searchBarOffset.toInt() * if (bottomSearchBar) -1 else 1)
- (if (bottomSearchBar) with(density) { keyboardFilterBarPadding.toPx() }.toInt() else 0)
},
level = { searchBarLevel }, level = { searchBarLevel },
value = { value },
focused = searchBarFocused, focused = searchBarFocused,
onFocusChange = { onFocusChange = {
if (it) viewModel.openSearch() if (it) viewModel.openSearch()
@ -198,11 +193,13 @@ fun AssistantScaffold(
actions = actions, actions = actions,
highlightedAction = searchVM.bestMatch.value as? SearchAction, highlightedAction = searchVM.bestMatch.value as? SearchAction,
isSearchOpen = true, isSearchOpen = true,
value = { value },
onValueChange = { searchVM.search(it) },
darkColors = LocalPreferDarkContentOverWallpaper.current && searchBarColor == SearchBarColors.Auto || searchBarColor == SearchBarColors.Dark, darkColors = LocalPreferDarkContentOverWallpaper.current && searchBarColor == SearchBarColors.Auto || searchBarColor == SearchBarColors.Dark,
style = searchBarStyle,
bottomSearchBar = bottomSearchBar, bottomSearchBar = bottomSearchBar,
searchBarOffset = {
(if (searchBarFocused || fixedSearchBar) 0
else searchBarOffset.toInt() * if (bottomSearchBar) -1 else 1)
- (if (bottomSearchBar) with(density) { keyboardFilterBarPadding.toPx() }.toInt() else 0)
},
onKeyboardActionGo = if (launchOnEnter) { onKeyboardActionGo = if (launchOnEnter) {
{ searchVM.launchBestMatchOrAction(context) } { searchVM.launchBestMatchOrAction(context) }
} else null } else null

View File

@ -30,7 +30,6 @@ import androidx.compose.foundation.layout.requiredWidth
import androidx.compose.foundation.layout.safeDrawing import androidx.compose.foundation.layout.safeDrawing
import androidx.compose.foundation.layout.systemBarsPadding import androidx.compose.foundation.layout.systemBarsPadding
import androidx.compose.foundation.layout.windowInsetsPadding import androidx.compose.foundation.layout.windowInsetsPadding
import androidx.compose.foundation.layout.wrapContentHeight
import androidx.compose.foundation.lazy.rememberLazyListState import androidx.compose.foundation.lazy.rememberLazyListState
import androidx.compose.foundation.pager.HorizontalPager import androidx.compose.foundation.pager.HorizontalPager
import androidx.compose.foundation.pager.PagerDefaults import androidx.compose.foundation.pager.PagerDefaults
@ -55,7 +54,6 @@ import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier import androidx.compose.ui.Modifier
import androidx.compose.ui.composed import androidx.compose.ui.composed
import androidx.compose.ui.geometry.Offset import androidx.compose.ui.geometry.Offset
@ -602,16 +600,9 @@ fun PagerScaffold(
LauncherSearchBar( LauncherSearchBar(
modifier = Modifier modifier = Modifier
.fillMaxSize(), .fillMaxSize(),
style = searchBarStyle,
level = { searchBarLevel }, level = { searchBarLevel },
searchBarOffset = { value = { value },
(if (focusSearchBar || fixedSearchBar) 0 else searchBarOffset.value.toInt() * if (bottomSearchBar) 1 else -1) +
with(density) {
(widgetEditModeOffset - if (bottomSearchBar) keyboardFilterBarPadding else 0.dp)
.toPx()
.roundToInt()
}
},
bottomSearchBar = bottomSearchBar,
focused = focusSearchBar, focused = focusSearchBar,
onFocusChange = { onFocusChange = {
if (it) viewModel.openSearch() if (it) viewModel.openSearch()
@ -620,10 +611,16 @@ fun PagerScaffold(
actions = actions, actions = actions,
highlightedAction = searchVM.bestMatch.value as? SearchAction, highlightedAction = searchVM.bestMatch.value as? SearchAction,
isSearchOpen = isSearchOpen, isSearchOpen = isSearchOpen,
value = { value },
onValueChange = { searchVM.search(it) },
darkColors = LocalPreferDarkContentOverWallpaper.current && searchBarColor == SearchBarColors.Auto || searchBarColor == SearchBarColors.Dark, darkColors = LocalPreferDarkContentOverWallpaper.current && searchBarColor == SearchBarColors.Auto || searchBarColor == SearchBarColors.Dark,
style = searchBarStyle, bottomSearchBar = bottomSearchBar,
searchBarOffset = {
(if (focusSearchBar || fixedSearchBar) 0 else searchBarOffset.value.toInt() * if (bottomSearchBar) 1 else -1) +
with(density) {
(widgetEditModeOffset - if (bottomSearchBar) keyboardFilterBarPadding else 0.dp)
.toPx()
.roundToInt()
}
},
onKeyboardActionGo = if (launchOnEnter) { onKeyboardActionGo = if (launchOnEnter) {
{ searchVM.launchBestMatchOrAction(context) } { searchVM.launchBestMatchOrAction(context) }
} else null } else null

View File

@ -58,9 +58,7 @@ import androidx.compose.ui.input.nestedscroll.NestedScrollSource
import androidx.compose.ui.input.pointer.pointerInput import androidx.compose.ui.input.pointer.pointerInput
import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.platform.LocalDensity import androidx.compose.ui.platform.LocalDensity
import androidx.compose.ui.platform.LocalHapticFeedback
import androidx.compose.ui.platform.LocalLayoutDirection import androidx.compose.ui.platform.LocalLayoutDirection
import androidx.compose.ui.platform.LocalSoftwareKeyboardController
import androidx.compose.ui.platform.LocalView import androidx.compose.ui.platform.LocalView
import androidx.compose.ui.res.stringResource import androidx.compose.ui.res.stringResource
import androidx.compose.ui.unit.IntOffset import androidx.compose.ui.unit.IntOffset
@ -580,12 +578,19 @@ fun PullDownScaffold(
LauncherSearchBar( LauncherSearchBar(
modifier = Modifier modifier = Modifier
.fillMaxSize(), .fillMaxSize(),
style = searchBarStyle,
level = { searchBarLevel }, level = { searchBarLevel },
value = { value },
focused = searchBarFocused, focused = searchBarFocused,
onFocusChange = { onFocusChange = {
if (it) viewModel.openSearch() if (it) viewModel.openSearch()
viewModel.setSearchbarFocus(it) viewModel.setSearchbarFocus(it)
}, },
actions = actions,
highlightedAction = searchVM.bestMatch.value as? SearchAction,
isSearchOpen = isSearchOpen,
darkColors = LocalPreferDarkContentOverWallpaper.current && searchBarColor == SearchBarColors.Auto || searchBarColor == SearchBarColors.Dark,
bottomSearchBar = bottomSearchBar,
searchBarOffset = { searchBarOffset = {
(if (searchBarFocused || fixedSearchBar) 0 else searchBarOffset.value.toInt() * (if (bottomSearchBar) 1 else -1)) + (if (searchBarFocused || fixedSearchBar) 0 else searchBarOffset.value.toInt() * (if (bottomSearchBar) 1 else -1)) +
with(density) { with(density) {
@ -594,14 +599,6 @@ fun PullDownScaffold(
.roundToInt() .roundToInt()
} }
}, },
actions = actions,
highlightedAction = searchVM.bestMatch.value as? SearchAction,
isSearchOpen = isSearchOpen,
value = { value },
onValueChange = { searchVM.search(it) },
darkColors = LocalPreferDarkContentOverWallpaper.current && searchBarColor == SearchBarColors.Auto || searchBarColor == SearchBarColors.Dark,
style = searchBarStyle,
bottomSearchBar = bottomSearchBar,
onKeyboardActionGo = if (launchOnEnter) { onKeyboardActionGo = if (launchOnEnter) {
{ searchVM.launchBestMatchOrAction(context) } { searchVM.launchBestMatchOrAction(context) }
} else null } else null

View File

@ -11,9 +11,9 @@ import de.mm20.launcher2.permissions.PermissionsManager
import de.mm20.launcher2.preferences.SearchResultOrder import de.mm20.launcher2.preferences.SearchResultOrder
import de.mm20.launcher2.preferences.search.CalendarSearchSettings import de.mm20.launcher2.preferences.search.CalendarSearchSettings
import de.mm20.launcher2.preferences.search.ContactSearchSettings import de.mm20.launcher2.preferences.search.ContactSearchSettings
import de.mm20.launcher2.preferences.search.FavoritesSettings
import de.mm20.launcher2.preferences.search.FileSearchSettings import de.mm20.launcher2.preferences.search.FileSearchSettings
import de.mm20.launcher2.preferences.search.LocationSearchSettings import de.mm20.launcher2.preferences.search.LocationSearchSettings
import de.mm20.launcher2.preferences.search.SearchFilterSettings
import de.mm20.launcher2.preferences.search.ShortcutSearchSettings import de.mm20.launcher2.preferences.search.ShortcutSearchSettings
import de.mm20.launcher2.preferences.ui.SearchUiSettings import de.mm20.launcher2.preferences.ui.SearchUiSettings
import de.mm20.launcher2.search.AppProfile import de.mm20.launcher2.search.AppProfile
@ -42,7 +42,6 @@ import kotlinx.coroutines.flow.collectLatest
import kotlinx.coroutines.flow.combine import kotlinx.coroutines.flow.combine
import kotlinx.coroutines.flow.distinctUntilChanged import kotlinx.coroutines.flow.distinctUntilChanged
import kotlinx.coroutines.flow.first import kotlinx.coroutines.flow.first
import kotlinx.coroutines.flow.map
import kotlinx.coroutines.flow.shareIn import kotlinx.coroutines.flow.shareIn
import kotlinx.coroutines.flow.stateIn import kotlinx.coroutines.flow.stateIn
import kotlinx.coroutines.launch import kotlinx.coroutines.launch
@ -63,6 +62,7 @@ class SearchVM : ViewModel(), KoinComponent {
private val searchUiSettings: SearchUiSettings by inject() private val searchUiSettings: SearchUiSettings by inject()
private val locationSearchSettings: LocationSearchSettings by inject() private val locationSearchSettings: LocationSearchSettings by inject()
private val devicePoseProvider: DevicePoseProvider by inject() private val devicePoseProvider: DevicePoseProvider by inject()
private val searchFilterSettings: SearchFilterSettings by inject()
val launchOnEnter = searchUiSettings.launchOnEnter val launchOnEnter = searchUiSettings.launchOnEnter
.stateIn(viewModelScope, SharingStarted.Eagerly, false) .stateIn(viewModelScope, SharingStarted.Eagerly, false)
@ -93,7 +93,8 @@ class SearchVM : ViewModel(), KoinComponent {
val showFilters = mutableStateOf(false) val showFilters = mutableStateOf(false)
val filters = mutableStateOf(SearchFilters()) val defaultFilters = searchFilterSettings.defaultFilter.stateIn(viewModelScope, SharingStarted.Eagerly, SearchFilters())
val filters = mutableStateOf(defaultFilters.value)
val separateWorkProfile = searchUiSettings.separateWorkProfile val separateWorkProfile = searchUiSettings.separateWorkProfile
@ -133,6 +134,7 @@ class SearchVM : ViewModel(), KoinComponent {
fun reset() { fun reset() {
closeFilters() closeFilters()
filters.value = defaultFilters.value
search("") search("")
} }
@ -142,6 +144,9 @@ class SearchVM : ViewModel(), KoinComponent {
if (searchQuery.value != query) { if (searchQuery.value != query) {
showFilters.value = false showFilters.value = false
} }
if (query.isEmpty() && searchQuery.value.isNotEmpty()) {
filters.value = defaultFilters.value
}
searchQuery.value = query searchQuery.value = query
isSearchEmpty.value = query.isEmpty() isSearchEmpty.value = query.isEmpty()
hiddenResults.value = emptyList() hiddenResults.value = emptyList()

View File

@ -2,11 +2,8 @@ package de.mm20.launcher2.ui.launcher.search.filters
import androidx.compose.foundation.background import androidx.compose.foundation.background
import androidx.compose.foundation.horizontalScroll import androidx.compose.foundation.horizontalScroll
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.BoxScope
import androidx.compose.foundation.layout.Column import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.fillMaxWidth import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.imePadding import androidx.compose.foundation.layout.imePadding

View File

@ -2,19 +2,13 @@ package de.mm20.launcher2.ui.launcher.searchbar
import androidx.compose.animation.AnimatedVisibility import androidx.compose.animation.AnimatedVisibility
import androidx.compose.animation.core.tween import androidx.compose.animation.core.tween
import androidx.compose.animation.expandVertically
import androidx.compose.animation.fadeIn import androidx.compose.animation.fadeIn
import androidx.compose.animation.fadeOut import androidx.compose.animation.fadeOut
import androidx.compose.animation.scaleIn import androidx.compose.animation.scaleIn
import androidx.compose.animation.scaleOut import androidx.compose.animation.scaleOut
import androidx.compose.animation.shrinkVertically
import androidx.compose.foundation.layout.Box import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.BoxScope
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.WindowInsets import androidx.compose.foundation.layout.WindowInsets
import androidx.compose.foundation.layout.imeAnimationTarget import androidx.compose.foundation.layout.imeAnimationTarget
import androidx.compose.foundation.layout.isImeVisible
import androidx.compose.foundation.layout.offset import androidx.compose.foundation.layout.offset
import androidx.compose.foundation.layout.padding import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.layout.safeDrawing import androidx.compose.foundation.layout.safeDrawing
@ -29,8 +23,6 @@ import androidx.compose.material3.IconButtonDefaults
import androidx.compose.material3.MaterialTheme import androidx.compose.material3.MaterialTheme
import androidx.compose.runtime.Composable import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect import androidx.compose.runtime.LaunchedEffect
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
import androidx.compose.runtime.remember import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier import androidx.compose.ui.Modifier
@ -46,7 +38,6 @@ import de.mm20.launcher2.ui.component.SearchBar
import de.mm20.launcher2.ui.component.SearchBarLevel import de.mm20.launcher2.ui.component.SearchBarLevel
import de.mm20.launcher2.ui.launcher.search.SearchVM import de.mm20.launcher2.ui.launcher.search.SearchVM
import de.mm20.launcher2.ui.launcher.search.filters.KeyboardFilterBar import de.mm20.launcher2.ui.launcher.search.filters.KeyboardFilterBar
import de.mm20.launcher2.ui.launcher.sheets.LocalBottomSheetManager
@Composable @Composable
fun LauncherSearchBar( fun LauncherSearchBar(
@ -54,7 +45,6 @@ fun LauncherSearchBar(
style: SearchBarStyle, style: SearchBarStyle,
level: () -> SearchBarLevel, level: () -> SearchBarLevel,
value: () -> String, value: () -> String,
onValueChange: (String) -> Unit,
focused: Boolean, focused: Boolean,
onFocusChange: (Boolean) -> Unit, onFocusChange: (Boolean) -> Unit,
actions: List<SearchAction>, actions: List<SearchAction>,
@ -85,7 +75,9 @@ fun LauncherSearchBar(
.windowInsetsPadding(WindowInsets.safeDrawing) .windowInsetsPadding(WindowInsets.safeDrawing)
.padding(8.dp) .padding(8.dp)
.offset { IntOffset(0, searchBarOffset()) }, .offset { IntOffset(0, searchBarOffset()) },
style = style, level = level(), value = _value, onValueChange = onValueChange, style = style, level = level(), value = _value, onValueChange = {
searchVM.search(it)
},
reverse = bottomSearchBar, reverse = bottomSearchBar,
darkColors = darkColors, darkColors = darkColors,
menu = { menu = {
@ -118,7 +110,9 @@ fun LauncherSearchBar(
} }
} }
} }
SearchBarMenu(searchBarValue = _value, onSearchBarValueChange = onValueChange) SearchBarMenu(searchBarValue = _value, onInputClear = {
searchVM.reset()
})
}, },
actions = { actions = {
SearchBarActions( SearchBarActions(

View File

@ -38,7 +38,7 @@ import de.mm20.launcher2.ui.settings.SettingsActivity
@Composable @Composable
fun RowScope.SearchBarMenu( fun RowScope.SearchBarMenu(
searchBarValue: String, searchBarValue: String,
onSearchBarValueChange: (newValue: String) -> Unit, onInputClear: () -> Unit,
) { ) {
val context = LocalContext.current val context = LocalContext.current
var showOverflowMenu by remember { mutableStateOf(false) } var showOverflowMenu by remember { mutableStateOf(false) }
@ -47,7 +47,7 @@ fun RowScope.SearchBarMenu(
val widgetsVM: WidgetsVM = viewModel() val widgetsVM: WidgetsVM = viewModel()
IconButton(onClick = { IconButton(onClick = {
if (searchBarValue.isNotBlank()) onSearchBarValueChange("") if (searchBarValue.isNotBlank()) onInputClear()
else showOverflowMenu = true else showOverflowMenu = true
}) { }) {
Icon( Icon(

View File

@ -1,6 +1,7 @@
plugins { plugins {
alias(libs.plugins.android.library) alias(libs.plugins.android.library)
alias(libs.plugins.kotlin.android) alias(libs.plugins.kotlin.android)
alias(libs.plugins.kotlin.plugin.serialization)
} }
android { android {

View File

@ -1,7 +1,9 @@
package de.mm20.launcher2.search package de.mm20.launcher2.search
import de.mm20.launcher2.ktx.toInt import de.mm20.launcher2.ktx.toInt
import kotlinx.serialization.Serializable
@Serializable
data class SearchFilters( data class SearchFilters(
val allowNetwork: Boolean = false, val allowNetwork: Boolean = false,
val hiddenItems: Boolean = false, val hiddenItems: Boolean = false,

View File

@ -2,6 +2,7 @@ package de.mm20.launcher2.preferences
import android.content.Context import android.content.Context
import de.mm20.launcher2.preferences.search.LocationSearchSettings import de.mm20.launcher2.preferences.search.LocationSearchSettings
import de.mm20.launcher2.search.SearchFilters
import kotlinx.serialization.SerialName import kotlinx.serialization.SerialName
import kotlinx.serialization.Serializable import kotlinx.serialization.Serializable
@ -144,6 +145,23 @@ data class LauncherSettingsData internal constructor(
val locationSearchShowPositionOnMap: Boolean = false, val locationSearchShowPositionOnMap: Boolean = false,
val locationSearchThemeMap: Boolean = true, val locationSearchThemeMap: Boolean = true,
val searchFilter: SearchFilters = SearchFilters(),
val searchFilterBar: Boolean = true,
val searchFilterBarItems: List<KeyboardFilterBarItem> = listOf(
KeyboardFilterBarItem.OnlineResults,
KeyboardFilterBarItem.Apps,
KeyboardFilterBarItem.Shortcuts,
KeyboardFilterBarItem.Events,
KeyboardFilterBarItem.Contacts,
KeyboardFilterBarItem.Files,
KeyboardFilterBarItem.Places,
KeyboardFilterBarItem.Articles,
KeyboardFilterBarItem.Websites,
KeyboardFilterBarItem.Places,
KeyboardFilterBarItem.Tools,
KeyboardFilterBarItem.HiddenResults,
),
) { ) {
constructor( constructor(
@ -376,4 +394,19 @@ data class LatLon(
data class ProviderSettings( data class ProviderSettings(
val locationId: String? = null, val locationId: String? = null,
val locationName: String? = null, val locationName: String? = null,
) )
@Serializable
enum class KeyboardFilterBarItem {
@SerialName("online") OnlineResults,
@SerialName("apps") Apps,
@SerialName("websites") Websites,
@SerialName("articles") Articles,
@SerialName("places") Places,
@SerialName("files") Files,
@SerialName("shortcuts") Shortcuts,
@SerialName("contacts") Contacts,
@SerialName("events") Events,
@SerialName("tools") Tools,
@SerialName("hidden") HiddenResults,
}

View File

@ -9,6 +9,7 @@ import de.mm20.launcher2.preferences.search.FavoritesSettings
import de.mm20.launcher2.preferences.search.FileSearchSettings import de.mm20.launcher2.preferences.search.FileSearchSettings
import de.mm20.launcher2.preferences.search.LocationSearchSettings import de.mm20.launcher2.preferences.search.LocationSearchSettings
import de.mm20.launcher2.preferences.search.RankingSettings import de.mm20.launcher2.preferences.search.RankingSettings
import de.mm20.launcher2.preferences.search.SearchFilterSettings
import de.mm20.launcher2.preferences.search.ShortcutSearchSettings import de.mm20.launcher2.preferences.search.ShortcutSearchSettings
import de.mm20.launcher2.preferences.search.UnitConverterSettings import de.mm20.launcher2.preferences.search.UnitConverterSettings
import de.mm20.launcher2.preferences.search.WebsiteSearchSettings import de.mm20.launcher2.preferences.search.WebsiteSearchSettings
@ -49,4 +50,5 @@ val preferencesModule = module {
factory { CalculatorSearchSettings(get()) } factory { CalculatorSearchSettings(get()) }
factory { ClockWidgetSettings(get()) } factory { ClockWidgetSettings(get()) }
factory { LocationSearchSettings(get()) } factory { LocationSearchSettings(get()) }
factory { SearchFilterSettings(get()) }
} }

View File

@ -0,0 +1,11 @@
package de.mm20.launcher2.preferences.search
import de.mm20.launcher2.preferences.LauncherDataStore
import kotlinx.coroutines.flow.map
class SearchFilterSettings internal constructor(
private val launcherDataStore: LauncherDataStore,
) {
val defaultFilter
get() = launcherDataStore.data.map { it.searchFilter }
}