Skip to content
ROVE Labs
Mobile appsEducation

Theorio: a Dutch car theory app with its own 3D traffic engine

Our own product. An Expo app for the Dutch car theory exam where every traffic situation is generated and solved by a rules engine, drawn in three.js inside the app, and explained with the article of law behind it. It also lets you drive an Amsterdam canal street in 3D.

  • Start
  • The Route
  • A 3D situation, explained
  • The Amsterdam drive
  • Hazard perception
  • Sign cards

1,200

generated 3D traffic situations

2,370

practice questions in four banks

140

hazard photos from 338 candidates

30

practice exams in the real format

Challenge

Learning for the Dutch theory exam usually means memorising a fixed set of pictures. You learn the picture, not the rule, and the first unfamiliar junction on the exam throws you. We wanted a course that can show an endless number of junctions, always knows the right answer, and can say why with the law in hand. And it had to work where people actually study: on a phone, a few minutes at a time. That meant four hard things: priority rules precise enough to compute, pictures that are drawn from data, a question bank that stays correct when the law changes, and 3D that ships inside a phone app.

Solution

  1. Engine first

    We wrote the priority rules as a tested engine before drawing anything. A situation is data, the answer is computed, and each step in the answer points at its article.

  2. Draw from data

    A three.js renderer builds every scene from primitive shapes. It only draws what the engine decided, from above with arrows or from behind your own car.

  3. Content pipelines

    Written questions are drafted against stored law text and verified. Hazard photos are generated from written specs and picked by a reviewer against a checklist.

  4. One app instead of a website

    We rebuilt the interface as a single Expo app and retired the web version. The engine, the renderer and the API stayed; both 3D scenes are bundled into the app.

  5. A course and a drive

    Fourteen chapters, each a short road with a video, theory, three rounds of questions, a 3D drive and a test, plus thirty practice exams in the real format. Three chapters and one exam are free.

Results

Theorio is in development and not yet released, so there are no learner results to report. What exists today is the app running in the iOS simulator, in Dutch and English, against its own API: the onboarding, the Route with fourteen chapters, all four question banks with their law citations, sign cards on a spaced schedule, the Amsterdam drive and thirty practice exams. Still open are payment in the app, the lesson videos, the drawings in the theory, accounts, reminders and more streets to drive.

(01)

A rules engine that works out every answer

Most theory apps store a picture and the letter of the right answer. Theorio stores neither for its traffic situations. A situation is a small data model: a junction with up to four arms, each with its road type, sign, traffic light or zebra, and two to four road users with where they come from and where they are going.

The engine first checks which paths actually cross or merge. For every pair that conflicts it applies the Dutch priority rules in a fixed order: emergency vehicles, zebra crossings, exits, signs, unpaved roads, trams, traffic alongside, the bent priority road, turning, and finally traffic from the right. Traffic lights and roundabouts have their own rules on top. Those pairwise decisions are layered into an order of who goes when.

Because the answer is derived, the explanation comes for free. In the app it is the answer screen: numbered badges on the vehicles, one line per road user, and under each line the article of law that decided it.

situations in the generated bank
1,200
situation types
7
priority rules
12
engine tests
52
  1. 01

    Model

    Junction, signs, lights and two to four road users, validated so impossible scenes are rejected.

  2. 02

    Conflicts

    Which paths cross or merge. Road users that never meet do not have to wait for each other.

  3. 03

    Decide

    For each conflicting pair the highest applicable rule decides who yields.

  4. 04

    Order

    The pairwise yields are layered into one order. Ties and deadlocks are thrown away.

  5. 05

    Explain

    Each step carries its rule and the article it comes from, in Dutch and English.

Who goes first?
Who goes first?
Answer by tapping a vehicle
Answer by tapping a vehicle
The order, with the article per vehicle
The order, with the article per vehicle
Or tap the whole order
Or tap the whole order

(02)

The same three.js scene, packed into the app

The renderer is a separate package that only draws. It receives a situation and an order from the engine and never decides priority itself, so the picture can never disagree with the answer.

There are no model files. Cars, trams, scooters, cyclists, pedestrians, roads, kerbs, shark teeth, zebra bars, signs and traffic lights are all built in code from primitive shapes. For the app we bundle that renderer into one self-contained page of about 640 kB. It ships inside the app and runs in a web view, so drawing a junction needs no server and no download.

React Native hands the scene over as data and gets taps back as messages: tapping a car in the picture selects the same answer as the button below it. The camera has two positions, an overview with an arrow for every path and a view from behind your own car for questions about what you should do. Everything around the scene, from the answer buttons to the feedback sheet, is native.

Roundabout with shark teeth
Roundabout with shark teeth
Priority road, seen from your own car
Priority road, seen from your own car
Zebra crossing at a junction
Zebra crossing at a junction
Exit
Exit

(03)

A drive through Amsterdam

A junction seen from above teaches the rule. It does not teach you to see the moment coming. So the app also has a drive: you follow your own car up a canal street at 30 km/h, past canal houses, parked cars, houseboats and cyclists.

