This is a submission for the Hacktoberfest Open-Source AI Challenge Week 1: Touch Grass
What I Built
Group chats are full of plans that never happen: "we should go out this weekend." Everyone means it, and nobody goes.
Grassroots turns that plan into a game. Your squad gets a quest every day to do together, outside: "Stroll together along the winding path in the park", a ball game, a walk-and-talk, a round of frisbee. Do it with your friends, send your photos, and you all score, with a +10 together bonus if your photos were taken within 90 minutes of each other. There's also a five-stop photo walk ("Photograph a fallen leaf"), and streaks, levels and a leaderboard to keep the squad honest. If you've been on your phone too long, a detox quest nudges you back out.
An open-weight referee keeps it fair. Gemma looks at every photo and decides whether it counts: are people in it, does it fit the quest, was it taken outdoors? It runs on my laptop's 4 GB graphics card, not in someone's cloud.
Parks and trails often have no signal, so the app doesn't need one. Your photos stay sealed on your phone like envelopes, and Gemma opens them when you're home. Nobody has to stare at a screen while you're out there with your friends.
The name is two ideas: the grass where you play, and the roots, the AI that waits at home while everything else grows out from it and comes back.
What's the point of wandering alone, collecting photos for nobody, when the best part of being outside is who you're with? In Grassroots your friends are part of the game. The quest is something you do together, the photos prove you were there together, and the leaderboard turns a simple walk into friendly rivalry: who found the best flower, whose streak is still alive, who earned the together bonus because the whole squad actually showed up. You're not racing a clock or your own screen time. You're competing with your friends, in the same place, on the same platform, and laughing about it afterwards.
Scoring: a squad quest is 10 points plus a streak bonus, each walk stop is 4 (+10 for finishing all five), and the detox quest is 15.
I took it outside
I switched my phone offline and took a photo for a walk stop. The app did what it promised: a banner said one item was sealed on my phone and would upload when I reconnected. Back online, my laptop printed a verdict and the envelope went from "Saved on your phone" to "Passed +4". A friend joined from a second phone, and Gemma described what it saw in plain words: a soccer ball on grass, a bright flower with green leaves. We ended 8 points to 4.
| What I measured | Result |
|---|---|
| Judge accuracy | 9 of 9 on a small test: leaf photos against lookalikes and indoor shots |
| Speed now | about 3.5 seconds per photo on an RTX 2050 (4 GB) laptop |
| Speed before one fix | up to about a minute per AI task |
| Offline | photos sealed with no signal, uploaded and judged once back online |
That test was small and used clean photos, so treat it as promising, not proven.
Demo
Try it: https://grassroots-488t.onrender.com. Photos are judged only while my laptop is running the home judge. If you see "waiting for the home judge", that is the design, not a bug. The demo runs on a free host, so its data can reset.
The screenshots above come from my own phone.
Code
Grassroots
Go out. Seal it. Bring it home.
An offline-first outdoor game for friends. You do real things outside, photos stay sealed on your phone, and a local open-weight AI (Gemma) opens the envelopes when you get home.
Built for the DEV Hacktoberfest Open-Source AI Challenge, Week 1: Touch Grass.
Live demo:
https://grassroots-488t.onrender.com(judging only happens while the home judge is running, see Limitations).
What it does
Create a squad, share the code, and compete on daily outdoor goals:
| Activity | What you do | Points |
|---|---|---|
| Squad quest | The whole group does an activity together (ball game, walk-and-talk, frisbee, stretching). Each player sends a photo. | 10 + streak bonus (up to 5) |
| Together bonus | Two squadmates' passed photos were taken within 90 minutes of each other. | +10 each |
| Walk challenge | Five photo checkpoints of simple things (something blue, a tree, a gate). Stops are revealed one at a time. | 4 per |
How I Built It
The hosted app is only a mailbox and a scoreboard. The AI never runs on the server.
Phone (installable web app, works offline)
| sealed photos upload when there is a connection
v
Render: Node server in "hub" mode <--- outgoing calls only --- Laptop: worker.js
stores sealed photos, scores points Gemma 4 E4B via Ollama
| Layer | What I used |
|---|---|
| Front end | One HTML file, service worker, web app manifest |
| Backend | Node and Express, a single JSON file |
| Model | Gemma 4 E4B (gemma4:e4b-it-q4_K_M) through Ollama |
| Hosting | Render, plus worker.js on my laptop |
The decisions, and why
| Decision | Why |
|---|---|
| Seal photos on the phone and judge them at home | Outdoors there is often no signal, and the judge lives at home anyway |
| Gemma through Ollama on a 4 GB laptop GPU | Open weights, runs locally, no cost per photo, and friends' photos don't go to a cloud AI |
| Squad quests with a 90-minute together bonus | The point is doing things with friends, and photo times need no GPS and work offline |
| Screen time is typed in | A web page can't read phone usage, so it's an honest self-report |
| Each walk stop is judged on its own | Judging comes later, so one failed stop must not block the rest |
| A hosted mailbox plus a home worker | A public link without paying for a GPU server, and the worker only makes outgoing calls, so no router setup |
| Photos are deleted once judged | Friends' photos stay on the server for as short a time as possible |
| Installable app, fonts bundled with it | It has to open with no signal, so there are no CDN files |
Things that broke, and what I changed
- The spa. My first test photo was my own room. Gemma called it a massage or spa area and invented a man "preparing materials". An open-ended "describe this" prompt invites guessing. Now the judge lists only what it can see, and then decides whether it matches the quest.
- Three petals. Gemma wrote a quest asking for "the brightest flower with exactly three visible petals". Nobody could finish it, and a small model can't count anyway. Quests now follow a rule (no numbers, nothing rare), invalid ones are thrown out, and Gemma writes a bank of them ahead of time so Swap quest is instant.
-
The one-minute wait. Every AI task took up to a minute. My first guess was that the model was spilling onto the CPU.
ollama pssaid 100% GPU, so I was wrong. The cause was Gemma 4's "thinking" step. Turning it off took judging to about four seconds. - The room that kept passing. Walk photos taken indoors were being accepted. The judge now also says whether a photo looks outdoors, and rejects only on an explicit "indoors", so a close-up of a leaf isn't punished.
- The browser experiment. I tried running Gemma inside the phone's browser with WebGPU, which would have removed the home judge. It worked on my laptop. My phone stopped with "the device (webgpu) does not support fp16". The roots stay at home.
I built this with help from an AI assistant (Claude) for code and planning. The testing and the decisions were mine, and they're all written down in the repo (decision.md, flow.md).
Why Does Open Innovation Matter?
- The AI runs on my laptop, not in someone's cloud. A 4 GB graphics card was enough for a vision model to judge photos in about four seconds.
- My friends' photos stay with a machine I control. The small hosted server holds a photo only until it's judged, then deletes it. A closed API would receive every one of them.
- I could change how it behaves. I switched off the thinking step, rewrote the prompt, and set the confidence threshold myself. That is how I found and fixed the minute-long wait. A hosted API wouldn't let me do that.
- It costs nothing per photo. The only bill is a small host for the mailbox.
Where open was worse: a larger closed model would likely read tricky photos more reliably, and it would judge at any hour. Mine only judges while my laptop is on. That's the price of keeping the roots at home, and for a game about friends going outside, I'd take that trade again.
Prize Categories
- Gemma: Gemma 4 E4B, running locally through Ollama, judges every photo and writes the quest bank.
- Render: hosts the app and its mailbox.
Thanks to the Gemma and Ollama teams for making a vision model run on an ordinary laptop, and to my friends for being the test squad.



Top comments (0)