The position asked for is the bezel slot: a circular complication plus a label
that arcs across the top, where the tick marks otherwise are. ClockKit called
that family graphicBezel; in WidgetKit it is an accessoryCircular widget with
.widgetLabel attached. Nothing was attached, so that arc stayed empty while
Apple's Calendar fills it — which is the difference that was visible on the
watch and invisible in every check made here.
All three circular kinds now carry it. Faces without a bezel slot ignore the
label, so there is no cost to always providing it.
cornerLabel becomes eventLabel: the same text serves the corner edge and the
bezel arc, and the old name claimed otherwise.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Date and "events today" filled their slot with AccessoryWidgetBackground and
centred text, which reads as a small element with space around it. Both are now
Gauges in .accessoryCircularCapacity — the WidgetKit equivalent of ClockKit's
ClosedGauge templates, which no longer exist and cannot be reached from a
WidgetKit complication at all.
The rings carry meaning rather than decorating: the date's drains through the
day, and the count's drains as today's appointments are worked through. Both
drain, matching the countdown rather than inventing a second direction. An
empty day leaves the ring empty instead of full, so it does not read as an
untouched one.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Text(style: .timer) renders 1:23:45 once more than an hour out. An
accessoryCorner has room for three or four characters beside its curved label,
and a circular gauge for about the same, so the live timer overlapped what it
sat next to.
Replaced with a compact value — "23m", "2h", "3d" — recomputed per timeline
entry, which is why the timeline now carries a mark every minute for the first
hour. Both corner kinds and the gauge also get lineLimit(1) and a minimum scale
factor, so an unexpectedly wide value shrinks instead of colliding.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
The watch receives the phone's payload over WatchConnectivity and writes it
into its own App Group container through the same SnapshotStore, so there is
one wire format and one reader. The agenda, the detail screen and the filter
all read that; the complications read what the app last wrote, since an
extension cannot run a WCSession of its own.
Complication timelines land on event boundaries rather than a schedule, so the
next appointment flips in the exact minute it changes without spending refresh
budget.
CalendarrWatchShared holds what both watch targets need, attached to each the
way Shared/ is attached to the app and the widgets.
recommendations() is implemented because watchOS requires it — iOS has a
default, the watch does not, since the complication gallery has to be
populated. Found by building, not by reading.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>