Adventures with Makeblock mBot and Typescript

I have so far not been successfully in this "teach your kids programming" thing. My three sons are technical but have not yet demonstrated any inclination to code.

Thinking I could help them find the inner fire, so to speak, I bought a programmable "robot" from China a few years ago - the mBot by Makeblock. It then proceeded to sit on my shelve and collected dust.

The thing was, I couldn't get past the block-based programming environment in mBlock IDE. It felt unnatural and constrained - I've only ever programmed in a text editor / IDE, and these visual tools confuse me.

However, having had zero experience with Arduino, upon which the mBot is based, I could just effortlessly drop into the text editor and start hacking. And I suspect that even if I could, it would not be the most friction-less way of teaching my sons to code.

On the shelf the robot sat.

Come the Great Corona Lockdown of 2020, I was gifted an extra portion of free time. One day I noticed the blue robot staring at me from the bookshelf, motionless. Hey, buddy! Could we rekindle our friendship?

It turns out we could. As it happens, I can talk to my robot in Javascript. Or better yet, Typescript.

What can the mBot do?

Simply put: it moves (two wheels with motors at each side with a single front wheel for support), it sings (or rather, squeaks), it blinks (two programmable LEDs), it can sense distance, follow a line, and when equipped with additional sensors, it gains additional powers.

Importantly, it has Bluetooth, and can wander about as instructed, wirelessly.

I think that's a pretty good basis for exploration and tinkering.

The mBot Javascript SDK

Suffice to say, I am late to the party. Perhaps too late?

There's a repo by Makeblock with Javascript SDK that was last updated in December 2016. Getting to run the simplest example on my robot was not trivial.

I had to downgrade Node to 8.9 to be able to compile the native bindings of some 3rd-party dependencies, which led to me install nvm for Windows as I don't intend to use this ancient version for my daily business.

The examples then ran but looking at the code, I did not feel motivated to expand on it and work out my own examples. After having adopted Typescript a few years back, I did not want to return to plain-old untyped Javascript.

What would it take to convert this into a Typescript project?

I didn't want to rework the existing samples, of course, but rather write my own and learn how to talk to my robot in a typed fashion.

Bringing the dependencies into 2020

The first step was to update the dependencies. The repo relies on the johnny-five and node-pixel Javascript frameworks to do the heavy lifting, and I wanted to have their latest features at my disposal.

I bumped Node to 10.*, which seemed to suffice.

After managing to install everything, which on Windows is not without pitfalls, the code ran without erroring out before reaching my robot but then failed because of an incorrect, or rather unexpected, firmware version.

The firmware we're talking about is called "Firmata" and implements a protocol for talking to microcontrollers (such as Arduino).

What I had to do was add the mBotFirmata sketch to the latest version (2.5.8) of the Arduino firmata, adding the drivers for the WS2812 LED strips used on the mBot from the node-pixel repository, and - surprisingly for me - it almost worked on the first try. Due to a defect in the current version of node-pixel that apparently does not support the newest firmata, I had to patch a single line in the node-pixel library to get past the startup errors.

Lo and behold, the LEDs blinked, the the wheels moved, my robot came alive.

Typescript FTW

Starting from scratch, using Typescript is trivial. Adjust the tsconfig.json to your liking / standards, and you are good to go.

It gets trickier with your dependencies and whether they've published their types or not. It turned out that johnny-five has while node-pixel has not.

To make my IDE experience smoother, I've stubbed some interfaces for objects and their methods from node-pixel that I'm going to be using and will add to them as I progress. Perhaps I can submit a PR at the end of this exercise.

It's hard to overstate how much value Typescript adds to a Javascript project. Even if this is just a toy project, I still want the solid Typescript refactoring experience in VS Code and be able to spot stupid errors and typos in an instant.

My first mBot program

Let's not shoot for the Moon and start simple. I want the robot to wander around my sizable working desk, blink, and if it sees an object approaching, emit a panic signal and back-off.

Current status: it only drives forward and would fall off the desk if I don't stop it. When it senses my hand, it blinks rapidly and backs off for a moment.

I don't think there's a sensor that would tell the robot it's about to fall off, and so I might try to put it in a playpen or something.

You'll find the code in the toys/scared.ts file if you want to see what I've done so far. Not much to write home about yet, frankly.

It's a bunch of functions but I'll convert it to a class as I think the object-paradigm fits it like a glove, given that the mBot is an actual object in the actual universe.

Could I use this to teach my kids to code?

Yes, I think I could, now.

What I'd like to do is to put together a few useful classes, abstractions on a sufficiently high level that they would feel like those "blocks" from the MBlock IDE without having to be visual.

I think that since programming is text-based, teaching programming should also be driven by textual interaction. The right level of abstraction is crucial, though, as I'd rather not start from bytes.

Having said that, the awareness of the existence of bytes (and strings, and numbers, etc.) early on will be useful in the education of my kids, should they eventually become interested. That's why I'll continue playing with my mBot with Typescript and not just Javascript. Hopefully I'll have something interesting to show them someday soon.