Rohan Deshpande Build log · May–Aug 2026

Ninebot Gokart Pro → drive-by-wire → autonomous

Teaching a go-kart to drive itself.

After years of racing rental karts, I wanted to buy my own and race it. Although, I couldn't afford one, so I bought a $300 kart and spent the summer after high school modifying it: only to remove the driver entirely.

The finished remote-controlled go-kart on a hardwood floor, with a webcam mounted on a pole above the front bumper and wiring running back to a clear bin of electronics on the seat.
FIG 1End of summer. Steering, throttle and brake all driven from a Raspberry Pi over an Xbox controller; the webcam on the pole is there to start collecting training data for the autonomous phase.
Timeline11 weeks
Pedal solutions tried4
Steering motors tried4
Final gearbox47:1 ≈8 N·m
Steering limit±25°
StatusPhase 3 of 3
PHASE 1ASSEMBLE

Why a kart

Breaking down the problem

Real competition karts cost multiple grand. A Segway Ninebot Gokart — a frame that clamps onto a hoverboard — costs a fraction of that. Looking back, the kart was an incredible test bed, and understanding how it worked was easier than I expected.

I divided the project into 3 phases. Phase 1: build the kart. Phase 2: make every control — throttle, brake, steering — drivable from a game controller with no human in the seat. Phase 3: replace the human holding the controller with a model.

This was my first real engineering project. I had just graduated high school with basic CAD skills and a little electronics experience. Almost everything below is a record of being wrong about something and then finding out why.

A black Ninebot self-balancing scooter standing on a hardwood floor next to an unfolded instruction manual.
FIG 2May 24. The original Segway. The kart frame bolts around it and uses the base as a rear wheel drive kart.
The assembled white go-kart photographed from above, showing the seat, steering wheel, pedals and four wheels.
FIG 3Assembled. The first test drive taught me two things that shaped the rest of the summer: the brake pedal is pretty much an immediate stop, and the steering is extremely sensitive.
PHASE 2Remote Control

Problem 1 — the pedals

Four attempts to change the pedals.

Each one failed for a reason that made the next one obvious. In hindsight I basically went from 100% mechanical engineering to like 80% electrical engineering.

ATTEMPT 1 · MAY 26 – JUN 21

Push the pedal with a servo

Dead end

The obvious move. I mounted the servo to the front bumper, printed a cap that pushes the pedal, and linked the two with a rod. I measured the pedal force with a phone accelerometer: roughly 2.9–3.6 N. I then bought a 40 kg·cm servo which I thought could push the pedal.

Though, my measurement was completely the wrong one to make. A pedal behaves like a spring, so its resistance climbs the further you push it.

Why it failed: the servo horn and the pedal rotate about different centers. For the first few degrees this isn't noticeable, but after they start diverging the part cannot allow the servo to move further. On top of that, the servo simply wasn't strong enough for the brake, which is far stiffer than the throttle.

Two blue 3D-printed parts on a grey table: a pedal cap with a long thin connecting rod, and a servo mounting bracket.
FIG 4The pedal cap and linkage. I printed the part with the thin rod first, but the rod kept flexing as the pedal moved. Hence, I rebuilt it as a solid rectangle with the servo mounted very close to the pedal.
Two red 3D-printed servo mounting brackets and a red printed lever arm on a dark table.
FIG 5Bumper mounts. The tall one toppled whenever the servo rotated and would have been unsteady when the kart started moving. The version on the right is what I came up for my 2nd solution, which is discussed below.
ATTEMPT 2 · JUN 21 – JUN 25

Move the magnet instead of the pedal

Superseded

Before designing another bracket I took the pedal apart. Inside there is literally just a Hall-effect sensor on a small green board and a magnet riding on the pedal arm. Pressing the pedal only sweeps a magnet past a sensor.

This genuinely surprised me. Every go-kart I'd driven had mechanical pedals. So the new plan: skip the pedal entirely and print a rig where a servo sweeps the same magnet past the same sensor. I went through several designs for the column and the sensor mount.

Why I abandoned it: partway through this revision I realised I was just doing all this to make a sensor emit a particular voltage. If the voltage is all the controller sees, I should skip the sensor and just emit the voltage directly.

The inside of the pedal housing: a small green circuit board with a Hall-effect sensor screwed above a black plastic pedal mechanism.
FIG 6The whole pedal, opened. All that's there is a magnet and a Hall sensor.
A CAD screenshot of a grey servo bracket next to a tall slotted column, annotated with green dimensions.
FIG 8Revision: column moved to the far side, sensor relocated to the top.

