2026-02-10 02:22:41 +00:00
|
|
|
import SwiftData
|
|
|
|
|
import SwiftUI
|
|
|
|
|
|
|
|
|
|
/// A view that displays todo tasks grouped by date and completion categories.
|
|
|
|
|
///
|
|
|
|
|
/// This view serves as the main interface for browsing tasks organized into four groups:
|
|
|
|
|
/// - **Today**: Tasks due today that are not yet completed
|
|
|
|
|
/// - **Upcoming**: Tasks due in the future that are not yet completed
|
|
|
|
|
/// - **Overdue**: Tasks due in the past that are not yet completed
|
|
|
|
|
/// - **Completed**: Tasks that have been marked as done
|
|
|
|
|
struct TaskGroupListView: View {
|
|
|
|
|
|
|
|
|
|
// MARK: Properties
|
|
|
|
|
|
2026-02-12 03:02:28 +01:00
|
|
|
/// Binding to the currently selected todo task group.
|
|
|
|
|
///
|
|
|
|
|
/// When provided, the view will use this binding for navigation split view selection.
|
|
|
|
|
@Binding
|
|
|
|
|
private var group: TodoGroup?
|
|
|
|
|
|
2026-02-10 02:22:41 +00:00
|
|
|
/// Query to monitor all todo tasks for changes.
|
|
|
|
|
///
|
|
|
|
|
/// This query triggers view updates whenever todo tasks are inserted, updated, or deleted,
|
|
|
|
|
/// ensuring the task counts displayed in the view remain accurate.
|
|
|
|
|
@Query
|
2026-02-12 03:02:28 +01:00
|
|
|
private var todos: [Todo]
|
2026-02-10 02:22:41 +00:00
|
|
|
|
|
|
|
|
/// The view model managing the state and logic for this view.
|
|
|
|
|
///
|
|
|
|
|
/// Handles task counting and provides access to all task groups.
|
|
|
|
|
/// Initialized with the default calendar for date calculations.
|
|
|
|
|
@State
|
|
|
|
|
private var viewModel = ViewModel()
|
|
|
|
|
|
2026-02-12 03:02:28 +01:00
|
|
|
// MARK: Initializers
|
|
|
|
|
|
|
|
|
|
/// Creates a task group list view with a binding to the selected group.
|
|
|
|
|
///
|
|
|
|
|
/// This initializer configures the view for use in a navigation split view,
|
|
|
|
|
/// where the binding tracks which task group is currently selected in the sidebar.
|
|
|
|
|
///
|
|
|
|
|
/// - Parameter group: A binding to the currently selected task group.
|
|
|
|
|
init(_ group: Binding<TodoGroup?>) {
|
|
|
|
|
self._group = group
|
|
|
|
|
}
|
|
|
|
|
|
2026-02-10 02:22:41 +00:00
|
|
|
// MARK: Body
|
|
|
|
|
|
|
|
|
|
/// The content and behavior of the view.
|
|
|
|
|
///
|
|
|
|
|
/// Displays a scrollable vertical list of task group cards. Each card shows:
|
|
|
|
|
/// - The group's icon in its associated color
|
|
|
|
|
/// - The group's title
|
|
|
|
|
/// - The current count of tasks in that group
|
|
|
|
|
///
|
2026-02-12 03:02:28 +01:00
|
|
|
/// Cards are tappable and update the selected group binding for navigation split view.
|
2026-02-10 02:22:41 +00:00
|
|
|
/// Task counts are fetched on-demand from the model context for each render.
|
|
|
|
|
var body: some View {
|
2026-02-12 03:02:28 +01:00
|
|
|
List(
|
|
|
|
|
viewModel.groups,
|
|
|
|
|
selection: $group
|
|
|
|
|
) { group in
|
|
|
|
|
Card(
|
|
|
|
|
group: group,
|
|
|
|
|
count: viewModel.count(
|
|
|
|
|
todos,
|
|
|
|
|
for: group
|
|
|
|
|
)
|
|
|
|
|
)
|
|
|
|
|
.listRowBackground(Color.clear)
|
|
|
|
|
.listRowSeparator(.hidden)
|
|
|
|
|
.tag(group)
|
2026-02-10 02:22:41 +00:00
|
|
|
}
|
2026-02-12 03:02:28 +01:00
|
|
|
.listStyle(.plain)
|
2026-02-10 02:22:41 +00:00
|
|
|
.navigationTitle("view.task-group-list.navigation.title")
|
2026-02-12 03:02:28 +01:00
|
|
|
.sensoryFeedback(
|
|
|
|
|
.selection,
|
|
|
|
|
trigger: group
|
|
|
|
|
)
|
2026-02-10 02:22:41 +00:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// MARK: - Previews
|
|
|
|
|
|
|
|
|
|
#Preview(
|
|
|
|
|
"Task group list with empty tasks",
|
|
|
|
|
traits: .emptyContainer
|
|
|
|
|
) {
|
2026-02-12 03:02:28 +01:00
|
|
|
@Previewable
|
|
|
|
|
@State
|
|
|
|
|
var group: TodoGroup?
|
|
|
|
|
|
2026-02-10 02:22:41 +00:00
|
|
|
NavigationStack {
|
2026-02-12 03:02:28 +01:00
|
|
|
TaskGroupListView($group)
|
2026-02-10 02:22:41 +00:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
#Preview(
|
|
|
|
|
"Task group list with sample tasks",
|
|
|
|
|
traits: .sampleTasks
|
|
|
|
|
) {
|
2026-02-12 03:02:28 +01:00
|
|
|
@Previewable
|
|
|
|
|
@State
|
|
|
|
|
var group: TodoGroup?
|
|
|
|
|
|
2026-02-10 02:22:41 +00:00
|
|
|
NavigationStack {
|
2026-02-12 03:02:28 +01:00
|
|
|
TaskGroupListView($group)
|
2026-02-10 02:22:41 +00:00
|
|
|
}
|
|
|
|
|
}
|