feat(todo): the Plan beside Upcoming, with what has no date (ADR 0033, D34)

Upcoming's 3-day grid gets the Plan Today's calendar has, through what
the two tabs now share (PlanHost). Its new last group holds the open
tasks of no day, so a week can be planned from the Inbox by dropping them
on an hour; they aren't counted on the button, which says what is due.

Whats-New: Upcoming's 3-day view has the Plan too, and tasks without a date can be dragged from it onto any day.
Whats-New-De: Auch die 3-Tage-Ansicht unter Demnächst hat den Plan, und Aufgaben ohne Datum lassen sich von dort auf jeden Tag ziehen.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Signed-off-by: Tizian 「ティツィアーン」 <raisondetredev@pm.me>
This commit is contained in:
Tizian 「ティツィアーン」 2026-11-05 19:37:55 +01:00
commit 31ff8d7e91
Signed by: raisondetredev
GPG key ID: 07F6FCF405488B64

View file

@ -135,6 +135,7 @@ void main() {
expect(plan.toPlan.map((t) => t.id), ['open']);
expect(plan.timed.map((t) => t.id), ['eight', 'nine']);
expect(plan.count, 4);
expect(plan.noDate.map((t) => t.id), ['undated']);
final home = planOf(tasks, today, projectIds: {'home'});
expect(home.overdue, isEmpty);
@ -142,4 +143,35 @@ void main() {
expect(home.timed.map((t) => t.id), ['eight']);
expect(home.count, 2);
});
test('the Plan keeps the tasks of no day apart, uncounted (D34)', () {
const today = Day(2026, 11, 5);
OpenTask task(String id, {String? parentId, bool completed = false}) => (
id: id,
content: TaskContent(
title: id,
projectId: id == 'other' ? 'home' : 'inbox',
parentId: parentId,
completedAt: completed ? DateTime(2026, 11, 4) : null,
),
);
final tasks = [
task('free'),
task('other'),
task('sub', parentId: 'free'),
task('done', completed: true),
];
final plan = planOf(tasks, today);
expect([for (final task in plan.noDate) task.id], ['free', 'other']);
expect(plan.count, 0);
expect(plan.isEmpty, isFalse);
expect(
[
for (final task in planOf(tasks, today, projectIds: {'home'}).noDate)
task.id,
],
['other'],
);
});
}