The measurement that changed everything

What the pedals are actually saying

I connected a multimeter to the sensor's output, then slowly pressed each pedal to measure the voltage. This confirmed my initial driving test of the kart: the brake pedal is digital.

BRAKE DIGITAL 0.78 V 4.2 V 3.2 V STATE FLIPS HERE ACCELERATOR ANALOG 0 V 4.4 V PROPORTIONAL CHANGE CEILING ABOVE THIS THE KART EMERGENCY-BRAKES 0 1 2 3 4 5 V VOLTS AT THE SENSOR OUTPUT

The brake is effectively a switch. It swings between roughly 0.78 V and 4.2 V, but the controller only cares about one boundary near 3.2 V — cross it and the brake is on.

The accelerator is properly analog: the kart tracks voltage all the way up to about 4.4 V, and past that the kart's own safety system stops the kart completely. To summarize, the throttle outputs a continuous voltage while the brake is essentially an on/off switch.

ATTEMPT 3 · JUL 20 – JUL 28

Replicate the signal with a servo and a potentiometer

Worked, badly

A Raspberry Pi can't produce an analog voltage on its own — its pins are digital and can only output a max of 3.3 V. However, a servo can turn a potentiometer, which can output continuous voltages. So: controller → Pi → Adafruit servo HAT → servo → potentiometer → 0–4 V into the controller.

Getting there meant printing a coupler between the servo shaft and the potentiometer and figuring how to connect an Xbox Controller to the Pi.

Then I rotated a servo with a game controller for the first time.

Why it wasn't enough: the potentiometer only has 240° of useful travel and the mapping was unforgiving. Any overshoot past 0 V or 4 V made the kart either stop or accelerate rapidly. With nothing bolted down, a bump was enough to nudge the servo out of range.

Hands holding an Xbox controller in front of a laptop, a breadboard, a bench power supply reading 5.00 volts, a red 3D-printed part and a small servo on a desk mat.
FIG 9Setup for the first controller-to-servo test. Power supply on the left, printed coupler in red, servo on the right.
ATTEMPT 4 · JUL 30 – JUL 31

Modifying the kart's signal with a DAC

Worked

After digging through Raspberry Pi forums, I found the part all my solutions had been trying to replicate: a digital-to-analog converter (DAC). An MCP4725 takes a number over I²C and puts out a real analog voltage. No servo or potentiometer required! MCP 4725's were also cheap enough that I could use one per pedal.

Two of them share the same bus, so I had to physically change the address of one by soldering a connection. This was my first time soldering, which shows in the photo, and the wiring is pretty messy.

Result: both the accelerator and the brake driven from an Xbox controller through the Pi, with the throttle proportional to the trigger. I was halfway through Phase 2, and this was the first progress I made towards the actual, working solution.

A Raspberry Pi connected by jumper wires to a small breadboard holding two red MCP4725 DAC modules, on a black and red desk mat.
FIG 10Two MCP4725 DACs on one I²C bus — one for throttle, one for brake (only one wired is shown in the picture). Both run at the Pi's 3.3 V.
0.78 V4.40 V

Problem 2 — the steering

The pedals were an electronics problem. Steering was initially a mechanical problem, then it became a coding issue.

I spent a while trying to work out how to influence the steering wheel before noticing I could just take it off and turn the shaft directly.

MotorTorqueOutcome
NEMA 17 — Adafruit, 12 V
1.8°/step, 200 steps/rev
lowMoved nothing. I could turn the shaft by hand, so I'd assumed a small stepper would manage it.
NEMA 17 — higher current
5–24 V, 2.5 A
0.7 N·mMore current, same result. The shaft just couldn't move with only the motor.
NEMA 34highPlenty of torque, physically too large to mount anywhere on the frame.
NEMA 23 + 47:1 planetary
23HS22-2804S-PG47, 24 V
≈8 N·mTurned the wheels. The gearbox was the answer, not a bigger motor.

This immediately created a new problem. A stepper motor only knows how many steps it has taken since the program started. Hence, if I stopped the program and turned the wheels by hand, the motor's count would be wrong. I found this out by breaking a printed support.

The fix is a sensor that reports the real angle. I started with an MPU-6050 gyroscope on the same I²C bus as the DACs. By itself it was fine. Once everything was mounted on the kart it stopped working within ten seconds, every time. I tried shorter cables, a second MPU-6050, and a different I²C address; none of it worked. I reasoned that this was due to both the DAC sensors and this gyroscope overloading the bus line.

