diff --git a/app/src/main/java/de/jeanlucmakiola/calendula/ui/imports/ImportScreen.kt b/app/src/main/java/de/jeanlucmakiola/calendula/ui/imports/ImportScreen.kt index 881b836..8a9b4d9 100644 --- a/app/src/main/java/de/jeanlucmakiola/calendula/ui/imports/ImportScreen.kt +++ b/app/src/main/java/de/jeanlucmakiola/calendula/ui/imports/ImportScreen.kt @@ -10,6 +10,7 @@ import androidx.compose.foundation.layout.padding import androidx.compose.foundation.rememberScrollState import androidx.compose.foundation.verticalScroll import androidx.compose.material.icons.Icons +import androidx.compose.material.icons.filled.Check import androidx.compose.material.icons.filled.Close import androidx.compose.material3.Button import androidx.compose.material3.CircularProgressIndicator @@ -38,8 +39,10 @@ import androidx.lifecycle.compose.collectAsStateWithLifecycle import de.jeanlucmakiola.calendula.R import de.jeanlucmakiola.calendula.domain.EventForm import de.jeanlucmakiola.calendula.domain.ics.IcsParseWarning +import de.jeanlucmakiola.calendula.ui.common.CalendarColorChip +import de.jeanlucmakiola.calendula.ui.common.GroupedRow +import de.jeanlucmakiola.calendula.ui.common.positionOf import de.jeanlucmakiola.calendula.ui.common.predictiveBack -import de.jeanlucmakiola.calendula.ui.common.OptionCard /** * Handles an opened/received `.ics` file. A single event is handed straight to @@ -106,33 +109,73 @@ private fun ManyContent(state: ImportUiState.Many, onImport: (Long) -> Unit) { } var selected by rememberSaveable { mutableStateOf(state.calendars.first().id) } + // Group by owning account, the same shape the event editor's calendar picker + // uses — coloured chip per calendar, a check on the selected one. + val groups = remember(state.calendars) { + state.calendars + .groupBy { + it.accountName.takeIf(String::isNotBlank) + ?: it.accountType.takeIf(String::isNotBlank) + ?: it.displayName + } + .toList() + } + Column( Modifier.fillMaxSize().verticalScroll(rememberScrollState()) - .padding(horizontal = 16.dp, vertical = 8.dp), - verticalArrangement = Arrangement.spacedBy(8.dp), + .padding(vertical = 8.dp), ) { Text( pluralStringResource(R.plurals.import_event_count, state.events.size, state.events.size), style = MaterialTheme.typography.bodyLarge, - modifier = Modifier.padding(vertical = 8.dp), + modifier = Modifier.padding(horizontal = 24.dp, vertical = 8.dp), ) Text( stringResource(R.string.import_target_header), - style = MaterialTheme.typography.labelLarge, - color = MaterialTheme.colorScheme.primary, + style = MaterialTheme.typography.bodyMedium, + color = MaterialTheme.colorScheme.onSurfaceVariant, + modifier = Modifier.padding(start = 24.dp, end = 24.dp, bottom = 4.dp), ) - state.calendars.forEach { calendar -> - OptionCard( - label = calendar.displayName, - onClick = { selected = calendar.id }, - selected = calendar.id == selected, - icon = null, + groups.forEach { (account, cals) -> + Text( + text = account, + style = MaterialTheme.typography.labelLarge, + color = MaterialTheme.colorScheme.primary, + modifier = Modifier.padding(start = 24.dp, end = 24.dp, top = 16.dp, bottom = 4.dp), ) + cals.forEachIndexed { index, calendar -> + val isSelected = calendar.id == selected + GroupedRow( + title = calendar.displayName, + position = positionOf(index, cals.size), + selected = isSelected, + leading = { CalendarColorChip(calendar.color) }, + trailing = if (isSelected) { + { + Icon( + imageVector = Icons.Default.Check, + contentDescription = null, + tint = MaterialTheme.colorScheme.primary, + ) + } + } else { + null + }, + onClick = { selected = calendar.id }, + ) + } + } + if (state.warnings.isNotEmpty()) { + Column( + Modifier.padding(horizontal = 24.dp, vertical = 8.dp), + verticalArrangement = Arrangement.spacedBy(4.dp), + ) { + state.warnings.forEach { WarningText(it) } + } } - state.warnings.forEach { WarningText(it) } Button( onClick = { onImport(selected) }, - modifier = Modifier.fillMaxWidth().padding(top = 8.dp), + modifier = Modifier.fillMaxWidth().padding(start = 16.dp, end = 16.dp, top = 8.dp), ) { Text(pluralStringResource(R.plurals.import_action, state.events.size, state.events.size)) }