- Mini calendar: mark every day an event spans (not just the start day) so
multi-day events (Urlaub/Ferien) show a dot across the whole range
- Week view: render short events on one line (time next to title) so the title
stays visible; drop the location line when there's no room
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
The agenda lists the whole cached range, so clicking Today only reset scroll
to the top (earliest past event). Scroll the agenda to the current date (or the
next day with events) after rendering, so Today/mini-cal clicks land correctly.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Bug fix: publishWidgetSnapshot() now guards against activeGroup != nil,
so group view events/colors never contaminate the widget cache.
Feature: widgets can now be configured via long-press → Edit Widget.
- WidgetCalendar struct + writeCalendars/readCalendars in WidgetData.swift
- calendarKey added to WidgetEvent (backward-compatible decoder)
- CalendarIntent.swift: CalendarAppEntity + CalendarEntityQuery + CalendarSelectionIntent
- CalendarrTimelineProvider migrated from TimelineProvider to AppIntentTimelineProvider
- All 13 StaticConfiguration widgets changed to AppIntentConfiguration
- publishWidgetSnapshot() builds + writes the calendar list for the intent
An empty selection (default) shows all calendars; selecting specific
calendars filters the widget events accordingly.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Don't start a header drag when the pointer goes down on a button/link, so
edit/copy/delete/close work again
- Make the popup body text selectable (user-select: text) for copying
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Replace group-category icons with 8 sharing-specific icons in the
Darstellung picker: share (3 nodes), link, send, eye, upload, wifi,
person_add, ios_share. Uses new shareIconSvg() + SHARE_ICON_KEYS/PATHS
constants, separate from group icons. Default changes from 'people' to 'share'.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Rename: Add google and homeassistant branches to the dblclick-rename
save() handler; backend already accepted name updates for both sources
- Group icon: Pass groupIconForLocalCal(cal.id) into sidebar entries so
the group's custom icon (home/heart/work/…) shows instead of always
defaulting to the people icon
- Share icon: New share_calendar_icon field in UserSettings (+ migration)
replaces the hardcoded SHARE_ICON SVG; users pick from GROUP_ICON_KEYS
in Settings → Darstellung via a new icon-picker row
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
The filter-sheet Switch now calls setCalendarHiddenSynced(), which
updates local hiddenKeys immediately AND fires a sidebar_hidden PATCH
to the server for caldav/google/homeassistant calendars. This makes
the quick-hide consistent with the web sidebar across all devices.
CalendarFilterEntry gains a source field so the sheet knows which
backend to target.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- groupVisible calendars get a share icon instead of the people icon;
people icon is reserved for actual group calendars
- sidebar scrollbar hidden (scrollbar-width: none + webkit)
- modal-body scrollbar hidden — fixes Impressum scroll indicator
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Instead of absolute positioning (which caused icons to overlay text),
use min-height:40px on .cal-item so the row is always tall enough for
28px mini-btns. Buttons stay in the flex flow with display:none when
hidden — no space reserved, no text truncation, no height shift on hover.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Buttons (.cal-item-remove, .cal-item-bell) are now position:absolute so
they never participate in flex layout — names get full available width at
all times. Buttons fade in over the right edge of the item on hover with
no layout shift and no row-height change.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- modal-card: overflow:hidden + flex column; modal-body scrolls instead,
so native scrollbar never overlaps the 20px border-radius corners
- cal-item-remove / cal-item-bell: display:none→flex replaced with
opacity:0/pointer-events:none→1/auto, eliminating reflow on hover
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
URL gains &stab=<panel> when settings are open (e.g. #...&settings=1&stab=accounts).
Tab switches update the URL; reload reopens settings on the same tab.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Notifications now show "in 30 Min. · Ort" instead of just the location,
giving users immediate context about how soon the event starts.
Default event duration picker moved from the View section to right below
the profile/privacy group, consistent with the iOS app arrangement.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Notifications now show "in 30 Min. · 10:00" instead of just the time,
giving users immediate context about how soon the event is.
Default event duration picker moved from the View section to right below
the privacy setting, grouped under the calendar/profile settings area.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Force resp.encoding='utf-8' in _fetch_ics so umlauts (ö/ä/ü) from sources
like Ferienwiki.de are decoded correctly instead of showing as ö/ä/ü.
Add default_event_duration_minutes to UserSettings (nullable int, same pattern
as default_reminder_minutes) with DB migration, GET/PUT in settings_router.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Reminder editor: presets + custom number+unit (minutes/hours/days/weeks)
- Grey out + footer hint when the selected calendar's reminders are muted;
reminders are kept, scheduler already skips them
- New synced setting defaultEventDurationMinutes for new events
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- Add reminder editor (presets + custom number+unit) wired through save
- Per-calendar reminder mute: filter-sheet toggle + greyed-out editor hint;
reminders are kept, never deleted
- New AlarmManager-based NotificationScheduler + channel + POST_NOTIFICATIONS;
skips muted calendars
- New synced setting default_event_duration_minutes for new events
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- Render event descriptions as sanitized HTML (links/line breaks) instead of
raw escaped text; no script execution
- Reminder picker: presets + custom number+unit (minutes/hours/days/weeks)
- Grey out + hint the reminder editor when a calendar's notifications are off
(reminders are kept, just not fired)
- New synced setting default_event_duration_minutes (default 60) for new events
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Transparent background caused Pixel launcher to inject its own tinted
ring. Replace with #16703D (sampled from iOS icon background) so the
launcher shape-clips cleanly without any visible halo.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Without mipmap-anydpi-v26 XML, Pixel launcher wraps legacy PNGs in a
white ring template. Adding adaptive-icon XML with the iOS-matching
foreground PNG at correct per-density sizes (108dp canvas) eliminates
the nested-ring appearance.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Use Modifier.size(20.dp) instead of height(20.dp) so the spinner is
constrained on both axes and doesn't get cut off horizontally.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Material 3 menus use shapes.extraSmall (4dp default) which looked boxy;
bump to 14dp so all dropdown popups (view switcher, group switcher, ...)
get rounded corners matching the iOS look.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
- Long-press on a day now opens a preview popup (ported from the iOS
DayContextPreviewView): all-day events as colored bars with tapered
ends when they continue beyond the day, timed events as dot+time+title
rows, plus quick actions (new event, week view, day view)
- Month scroll performance: stable item keys + contentType in the
LazyColumn, remembered Instant.now()/theme colors, remembered callbacks
so visible week rows stay skippable during recomposition
- Fix "+N" and "KW" labels overlapping the lowest event lane (row bottom
padding 6dp -> 16dp, mirrors the iOS fix)
- Event detail: delete is now a quiet red text button instead of a
full-width filled container
- Top bar: hairline divider so the bar/calendar boundary is visible
- FAB: explicit circular shape
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
- DayPreviewAllDayBar: use custom ChevronBarShape (polygon clip) instead of
chevron SF Symbols; bars have tapered pointed ends for continuation
- MonthView rowHeight: increase bottom padding from +4 to +16 so the
overflow "+N" count no longer overlaps the last event bar lane
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
All-day continuation bars now use CSS clip-path polygon for the tapered
arrow shape; bars stay inset within the popup (no edge bleed). Version v51.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- CalendarDayWidget: add 6pt top padding to header so content isn't flush
against the widget edge
- ThisWeekWidget: increase per-day event cap from 6 to 8 to prevent "+1"
overflow when there is vertical space available
- MonthView: add DayContextPreviewView to the long-press context menu using
.contextMenu(menuItems:preview:); shows all-day events as colored bars
with chevron continuation arrows, timed events as dot+time+title rows
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
All-day events in the "+N weitere" popup now render as colored bars matching
the month-grid style: continues-left/right arrows when the event spans beyond
the selected day. Timed events keep dot+time+title format. Version bump v50.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Tab title shows only "Calendarr" (version stays in sidebar/impressum)
- Fix lane assignment in month view: use 2D per-column occupancy grid instead of
global colEnd tracking; eliminates empty rows caused by non-overlapping events
being pushed to lower lanes
- "+N weitere" now opens an inline popup listing all events for that day
(all-day first, then by time); clicking an event opens its detail popup
- Double-click on day cell navigates to day view (was already implemented)
- Remove hardcoded "v18" from login screen impressum button
- Bump version to v49
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
The per-day cap of 3 made busy days collapse to "+N" so only ~6-7 events
showed total. Raise it (25) and let the total-row cap govern; extraLarge
fills up to 40 rows.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- Date picker: clicking a day only selects it now; the choice is committed
when you leave the picker (click outside) or press Save — for both date and
datetime modes (previously datetime discarded on click-away, and date
committed instantly on click, neither of which was wanted).
- The day right-click context menu ("Neuen Termin erstellen") now closes when
an event popup opens (the event row stops propagation, so its own
outside-click closer never fired).
- version v47 -> v48.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
A native <select> can't render the group icon SVG, so the calendar picker
is replaced with a styled dropdown: colour dot + group icon + name, grouped
by account/source with a "Groups" section. The native <select> is kept
hidden as the value holder + change-event source, so all existing save and
private/reminder-row logic is unchanged. Click-outside / Escape close it.
version v46 -> v47.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Drop 10 min / 2 h / 2 days, add 1 week, and use full-word "… vorher" /
"… before" labels so the choices match the web client.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- Stop the blinking text caret / selection on non-editable UI chrome
(headings, buttons, icons, dropdowns): body is user-select:none, with text
selection opted back in for inputs/textareas. Felt like an editable field.
- Reminder options trimmed to 5/15/30 min, 1 h, 1 day, 1 week (dropped 10 min,
2 h, 2 days; added 1 week). Labels now read "5 Minuten vorher", "1 Tag
vorher", "1 Woche vorher" instead of "vor 5 Min." / "vor 1 Tag(en)".
- Group calendars can now be muted (reminder bell) in the sidebar when owned.
- Event modal corners rounded (20px) to match the pill buttons.
- version v45 -> v46.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
C1 — Localization: route the remaining hardcoded German strings through
L10n (LoginView, ServerSetupView, SettingsView email, EventDetailSheet) so
"System Default" + English device language shows fully English text.
C2 — Per-calendar reminders: parse the new reminders_enabled flag on every
calendar type; CalendarStore persists a reminderDisabledKeys set and passes
it to NotificationScheduler, which skips events of muted calendars (default
and per-event reminders). Filter sheet gains a per-calendar reminder toggle
(leading swipe + bell.slash indicator), reconciled from the server and
synced back via PUT.
C3 — Widgets:
- Shared WidgetTime.range helper; Today / Today & Tomorrow / Three Days /
Up Next now show start–end instead of only the start time.
- This Week: show up to 6 events per day (was 3) to use the height.
- Two Weeks: mini event-title pills instead of bare dots.
- Two Months: weeks expand to fill the column (no more empty lower third).
- Day & Events: smaller header/strip/rows so content stops clipping.
- Next 5 days → Next 7 days (range + labels), higher row cap.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- Event popup: new "Reminders" section for local events — show/add/remove
multiple reminders, prefilled with the global default on new events; sent
in the local create/update body and synced like any other event field.
- Sidebar calendar list: per-calendar reminder bell toggle (PUTs the new
reminders_enabled flag); disabled state shown dimmed.
- Date picker: a day click now commits immediately in date-only mode instead
of requiring an extra "Save" click.
- Start/End: moving the end before the start now shifts the start back
(mirroring the start handler) instead of showing an error toast.
- Calendar dropdown: group calendars moved under a "Groups" optgroup; dropped
the 👥 emoji prefix (a native <select> can't render the icon SVG).
- Month grid: selectedDate defaults to today so the highlight no longer
follows the cells while navigating before any click.
- Today cell tint now derives from --today-color instead of hardcoded blue.
- version v44 -> v45.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
New boolean column on every calendar type (CalDAV, local, Google, Home
Assistant, iCal subscription), default ON so existing data is unchanged.
Lets a calendar be shown without generating reminders/notifications.
- models.py: reminders_enabled on the five calendar models
- main.py _migrate(): ALTER TABLE ADD COLUMN for each table
- caldav/google/homeassistant/local/ical routers: expose the flag in the
calendar serialization and accept it in the calendar/subscription update
endpoints
Clients map event -> (source, calendar_id) -> reminders_enabled to skip
scheduling notifications for disabled calendars.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Left side now holds only the prev/next chevrons; "Heute" moved next to the
burger menu on the right (both flat and Liquid Glass bars), so the month title
is centered again instead of pushed right by a heavy left cluster.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
CalEvent gains `reminders` (parsed from the server); AppSettings/SettingsStore
gain `defaultReminderMinutes` (null = off) and it's sent via updateSettings;
createLocalEvent/updateLocalEvent/eventBody and CalendarViewModel.saveEvent
thread `reminders` through. UI (editor + settings picker) and the local
notification scheduling follow next.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
The top bar now shows only nav + title + a single burger. Tapping it opens a
compact menu: View (with a fixed icon, no longer per-view), Filter, Groups
(if any), Sync, and an "Einstellungen" entry that opens the existing full menu.
Removed the separate group/view/filter icons from both the flat bar and the
Liquid Glass toolbar.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Per-event reminders (multiple, local calendars only) in the editor, prefilled
from a new "default reminder" setting that applies to all events otherwise.
CalEvent gains `reminders`; AppSettings/SettingsSync sync default_reminder_minutes
(always group). New NotificationScheduler requests permission and schedules the
soonest ≤60 upcoming reminders via UNUserNotificationCenter, rescheduling on
load/sync/edit and when the default changes (skipped in group overlay).
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
local_events gains a `reminders` TEXT column (comma-separated minutes-before-
start, like exdate); EventCreate/EventUpdate accept a `reminders: [int]` list
and build_local_event_dict emits it back as a list. user_settings gains
`default_reminder_minutes` (nullable int, null = off), exposed/updatable via
/api/settings (explicit null persists as off). Migrations added in _migrate().
Clients (iOS/Android) schedule the OS notifications locally from these.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
The NavigationStack toolbar title never refreshes on month change on iOS 26
(4 approaches tried: principal Text, navigationTitle, @Observable store). The
title now renders as a normal inline Text in a top safe-area inset just below
the system glass toolbar — the same mechanism as the flat variant, which does
update. The system toolbar keeps the buttons + the real Liquid Glass look.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Moved the group member filter from a top bar into the left sidebar (a
"Mitglieder" section that replaces the personal calendar list while a group is
active). Each member row has a checkbox (show/hide their events) and a colour
dot that opens the colour picker to recolour that member just for this viewer —
stored per-device in localStorage and applied over the server colour. Bumped v44.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Group icons are semantic keys rendered as inline SVG (mirroring iOS SF Symbols /
Android Material) in the picker, group list and sidebar flags — instead of OS
emoji that vary per platform. Legacy emoji values still render as a fallback.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>