So I switched to a WT901BLECL, which connects over Bluetooth LE instead. It leaves the I²C bus alone and the connection has been stable since.

Seven 3D-printed steering coupler versions lined up left to right on a grey table, in red, blue and orange plastic, each slightly larger and more complex than the last.
FIG 11Every version of the steering coupler. Each one came off the printer, went onto the kart, and failed (alignment, size of the hole, etc). The next print got measured again with a dial caliper.
A CAD screenshot of a grey U-shaped bracket with a long slotted arm, annotated with green dimensions.
FIG 12Holder CAD. I stopped modelling from photographs after learning the hard way that a photo is always slightly off-angle — now I measure every part meticulously with a caliper.
Three 3D-printed arm parts in red, blue and orange laid side by side on a grey table, increasing in width and bracing.
FIG 13Three generations of the same motor holder. Each revision tried to solve the flexing issue, but none were a permanent solution.
Two white 3D-printed parts with support material still attached, sitting on the textured build plate inside a 3D printer.
FIG 14Print failure. This was common with pretty much every design. Issues included a dirty nozzle, dirty printbed, and incorrect filament settings.
A stepper motor held in a red 3D-printed wedge-shaped mount clamped to the front of the go-kart, with green and yellow wires running from it.
FIG 15An early motor mount on the kart. The angle matters: the mount has to hold the motor square to the steering shaft.
The geared stepper motor in a blue 3D-printed housing mounted high on the kart's steering column, with wires running down to a clear bin of electronics on the seat.
FIG 16The geared NEMA 23 inserted into the steering column.
47:18 N·m

Putting it together

The final stages.

Top-down view of the go-kart showing the steering motor at the front and a clear plastic bin on the seat holding a Raspberry Pi, breadboard, stepper driver and battery packs, with wires running forward.
FIG 17The whole system. The Pi, breadboard, stepper driver and power supplies are contained in a plastic bin strapped to the seat (temporary solution).
A desk with a Raspberry Pi, a stepper motor driver board, a small breadboard, a blue Xbox controller and a geared stepper motor all connected by coloured jumper wires.
FIG 18Before putting everything in the kart, I ran multiple tests to make sure the entire system was working.

A routine update broke every program I had written. A Raspberry Pi OS update moved the GPIO pins onto a different chip, and suddenly nothing ran. For an afternoon I was convinced I'd destroyed something expensive. It turned out to be a small fix that just meant altering the code to search for a different chip.

The steering had no failsafe. When the angle sensor dropped out, the motor kept acting on the last command it received — so if my thumb had been on the stick, it would keep turning indefinitely. I added a failsafe to where everything would stop immediately when the sensor stopped working. The code then retries the connection for fifteen seconds before throwing an error. Noise still lets it overshoot the 25° software limit to about 33° occasionally, which is the next thing to fix.

Some parts shouldn't be printed. The coupler between the steering column and the motor kept flexing no matter how much material I added. I got in contact with a local metal fabrication shop (CORRPAK), who very generously made the motor holder out of aluminum.

Rohan sitting on a stool holding a game controller, driving the go-kart which is raised off the ground on two folding stands in a living room.
FIG 19 Servo + potentiometer solution. I actually got far enough on this solution to test on the kart, but the margin between max acceleration and max emergency brake was ridiculously small. Testing on a stand also eliminated any friction on the tires, which caused problems when I actually needed to drive the kart outside.
Close-up of the go-kart raised on stands, with a hand holding a controller beside the steering motor and a bench power supply reading 24 volts in the background.
FIG 20This is when the 3d printed motor holder snapped, and I realized I had to have a gyroscope.
If I'd known how little time it takes to build a working solution once you have the right idea, compared to how long the project actually took, I'd be shocked. But I guess that's engineering. Notebook, July 26th
PHASE 3IN PROGRESS

What's next

Completely Autonomous Driving.

Phase 3 is to create and test an AI driving model.

The webcam in Fig 1 is mounted such that it sees a decent bit of track ahead. I aim to make every frame get saved alongside the steering angle and throttle value. This should be done session by session into separate folders so I can train on specific runs.

I'm working through a computer-vision course and setting up Donkey Car on the Pi. I'm also considering replacing the Pi with a more powerful Jetson.

The finished remote-controlled go-kart seen from the front-left, with the geared stepper motor on the steering column, the webcam on a pole, and a clear bin of electronics on the seat.
FIG 21August 12. Throttle, brake and steering all completed.