The drive stops twice. First for a hazard: a pedestrian steps into the road, and you choose between braking, releasing the accelerator and doing nothing. Then at the bridge, where a tram crosses and you say whether it goes first. That second answer is not scripted. The junction goes to the same rules engine as every other situation, and the drive plays on from what you answered.

The street is built the way the junctions are: in code. The house fronts, the trees, the tram and the brick paving with its textures are generated when the drive loads, in about 2,600 lines of TypeScript and without a single model or image file. For now there is one street. It is a stop on the Route and a tile on the start screen.

street so far, an Amsterdam canal
1
stops: a hazard and a junction
2
model or image files
0
km/h, as the zone sign says
30
The street before you set off
The street before you set off
First stop: what do you do?
First stop: what do you do?
Braked for the pedestrian
Braked for the pedestrian
Second stop: the tram
Second stop: the tram
The tram goes first
The tram goes first
End of the drive
End of the drive

(04)

A course shaped like a road

The app opens with a language choice and three short questions: when your exam is, how many minutes a day you have, and whether you want to follow the Route or practise freely. The answers become a plan you can change later.

The Route has fourteen chapters. Each chapter is a short winding road with five stops: a video, the theory, three rounds of ten questions, the 3D drive and a test you pass with eight out of ten. The start screen shows where you are on the Route and what is due today, with a tile for everything you can practise on its own.

A streak, points and a daily goal keep score. The theory can also be read on its own, chapter by chapter, with a search across all of it.

chapters on the Route
14
stops per chapter
5
rounds of ten questions
3
to pass a chapter test
8 / 10
Welcome
Welcome
When is your exam?
When is your exam?
Route or free practice
Route or free practice
Your plan
Your plan
Start
Start
The Route
The Route
Chapters
Chapters
Theory
Theory

(05)

Written questions, each tied to an article of law

The written questions cover what a 3D scene cannot: speed limits, parking, lighting, documents, alcohol, loading. We stored the relevant Dutch traffic law locally, ten texts from the government's own publication, split per article.

Every question is drafted with AI against the stored text of one article and then checked by an independent verifier. The question keeps its source and article number, and the learner sees that citation under the explanation.

An automated test checks every question on each change: the cited article must exist, the photo or sign must exist, the answer options must be complete and both languages must be present. A question you miss comes back the same day and then after one, two, four, seven and fourteen days. The 154 signs are also flashcards: you rate each card with one of four buttons and the standard SM-2 schedule decides when you see it again.

written questions
730
law articles stored
2,888
sign questions from 154 signs
300
languages, Dutch and English
2
  1. 01

    Store the law

    Ten texts saved per article, with the date of the version used.

  2. 02

    Draft

    AI drafts a question against one article, in one of three formats.

  3. 03

    Verify

    An independent verifier checks the draft against the same article.

  4. 04

    Test

    Automated checks on citations, images, options and translations.

  5. 05

    Review

    Reported and often-missed questions go to a review queue in the API.

A rule question
A rule question
The answer, with its source
The answer, with its source
Which sign is it?
Which sign is it?
A sign card
A sign card
How well did you know it?
How well did you know it?
Theory, one page at a time
Theory, one page at a time

(06)

Sampling hazard photos instead of shooting them

Hazard perception needs photos from the driver's seat: a ball rolling between parked cars, a pedestrian stepping onto a zebra, a tractor filling the lane ahead. Shooting those safely and legally on Dutch roads is slow and expensive, so we generate them.

Each scene starts as a written spec: what the photo shows, the speed you are driving, the right reaction, and a checklist of what must be visible. For every spec we generate two or three candidates and compare them against that checklist. A reviewer who did not write the spec picks one, or rejects all of them.

We ran a trial with two image models on the same five prompts first. One matched the checklist three times out of five, the other five out of five, and that settled the choice. The most common reason to reject a photo turned out to be distance: the model draws almost everything two to four times closer than asked, which changes whether braking is the right answer.

scene specs written
159
candidate photos generated
338
photos in the app
140
brake, release, nothing
49 / 45 / 46
Three generated candidates of a ball rolling between parked cars in a Dutch street
Three candidates for one spec: a ball between parked cars at 30 km/h
Three generated candidates of a pedestrian with a pram at a zebra crossing
Three candidates for a pedestrian stepping onto a zebra crossing at 50 km/h

(07)

Practice exams in the real format

Thirty numbered practice exams follow the format of the real one: fifty questions in thirty minutes, pass at forty-four. Each exam mixes rule questions, signs, 3D situations and hazard photos, and nothing is marked until you hand in.

A map of fifty dots shows which questions are answered, open or flagged, and jumps to any of them. Pausing keeps your answers, but the clock runs on, as it would in the exam room. Afterwards the result is split per part and every mistake goes into the repeat queue with its explanation.

numbered practice exams
30
questions each
50
minutes on the clock
30
right to pass
44
Thirty exams, the first one free
Thirty exams, the first one free
A photo question under the clock
A photo question under the clock
Hazard perception at 80 km/h
Hazard perception at 80 km/h
Pausing does not stop the clock
Pausing does not stop the clock

Next step

Want something like this?

Tell us about your version of this problem.