Case study // 2026
FitCal
Photograph a meal, get its ingredients, weights and macros.
- Year
- 2026
- Role
- Solo: design, mobile, backend
- Areas
- CV // Full-stack
- Stack
- Kotlin Multiplatform, Compose Multiplatform, Swift, Postgres, TypeScript
Logging food by hand is the reason most people stop tracking it. FitCal turns a photo of a meal into a list of ingredients with estimated weights and macros, then lets you correct anything it got wrong.
It ships to Android and iOS from one Kotlin Multiplatform codebase with a shared Compose Multiplatform UI, a thin Swift shell on iOS and a Postgres backend.
The system
Photo
Camera or gallery
On-device prep
Resized and compressed before upload
Model gateway
Edge Function: OpenRouter, then Gemini, then Groq
Meal estimate
Ingredients, weights, macros
Edit & recalculate
Text-only prompt, no re-upload
One outage shouldn't break scanning
Scans go through a gateway on Supabase Edge Functions that fails over between three vision-language providers: OpenRouter first, then Gemini, then Groq. If one is down or slow, the scan still finishes.
Fewer tokens, less waiting
Photos are resized and compressed on the device before they leave it, which cuts both tokens and latency.
When you change an ingredient, the macros are recalculated with a text-only prompt instead of sending the photo again. The project README puts that at about 10× faster.
Everything around the scan
- Barcode scanning for packaged food
- Health Connect sync
- Home-screen widget and meal reminders
- Weekly summaries and adaptive calorie targets
- Privacy consent with an age gate
- Analytics and crash reporting; backend logic in PL/pgSQL