fix: open existing events from external VIEW intents (Codeberg #48) #69

Merged
makiolaj merged 1 commits from fix/widget-view-event-intent into release/v2.14.1 2026-07-12 09:09:25 +00:00
Owner

Fixes Codeberg #48https://codeberg.org/jlmakiola/calendula/issues/48
(reported on v2.14.0, Pixel 7 / Android 16 / LineageOS). Follow-up to the
closed #30.

The gap

v2.14.0 added the ACTION_INSERT filter (#30), so the widget "+" can create an
event in Calendula. But tapping an existing event in a third-party widget
(e.g. Todo Agenda) still didn't list Calendula in the chooser — nothing handled
ACTION_VIEW on content://com.android.calendar/events/<id>.

Fix

  • Manifest — add a VIEW intent-filter matched by the provider's item MIME
    type
    vnd.android.cursor.item/event (mirrors AOSP Calendar and the sibling
    INSERT dir/event filter). A content: VIEW intent carries the resolved type,
    so Android's matching would reject a path-only <data> filter — the MIME match
    is the reliable one.
  • MainActivity.viewEventKeyOrNull — parse the events URI into the existing
    occurrence detail-key channel (the same one reminder taps flow through, so
    RootScreen → CalendarHost → EventDetailScreen needs no changes). Occurrence
    times ride as EXTRA_EVENT_BEGIN_TIME / EXTRA_EVENT_END_TIME when the
    launcher supplies them.
  • EventDetailViewModel — a NO_OCCURRENCE_TIME sentinel makes loadDetail
    keep the event row's own DTSTART/DTEND when the launcher sends a bare URI (no
    occurrence extras), instead of overriding to the epoch (which would render the
    event at 1970 — the same hazard flagged for #34).

Testing

  • ./gradlew assembleDebug lint test green locally.
  • No new unit tests: intent-filter matching and the ViewModel/intent glue aren't
    JVM-testable here (the project's JVM-first coverage is pure domain + mappers).
  • ⚠️ Not yet on-device verified — needs a real device to confirm the filter
    matches the widget's actual VIEW intent and that its extras behave as expected.

🤖 Generated with Claude Code

Fixes **Codeberg #48** — https://codeberg.org/jlmakiola/calendula/issues/48 (reported on v2.14.0, Pixel 7 / Android 16 / LineageOS). Follow-up to the closed #30. ## The gap v2.14.0 added the `ACTION_INSERT` filter (#30), so the widget "+" can create an event in Calendula. But tapping an **existing** event in a third-party widget (e.g. Todo Agenda) still didn't list Calendula in the chooser — nothing handled `ACTION_VIEW` on `content://com.android.calendar/events/<id>`. ## Fix - **Manifest** — add a VIEW `intent-filter` matched by the provider's **item MIME type** `vnd.android.cursor.item/event` (mirrors AOSP Calendar and the sibling INSERT `dir/event` filter). A `content:` VIEW intent carries the resolved type, so Android's matching would reject a path-only `<data>` filter — the MIME match is the reliable one. - **`MainActivity.viewEventKeyOrNull`** — parse the events URI into the existing occurrence detail-key channel (the same one reminder taps flow through, so `RootScreen → CalendarHost → EventDetailScreen` needs no changes). Occurrence times ride as `EXTRA_EVENT_BEGIN_TIME` / `EXTRA_EVENT_END_TIME` when the launcher supplies them. - **`EventDetailViewModel`** — a `NO_OCCURRENCE_TIME` sentinel makes `loadDetail` keep the event row's own DTSTART/DTEND when the launcher sends a bare URI (no occurrence extras), instead of overriding to the epoch (which would render the event at 1970 — the same hazard flagged for #34). ## Testing - `./gradlew assembleDebug lint test` green locally. - No new unit tests: intent-filter matching and the ViewModel/intent glue aren't JVM-testable here (the project's JVM-first coverage is pure domain + mappers). - ⚠️ **Not yet on-device verified** — needs a real device to confirm the filter matches the widget's actual VIEW intent and that its extras behave as expected. 🤖 Generated with [Claude Code](https://claude.com/claude-code)
makiolaj added 1 commit 2026-07-12 09:02:15 +00:00
fix: open existing events from external VIEW intents (#48)
All checks were successful
CI / ci (pull_request) Successful in 10m20s
9d718e0f51
Follow-up to #30. v2.14.0 handles ACTION_INSERT (the widget "+"), but
tapping an existing event in a third-party widget (e.g. Todo Agenda) never
offered Calendula, because nothing handled ACTION_VIEW on
content://com.android.calendar/events/<id>.

- Manifest: add a VIEW intent-filter matched by the provider's item MIME
  type (vnd.android.cursor.item/event), mirroring AOSP Calendar and the
  sibling INSERT dir/event filter. A content: VIEW intent carries the
  resolved type, so a path-only filter wouldn't match it.
- MainActivity.viewEventKeyOrNull: parse the events URI into the existing
  occurrence detail-key channel (the one reminder taps use). Occurrence
  times ride as EXTRA_EVENT_BEGIN_TIME/END_TIME when the launcher supplies
  them; a bare URI omits them.
- EventDetailViewModel: a NO_OCCURRENCE_TIME sentinel makes loadDetail keep
  the event row's own DTSTART/DTEND for a bare URI instead of overriding to
  the epoch (would otherwise render at 1970).

Needs on-device verification (intent-filter matching + the widget's actual
extras).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
makiolaj merged commit 9fb4502ed0 into release/v2.14.1 2026-07-12 09:09:25 +00:00
makiolaj deleted branch fix/widget-view-event-intent 2026-07-12 09:09:25 +00:00
Sign in to join this conversation.
No Reviewers
No Label
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: makiolaj/calendula#69