Restructure calendar widget settings
This commit is contained in:
parent
bf29ce6f08
commit
cc9bff436a
@ -44,6 +44,7 @@ import androidx.compose.ui.graphics.Color
|
|||||||
import androidx.compose.ui.graphics.toArgb
|
import androidx.compose.ui.graphics.toArgb
|
||||||
import androidx.compose.ui.platform.LocalContext
|
import androidx.compose.ui.platform.LocalContext
|
||||||
import androidx.compose.ui.res.stringResource
|
import androidx.compose.ui.res.stringResource
|
||||||
|
import androidx.compose.ui.text.style.TextDecoration
|
||||||
import androidx.compose.ui.text.style.TextOverflow
|
import androidx.compose.ui.text.style.TextOverflow
|
||||||
import androidx.compose.ui.unit.dp
|
import androidx.compose.ui.unit.dp
|
||||||
import androidx.compose.ui.unit.roundToIntRect
|
import androidx.compose.ui.unit.roundToIntRect
|
||||||
@ -121,7 +122,13 @@ fun CalendarItem(
|
|||||||
this@AnimatedContent
|
this@AnimatedContent
|
||||||
),
|
),
|
||||||
text = calendar.labelOverride ?: calendar.label,
|
text = calendar.labelOverride ?: calendar.label,
|
||||||
style = MaterialTheme.typography.titleMedium
|
style = MaterialTheme.typography.titleMedium,
|
||||||
|
maxLines = 1,
|
||||||
|
textDecoration = if (calendar.isCompleted == true) {
|
||||||
|
TextDecoration.LineThrough
|
||||||
|
} else {
|
||||||
|
TextDecoration.None
|
||||||
|
}
|
||||||
)
|
)
|
||||||
if (calendar.calendarName != null) {
|
if (calendar.calendarName != null) {
|
||||||
Text(
|
Text(
|
||||||
@ -300,7 +307,13 @@ fun CalendarItem(
|
|||||||
this@AnimatedContent
|
this@AnimatedContent
|
||||||
),
|
),
|
||||||
text = calendar.labelOverride ?: calendar.label,
|
text = calendar.labelOverride ?: calendar.label,
|
||||||
style = MaterialTheme.typography.titleSmall
|
style = MaterialTheme.typography.titleSmall,
|
||||||
|
maxLines = 1,
|
||||||
|
textDecoration = if (calendar.isCompleted == true) {
|
||||||
|
TextDecoration.LineThrough
|
||||||
|
} else {
|
||||||
|
TextDecoration.None
|
||||||
|
}
|
||||||
)
|
)
|
||||||
Text(
|
Text(
|
||||||
modifier = Modifier
|
modifier = Modifier
|
||||||
|
|||||||
@ -12,6 +12,7 @@ import androidx.activity.result.contract.ActivityResultContracts
|
|||||||
import androidx.appcompat.app.AppCompatActivity
|
import androidx.appcompat.app.AppCompatActivity
|
||||||
import androidx.browser.customtabs.CustomTabColorSchemeParams
|
import androidx.browser.customtabs.CustomTabColorSchemeParams
|
||||||
import androidx.browser.customtabs.CustomTabsIntent
|
import androidx.browser.customtabs.CustomTabsIntent
|
||||||
|
import androidx.compose.animation.AnimatedVisibility
|
||||||
import androidx.compose.foundation.background
|
import androidx.compose.foundation.background
|
||||||
import androidx.compose.foundation.gestures.awaitEachGesture
|
import androidx.compose.foundation.gestures.awaitEachGesture
|
||||||
import androidx.compose.foundation.gestures.awaitFirstDown
|
import androidx.compose.foundation.gestures.awaitFirstDown
|
||||||
@ -34,6 +35,7 @@ import androidx.compose.material.icons.rounded.Link
|
|||||||
import androidx.compose.material.icons.rounded.LinkOff
|
import androidx.compose.material.icons.rounded.LinkOff
|
||||||
import androidx.compose.material.icons.rounded.OpenInNew
|
import androidx.compose.material.icons.rounded.OpenInNew
|
||||||
import androidx.compose.material3.ButtonDefaults
|
import androidx.compose.material3.ButtonDefaults
|
||||||
|
import androidx.compose.material3.CheckboxDefaults
|
||||||
import androidx.compose.material3.HorizontalDivider
|
import androidx.compose.material3.HorizontalDivider
|
||||||
import androidx.compose.material3.Icon
|
import androidx.compose.material3.Icon
|
||||||
import androidx.compose.material3.MaterialTheme
|
import androidx.compose.material3.MaterialTheme
|
||||||
@ -42,7 +44,6 @@ import androidx.compose.material3.OutlinedCard
|
|||||||
import androidx.compose.material3.Text
|
import androidx.compose.material3.Text
|
||||||
import androidx.compose.material3.TextButton
|
import androidx.compose.material3.TextButton
|
||||||
import androidx.compose.runtime.Composable
|
import androidx.compose.runtime.Composable
|
||||||
import androidx.compose.runtime.LaunchedEffect
|
|
||||||
import androidx.compose.runtime.collectAsState
|
import androidx.compose.runtime.collectAsState
|
||||||
import androidx.compose.runtime.getValue
|
import androidx.compose.runtime.getValue
|
||||||
import androidx.compose.runtime.mutableStateOf
|
import androidx.compose.runtime.mutableStateOf
|
||||||
@ -52,22 +53,26 @@ import androidx.compose.runtime.setValue
|
|||||||
import androidx.compose.ui.Alignment
|
import androidx.compose.ui.Alignment
|
||||||
import androidx.compose.ui.Modifier
|
import androidx.compose.ui.Modifier
|
||||||
import androidx.compose.ui.draw.clip
|
import androidx.compose.ui.draw.clip
|
||||||
|
import androidx.compose.ui.graphics.Color
|
||||||
import androidx.compose.ui.graphics.toArgb
|
import androidx.compose.ui.graphics.toArgb
|
||||||
import androidx.compose.ui.input.pointer.PointerEventPass
|
import androidx.compose.ui.input.pointer.PointerEventPass
|
||||||
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.LocalLifecycleOwner
|
|
||||||
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 androidx.compose.ui.unit.dp
|
import androidx.compose.ui.unit.dp
|
||||||
import androidx.compose.ui.unit.isUnspecified
|
import androidx.compose.ui.unit.isUnspecified
|
||||||
import androidx.core.net.toUri
|
import androidx.core.net.toUri
|
||||||
|
import androidx.lifecycle.compose.LocalLifecycleOwner
|
||||||
import de.mm20.launcher2.calendar.CalendarRepository
|
import de.mm20.launcher2.calendar.CalendarRepository
|
||||||
import de.mm20.launcher2.calendar.providers.CalendarList
|
|
||||||
import de.mm20.launcher2.crashreporter.CrashReporter
|
import de.mm20.launcher2.crashreporter.CrashReporter
|
||||||
import de.mm20.launcher2.ktx.isAtLeastApiLevel
|
import de.mm20.launcher2.ktx.isAtLeastApiLevel
|
||||||
import de.mm20.launcher2.permissions.PermissionGroup
|
import de.mm20.launcher2.permissions.PermissionGroup
|
||||||
import de.mm20.launcher2.permissions.PermissionsManager
|
import de.mm20.launcher2.permissions.PermissionsManager
|
||||||
|
import de.mm20.launcher2.plugin.PluginRepository
|
||||||
|
import de.mm20.launcher2.plugin.PluginType
|
||||||
|
import de.mm20.launcher2.search.calendar.CalendarListType
|
||||||
|
import de.mm20.launcher2.themes.atTone
|
||||||
import de.mm20.launcher2.ui.R
|
import de.mm20.launcher2.ui.R
|
||||||
import de.mm20.launcher2.ui.base.LocalAppWidgetHost
|
import de.mm20.launcher2.ui.base.LocalAppWidgetHost
|
||||||
import de.mm20.launcher2.ui.component.BottomSheetDialog
|
import de.mm20.launcher2.ui.component.BottomSheetDialog
|
||||||
@ -383,7 +388,7 @@ fun ColumnScope.ConfigureAppWidget(
|
|||||||
val minHeight = if (widgetInfo.minResizeHeight in 1..widgetInfo.minHeight) {
|
val minHeight = if (widgetInfo.minResizeHeight in 1..widgetInfo.minHeight) {
|
||||||
widgetInfo.minResizeHeight.toDp()
|
widgetInfo.minResizeHeight.toDp()
|
||||||
} else {
|
} else {
|
||||||
widgetInfo.minHeight.toDp()
|
widgetInfo.minHeight.toDp()
|
||||||
}
|
}
|
||||||
|
|
||||||
DragResizeHandle(
|
DragResizeHandle(
|
||||||
@ -503,66 +508,103 @@ fun ColumnScope.ConfigureCalendarWidget(
|
|||||||
) {
|
) {
|
||||||
val calendarRepository: CalendarRepository = get()
|
val calendarRepository: CalendarRepository = get()
|
||||||
val permissionsManager: PermissionsManager = get()
|
val permissionsManager: PermissionsManager = get()
|
||||||
|
val pluginRepository: PluginRepository = get()
|
||||||
val calendars by remember {
|
val calendars by remember {
|
||||||
calendarRepository.getCalendars().map {
|
calendarRepository.getCalendars().map {
|
||||||
it.sortedBy { it.name }
|
it.sortedBy { it.name }
|
||||||
}
|
}
|
||||||
}.collectAsState(null)
|
}.collectAsState(null)
|
||||||
|
val plugins by remember {
|
||||||
|
pluginRepository.findMany(
|
||||||
|
type = PluginType.Calendar,
|
||||||
|
enabled = true,
|
||||||
|
)
|
||||||
|
}.collectAsState(emptyList())
|
||||||
|
|
||||||
val hasPermission by remember {
|
val hasPermission by remember {
|
||||||
permissionsManager.hasPermission(PermissionGroup.Calendar)
|
permissionsManager.hasPermission(PermissionGroup.Calendar)
|
||||||
}.collectAsState(true)
|
}.collectAsState(true)
|
||||||
|
|
||||||
OutlinedCard {
|
val hasTasks = remember(calendars) {
|
||||||
Column(
|
calendars?.any { it.types.contains(CalendarListType.Tasks) } == true
|
||||||
modifier = Modifier.fillMaxWidth()
|
|
||||||
) {
|
|
||||||
SwitchPreference(
|
|
||||||
title = stringResource(R.string.preference_calendar_hide_allday),
|
|
||||||
iconPadding = false,
|
|
||||||
value = !widget.config.allDayEvents,
|
|
||||||
onValueChanged = {
|
|
||||||
onWidgetUpdated(widget.copy(config = widget.config.copy(allDayEvents = !it)))
|
|
||||||
}
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
Text(
|
|
||||||
modifier = Modifier.padding(top = 16.dp, bottom = 4.dp),
|
AnimatedVisibility(hasTasks) {
|
||||||
style = MaterialTheme.typography.titleSmall,
|
|
||||||
color = MaterialTheme.colorScheme.secondary,
|
|
||||||
text = stringResource(R.string.preference_calendar_calendars)
|
|
||||||
)
|
|
||||||
val context = LocalLifecycleOwner.current as AppCompatActivity
|
|
||||||
val excludedCalendars = remember(widget.config) {
|
|
||||||
widget.config.excludedCalendarIds ?: widget.config.legacyExcludedCalendarIds?.map { "local:$it" } ?: emptyList()
|
|
||||||
}
|
|
||||||
if (calendars?.isNotEmpty() == true) {
|
|
||||||
OutlinedCard {
|
OutlinedCard {
|
||||||
Column(
|
Column(
|
||||||
modifier = Modifier.fillMaxWidth()
|
modifier = Modifier.fillMaxWidth()
|
||||||
) {
|
) {
|
||||||
for ((i, calendar) in calendars!!.withIndex()) {
|
SwitchPreference(
|
||||||
if (i > 0) HorizontalDivider()
|
title = stringResource(R.string.preference_calendar_hide_completed),
|
||||||
CheckboxPreference(
|
iconPadding = false,
|
||||||
title = calendar.name,
|
value = !widget.config.completedTasks,
|
||||||
summary = calendar.owner,
|
onValueChanged = {
|
||||||
iconPadding = false,
|
onWidgetUpdated(widget.copy(config = widget.config.copy(completedTasks = !it)))
|
||||||
value = excludedCalendars.contains(calendar.id) != true,
|
}
|
||||||
onValueChanged = {
|
)
|
||||||
onWidgetUpdated(
|
}
|
||||||
widget.copy(
|
}
|
||||||
config = widget.config.copy(
|
}
|
||||||
excludedCalendarIds = if (it) {
|
val context = LocalLifecycleOwner.current as AppCompatActivity
|
||||||
excludedCalendars - calendar.id
|
val excludedCalendars = remember(widget.config) {
|
||||||
} else {
|
widget.config.excludedCalendarIds
|
||||||
excludedCalendars + calendar.id
|
?: widget.config.legacyExcludedCalendarIds?.map { "local:$it" } ?: emptyList()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
val groups = remember(calendars) {
|
||||||
|
calendars?.groupBy { it.providerId }?.entries
|
||||||
|
}
|
||||||
|
|
||||||
|
if (groups?.isNotEmpty() == true) {
|
||||||
|
for (group in groups) {
|
||||||
|
val pluginName = remember(plugins, group.key) {
|
||||||
|
if (group.key == "local") context.getString(R.string.preference_calendar_calendars)
|
||||||
|
else plugins.find { it.authority == group.key }?.label
|
||||||
|
}
|
||||||
|
if (pluginName != null) {
|
||||||
|
Text(
|
||||||
|
modifier = Modifier.padding(top = 16.dp, bottom = 4.dp),
|
||||||
|
style = MaterialTheme.typography.titleSmall,
|
||||||
|
color = MaterialTheme.colorScheme.secondary,
|
||||||
|
text = pluginName
|
||||||
|
)
|
||||||
|
}
|
||||||
|
OutlinedCard {
|
||||||
|
Column(
|
||||||
|
modifier = Modifier.fillMaxWidth()
|
||||||
|
) {
|
||||||
|
for ((i, calendar) in group.value.withIndex()) {
|
||||||
|
if (i > 0) HorizontalDivider()
|
||||||
|
CheckboxPreference(
|
||||||
|
title = calendar.name,
|
||||||
|
summary = calendar.owner,
|
||||||
|
iconPadding = false,
|
||||||
|
value = !excludedCalendars.contains(calendar.id),
|
||||||
|
onValueChanged = {
|
||||||
|
onWidgetUpdated(
|
||||||
|
widget.copy(
|
||||||
|
config = widget.config.copy(
|
||||||
|
excludedCalendarIds = if (it) {
|
||||||
|
excludedCalendars - calendar.id
|
||||||
|
} else {
|
||||||
|
excludedCalendars + calendar.id
|
||||||
|
}
|
||||||
|
)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
},
|
||||||
|
checkboxColors = CheckboxDefaults.colors(
|
||||||
|
checkedColor = if (calendar.color == 0) MaterialTheme.colorScheme.primary
|
||||||
|
else Color(
|
||||||
|
calendar.color.atTone(if (LocalDarkTheme.current) 80 else 40)
|
||||||
|
),
|
||||||
|
checkmarkColor = if (calendar.color == 0) MaterialTheme.colorScheme.onPrimary
|
||||||
|
else Color(
|
||||||
|
calendar.color.atTone(if (LocalDarkTheme.current) 20 else 100)
|
||||||
|
)
|
||||||
)
|
)
|
||||||
}
|
)
|
||||||
)
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -208,7 +208,8 @@ fun CalendarWidget(
|
|||||||
),
|
),
|
||||||
onClick = {
|
onClick = {
|
||||||
viewModel.showAllEvents()
|
viewModel.showAllEvents()
|
||||||
}
|
},
|
||||||
|
modifier = Modifier.padding(top = 8.dp)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
if (nextEvents.isNotEmpty()) {
|
if (nextEvents.isNotEmpty()) {
|
||||||
@ -263,10 +264,11 @@ fun CalendarWidget(
|
|||||||
@Composable
|
@Composable
|
||||||
private fun Info(
|
private fun Info(
|
||||||
text: String,
|
text: String,
|
||||||
|
modifier: Modifier = Modifier,
|
||||||
onClick: (() -> Unit)? = null,
|
onClick: (() -> Unit)? = null,
|
||||||
) {
|
) {
|
||||||
Box(
|
Box(
|
||||||
modifier = Modifier
|
modifier = modifier
|
||||||
.fillMaxWidth()
|
.fillMaxWidth()
|
||||||
.clip(MaterialTheme.shapes.small)
|
.clip(MaterialTheme.shapes.small)
|
||||||
.border(1.dp, MaterialTheme.colorScheme.outlineVariant, MaterialTheme.shapes.small)
|
.border(1.dp, MaterialTheme.colorScheme.outlineVariant, MaterialTheme.shapes.small)
|
||||||
|
|||||||
@ -176,7 +176,10 @@ class CalendarWidgetVM : ViewModel(), KoinComponent {
|
|||||||
maxVisibility = VisibilityLevel.SearchOnly,
|
maxVisibility = VisibilityLevel.SearchOnly,
|
||||||
limit = 9999,
|
limit = 9999,
|
||||||
).collectLatest { hidden ->
|
).collectLatest { hidden ->
|
||||||
upcomingEvents = events.filter { !hidden.contains(it.key) }.sortedBy { it.startTime ?: it.endTime }
|
upcomingEvents = events
|
||||||
|
.filter {
|
||||||
|
!hidden.contains(it.key) && !(!config.completedTasks && it.isCompleted == true)
|
||||||
|
}.sortedBy { it.startTime ?: it.endTime }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -1,20 +1,19 @@
|
|||||||
package de.mm20.launcher2.ui.settings.calendarsearch
|
package de.mm20.launcher2.ui.settings.calendarsearch
|
||||||
|
|
||||||
import android.app.PendingIntent
|
import android.app.PendingIntent
|
||||||
|
import android.util.Log
|
||||||
import androidx.appcompat.app.AppCompatActivity
|
import androidx.appcompat.app.AppCompatActivity
|
||||||
import androidx.compose.animation.AnimatedVisibility
|
import androidx.compose.animation.AnimatedVisibility
|
||||||
import androidx.compose.foundation.layout.padding
|
import androidx.compose.foundation.layout.padding
|
||||||
import androidx.compose.foundation.layout.wrapContentHeight
|
|
||||||
import androidx.compose.foundation.layout.wrapContentWidth
|
|
||||||
import androidx.compose.foundation.lazy.LazyColumn
|
import androidx.compose.foundation.lazy.LazyColumn
|
||||||
import androidx.compose.foundation.lazy.items
|
import androidx.compose.foundation.lazy.items
|
||||||
import androidx.compose.material.icons.Icons
|
import androidx.compose.material.icons.Icons
|
||||||
|
import androidx.compose.material.icons.rounded.CalendarToday
|
||||||
|
import androidx.compose.material.icons.rounded.Checklist
|
||||||
import androidx.compose.material.icons.rounded.ErrorOutline
|
import androidx.compose.material.icons.rounded.ErrorOutline
|
||||||
import androidx.compose.material3.AlertDialogDefaults
|
|
||||||
import androidx.compose.material3.BasicAlertDialog
|
|
||||||
import androidx.compose.material3.CheckboxDefaults
|
import androidx.compose.material3.CheckboxDefaults
|
||||||
import androidx.compose.material3.MaterialTheme
|
import androidx.compose.material3.MaterialTheme
|
||||||
import androidx.compose.material3.Surface
|
import androidx.compose.material3.ModalBottomSheet
|
||||||
import androidx.compose.material3.Text
|
import androidx.compose.material3.Text
|
||||||
import androidx.compose.material3.TextButton
|
import androidx.compose.material3.TextButton
|
||||||
import androidx.compose.runtime.Composable
|
import androidx.compose.runtime.Composable
|
||||||
@ -35,14 +34,15 @@ import androidx.lifecycle.viewmodel.compose.viewModel
|
|||||||
import de.mm20.launcher2.crashreporter.CrashReporter
|
import de.mm20.launcher2.crashreporter.CrashReporter
|
||||||
import de.mm20.launcher2.ktx.sendWithBackgroundPermission
|
import de.mm20.launcher2.ktx.sendWithBackgroundPermission
|
||||||
import de.mm20.launcher2.plugin.PluginState
|
import de.mm20.launcher2.plugin.PluginState
|
||||||
|
import de.mm20.launcher2.search.calendar.CalendarListType
|
||||||
import de.mm20.launcher2.themes.atTone
|
import de.mm20.launcher2.themes.atTone
|
||||||
import de.mm20.launcher2.ui.R
|
import de.mm20.launcher2.ui.R
|
||||||
import de.mm20.launcher2.ui.component.Banner
|
import de.mm20.launcher2.ui.component.Banner
|
||||||
import de.mm20.launcher2.ui.component.MissingPermissionBanner
|
import de.mm20.launcher2.ui.component.MissingPermissionBanner
|
||||||
import de.mm20.launcher2.ui.component.preferences.CheckboxPreference
|
import de.mm20.launcher2.ui.component.preferences.CheckboxPreference
|
||||||
|
import de.mm20.launcher2.ui.component.preferences.PreferenceCategory
|
||||||
import de.mm20.launcher2.ui.component.preferences.PreferenceScreen
|
import de.mm20.launcher2.ui.component.preferences.PreferenceScreen
|
||||||
import de.mm20.launcher2.ui.component.preferences.PreferenceWithSwitch
|
import de.mm20.launcher2.ui.component.preferences.PreferenceWithSwitch
|
||||||
import de.mm20.launcher2.ui.component.preferences.SwitchPreference
|
|
||||||
import de.mm20.launcher2.ui.locals.LocalDarkTheme
|
import de.mm20.launcher2.ui.locals.LocalDarkTheme
|
||||||
|
|
||||||
@Composable
|
@Composable
|
||||||
@ -76,7 +76,7 @@ fun CalendarSearchSettingsScreen() {
|
|||||||
val selectedCalendars = remember(excludedCalendars, calendarLists) {
|
val selectedCalendars = remember(excludedCalendars, calendarLists) {
|
||||||
calendarLists?.count { it.providerId == "local" }
|
calendarLists?.count { it.providerId == "local" }
|
||||||
?.minus(excludedCalendars.count {
|
?.minus(excludedCalendars.count {
|
||||||
it.startsWith("local")
|
it.startsWith("local:")
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
PreferenceWithSwitch(
|
PreferenceWithSwitch(
|
||||||
@ -117,7 +117,7 @@ fun CalendarSearchSettingsScreen() {
|
|||||||
calendarLists?.count { it.providerId == plugin.plugin.authority }
|
calendarLists?.count { it.providerId == plugin.plugin.authority }
|
||||||
?.minus(excludedCalendars.count {
|
?.minus(excludedCalendars.count {
|
||||||
it.startsWith(
|
it.startsWith(
|
||||||
plugin.plugin.authority
|
"${plugin.plugin.authority}:"
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
@ -126,7 +126,7 @@ fun CalendarSearchSettingsScreen() {
|
|||||||
enabled = state is PluginState.Ready,
|
enabled = state is PluginState.Ready,
|
||||||
summary = (state as? PluginState.SetupRequired)?.message
|
summary = (state as? PluginState.SetupRequired)?.message
|
||||||
?: if (selectedCalendars != null && calendarLists != null) "$selectedCalendars lists selected"
|
?: if (selectedCalendars != null && calendarLists != null) "$selectedCalendars lists selected"
|
||||||
else (state as? PluginState.Ready)?.text ?: plugin.plugin.description,
|
else (state as? PluginState.Ready)?.text ?: plugin.plugin.description,
|
||||||
switchValue = enabledProviders.contains(plugin.plugin.authority) && state is PluginState.Ready,
|
switchValue = enabledProviders.contains(plugin.plugin.authority) && state is PluginState.Ready,
|
||||||
onSwitchChanged = {
|
onSwitchChanged = {
|
||||||
viewModel.setProviderEnabled(plugin.plugin.authority, it)
|
viewModel.setProviderEnabled(plugin.plugin.authority, it)
|
||||||
@ -139,6 +139,8 @@ fun CalendarSearchSettingsScreen() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Log.d("MM20", "${calendarLists.toString()}")
|
||||||
|
|
||||||
val dialogCalendarLists by remember {
|
val dialogCalendarLists by remember {
|
||||||
derivedStateOf {
|
derivedStateOf {
|
||||||
if (showDialogForProvider == null) null
|
if (showDialogForProvider == null) null
|
||||||
@ -147,39 +149,41 @@ fun CalendarSearchSettingsScreen() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (showDialogForProvider != null && dialogCalendarLists != null) {
|
if (showDialogForProvider != null && dialogCalendarLists != null) {
|
||||||
BasicAlertDialog(
|
ModalBottomSheet(
|
||||||
onDismissRequest = {
|
onDismissRequest = {
|
||||||
showDialogForProvider = null
|
showDialogForProvider = null
|
||||||
},
|
},
|
||||||
) {
|
) {
|
||||||
Surface(
|
val groups = remember(dialogCalendarLists) {
|
||||||
modifier = Modifier
|
dialogCalendarLists!!.groupBy { it.owner }.entries.sortedBy { it.key }
|
||||||
.wrapContentWidth()
|
}
|
||||||
.wrapContentHeight(),
|
|
||||||
shape = MaterialTheme.shapes.large,
|
LazyColumn {
|
||||||
tonalElevation = AlertDialogDefaults.TonalElevation
|
items(groups) {
|
||||||
) {
|
PreferenceCategory(
|
||||||
LazyColumn {
|
title = it.key,
|
||||||
items(dialogCalendarLists ?: emptyList()) {
|
iconPadding = false,
|
||||||
CheckboxPreference(
|
) {
|
||||||
title = it.name,
|
for (list in it.value) {
|
||||||
summary = it.owner,
|
CheckboxPreference(
|
||||||
iconPadding = false,
|
title = list.name,
|
||||||
value = it.id !in excludedCalendars,
|
iconPadding = false,
|
||||||
onValueChanged = { value ->
|
value = list.id !in excludedCalendars,
|
||||||
viewModel.setCalendarExcluded(it.id, !value)
|
onValueChanged = { value ->
|
||||||
},
|
viewModel.setCalendarExcluded(list.id, !value)
|
||||||
checkboxColors = CheckboxDefaults.colors(
|
},
|
||||||
checkedColor = if (it.color == 0) MaterialTheme.colorScheme.primary
|
checkboxColors = CheckboxDefaults.colors(
|
||||||
else Color(
|
checkedColor = if (list.color == 0) MaterialTheme.colorScheme.primary
|
||||||
it.color.atTone(if (LocalDarkTheme.current) 80 else 40)
|
else Color(
|
||||||
),
|
list.color.atTone(if (LocalDarkTheme.current) 80 else 40)
|
||||||
checkmarkColor = if (it.color == 0) MaterialTheme.colorScheme.onPrimary
|
),
|
||||||
else Color(
|
checkmarkColor = if (list.color == 0) MaterialTheme.colorScheme.onPrimary
|
||||||
it.color.atTone(if (LocalDarkTheme.current) 20 else 100)
|
else Color(
|
||||||
|
list.color.atTone(if (LocalDarkTheme.current) 20 else 100)
|
||||||
|
)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
)
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -627,6 +627,7 @@
|
|||||||
<string name="preference_google_signin_summary">Sign in to search Google Drive</string>
|
<string name="preference_google_signin_summary">Sign in to search Google Drive</string>
|
||||||
<string name="preference_calendar_calendars">Calendars</string>
|
<string name="preference_calendar_calendars">Calendars</string>
|
||||||
<string name="preference_calendar_hide_allday">Hide all-day events</string>
|
<string name="preference_calendar_hide_allday">Hide all-day events</string>
|
||||||
|
<string name="preference_calendar_hide_completed">Hide completed tasks</string>
|
||||||
<string name="preference_screen_buildinfo">Build information</string>
|
<string name="preference_screen_buildinfo">Build information</string>
|
||||||
<string name="preference_screen_buildinfo_summary">More information about this build of this app</string>
|
<string name="preference_screen_buildinfo_summary">More information about this build of this app</string>
|
||||||
<string name="preference_search_bar_style">Style</string>
|
<string name="preference_search_bar_style">Style</string>
|
||||||
|
|||||||
@ -6,6 +6,7 @@ import android.provider.CalendarContract
|
|||||||
import androidx.core.database.getStringOrNull
|
import androidx.core.database.getStringOrNull
|
||||||
import de.mm20.launcher2.permissions.PermissionGroup
|
import de.mm20.launcher2.permissions.PermissionGroup
|
||||||
import de.mm20.launcher2.search.CalendarEvent
|
import de.mm20.launcher2.search.CalendarEvent
|
||||||
|
import de.mm20.launcher2.search.calendar.CalendarListType
|
||||||
import kotlinx.coroutines.Dispatchers
|
import kotlinx.coroutines.Dispatchers
|
||||||
import kotlinx.coroutines.withContext
|
import kotlinx.coroutines.withContext
|
||||||
import java.util.Calendar
|
import java.util.Calendar
|
||||||
@ -201,6 +202,7 @@ class AndroidCalendarProvider(
|
|||||||
name = cursor.getStringOrNull(5) ?: cursor.getStringOrNull(1) ?: "",
|
name = cursor.getStringOrNull(5) ?: cursor.getStringOrNull(1) ?: "",
|
||||||
owner = cursor.getStringOrNull(2),
|
owner = cursor.getStringOrNull(2),
|
||||||
color = cursor.getInt(3),
|
color = cursor.getInt(3),
|
||||||
|
types = listOf(CalendarListType.Calendar),
|
||||||
providerId = "local",
|
providerId = "local",
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|||||||
@ -15,6 +15,9 @@ data class CalendarWidgetConfig(
|
|||||||
val legacyExcludedCalendarIds: List<Long>? = null,
|
val legacyExcludedCalendarIds: List<Long>? = null,
|
||||||
@SerialName("excludedCalendars")
|
@SerialName("excludedCalendars")
|
||||||
val excludedCalendarIds: List<String>? = null,
|
val excludedCalendarIds: List<String>? = null,
|
||||||
|
val completedTasks: Boolean = true,
|
||||||
|
val upcomingEventsCount: Int = 3,
|
||||||
|
val upcomingTaskCount: Int = 3,
|
||||||
)
|
)
|
||||||
data class CalendarWidget(
|
data class CalendarWidget(
|
||||||
override val id: UUID,
|
override val id: UUID,
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user