Skip to content

Add category assignments, auto-categoriser, and grouped app library view (#323) - #325

Merged
BarMal merged 1 commit into
masterfrom
feature/app-category-assignments
Jun 13, 2026
Merged

BarMal merged 1 commit into
masterfrom
feature/app-category-assignments

Conversation

@BarMal

@BarMal BarMal commented Jun 13, 2026

Copy link
Copy Markdown
Owner

Summary

  • AppCategoryGroup — model pairing an AppCategory with its filtered AppEntry list
  • AppAutoCategoriser — package-name heuristic rules mapping ~50 well-known app packages to category IDs (communications, finance, shopping, media, productivity, games, system, customisation)
  • LauncherSettings — categoryList / setCategoryList, appCategoryAssignments / setAppCategoryAssignments / setAppCategoryIds, appGroupingEnabled / setAppGroupingEnabled, and autoCategorise(appEntries) which bulk-assigns via the categoriser; all category state included in launcherChangeToken so renders refresh on change
  • AppLibraryFilter.groupByCategory — groups a filtered app list by enabled categories, respecting the active search query and profile scope; empty categories are omitted
  • AppLibraryPageModel / AppLibraryPageModelFactory — new AppLibraryCategoryContext carries categories + assignments + toggle; factory populates categoryGroups on the model when context is present and groupingEnabled=true and assignments are non-empty
  • LauncherAppLibraryController — when categoryGroups is non-null, renders a grouped card stack: one dimmed section-header card per category (title + app count) followed by that category's app cards, all in one unified scrollable stack
  • CalmLauncherRunner — wires settings reads into a categoryContext lambda injected into the factory

UX

When the user enables app grouping (setAppGroupingEnabled(true)) and triggers auto-categorisation (autoCategorise(appEntries)), the app library page shows apps grouped under section header cards for each category. The flat list view is unchanged when grouping is off or no assignments exist.

Manual per-app assignment is supported via setAppCategoryIds(identityKey, ids) — UI for this is a subsequent slice.

Test plan

  • ./gradlew :app:testDebugUnitTest — all tests pass
  • AppAutoCategoriserTest — WhatsApp → communications, Spotify → media, Docs → productivity, unknown → empty
  • AppLibraryFilterTest — groupByCategory groups correctly, skips disabled/empty categories, applies search query
  • AppLibraryPageModelTest — factory returns null groups when context absent/disabled/empty; populates groups when enabled

Closes part of #323

https://claude.ai/code/session_014SVjLmSTdqY3hSCrK59YFV


Generated by Claude Code

…iew (#323)

- AppCategoryGroup: model pairing an AppCategory with its filtered apps
- AppAutoCategoriser: package-name heuristics mapping known apps to category ids
- LauncherSettings: categoryList, appCategoryAssignments, appGroupingEnabled,
  autoCategorise helper; category state included in launcherChangeToken
- AppLibraryFilter: groupByCategory groups filtered apps by enabled category,
  respecting search query and profile scope
- AppLibraryPageModel / factory: categoryGroups field populated when an
  AppLibraryCategoryContext is provided with groupingEnabled=true
- LauncherAppLibraryController: renders grouped view with a section-header card
  per category when categoryGroups is non-null
- CalmLauncherRunner: wires settings into AppLibraryPageModelFactory via context lambda

https://claude.ai/code/session_014SVjLmSTdqY3hSCrK59YFV
@BarMal
BarMal merged commit cbb92de into master Jun 13, 2026
1 check failed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants