Cheaper way to control Hoverboard motors

10 min readMay 13, 2023

Just some background, if you follow my blog I had written an article Building Hoverboard Robot a while ago. In that article, I used a more a clone of ODrive board which was still fairly expensive and it died after few days, leaving my project unfinished. Since then I have been on hunt for a replacement motor controller board that I can use to revamp the project. I found a cheaper board when I came across youtube videos and blog articles from MadEE [links in reference section] on how to use RioRand ZS-X11H motor controller board which has a rating of 350W 6–60V. This means it can drive the hoverboard motor driven by a 36V battery. This article is my experience on how I used that board to drive two hoverboard motors using Arduino Nano. However, once you know the basic setup you can pretty much use any microcontroller like Raspberry Pi Pico, ESP32, Teensy or RPi4 to control the speed and direction. It’s not a perfect board by any means but it gets the job done at much cheaper price point [around $18 each]. I actually messed up a couple of these before I got my technique right but it is cheap enough where you can afford to make mistakes.

The board layout from product description as there is no other documentation available.

Components needed for the project

  1. Hoverboard and potentially build the robot frame on top of hoverboard. I described this in my article in detail on how to do this
  2. Arduino Nano [I used the one from Seeduino, I like the quality and documentation of their components]
  3. RioRand ZS-X11H motor controller board [Quantity — 2]
  4. Pin headers, wires, a jumper and additional JST headers mentioned in next section

Preparing ZS-X11H board for use

Even though the ZS-X11H board is a really good quality board the manufacturer has not made it easy to use. In order to properly use the board I ended up making two changes to the board before I could use it.

  1. Solder 2-pin header to install jumper to enable PWM control unpopulated by manufacturer
  2. Install a JST male header for PWM Control header that is unpopulated from manufacturer

You need to install a 2-pin male header in the location shown below. You can typically just get a set of headers from Amazon or anywhere else and cut two pins out of there with a utility knife. This is standard 2.54 mm spacing header and they are available everywhere.

I tried to just fill the two holes with solder directly but I’m not very good at soldering so I ended up damaging the board. So final solution was to solder 2-pin male header on the back of the board and then install the standard jumper to short the pins. This is a lot more elegant solution since you can always remove the plastic jumper to test the board using the potentiometer that is on the board.

Tricky part here was, I had to unscrew the big aluminum heat-sink that is on the back of the board and only then I was able to access the location to solder the 2-pin header.

Second step is to install the PWM control header next to the Encoder header [marked in black rectangle above]. The manufacturer supplies the Encoder header pre-installed as JST style male header on the board. However, they did not pre-install the PWM Control header and you can see those 5-pins next to the Encoder header are just empty holes unpopulated by the header pins. I believe the pitch on this particular holes is 1 mm or 1.5 mm [not standard 2.54 mm] so I had to purchase a few different parts by trial and error before I found the one that fit the pitch. Here is the link to the header that fits on amazon. This is a kit that comes with pre-crimped wires so you can build your own connectors. I tried installing standard male pin header but those were not tall enough to have a proper grip with the dupont wires and those kept coming off during testing so better solution would be to install proper JST style header that will lock in the wires.

We are only going to use P and S pins from the PWM Control Header so if you feel that installing JST header is an overkill and you can just solder the wire directly to P and S pins you can do that. However, just know that it is not a very robust solution and you might end up damaging the board.

Wiring & Programming

I followed the detailed instructions from MAD-EE’s blog article to first get single motor controlled from an Arduino Nano and then modified the code to control two motors. All his code examples worked without a hitch in first try. You can simply copy paste the code from his final code section and make sure your pin numbers are same as in code before uploading the code to Arduino Nano.

Here is the Wiring Diagram I ended up with for Arduino Nano to control both motor controllers.

It was hard to show 3 phase wires [Ma, Mb, Mc] from motor going from motor to top left screw terminal marked by thick Red line so make sure to connect appropriate phase wires from hub motor to proper pins on ZS-X11H.

Same is true for the encoder wires going from motor to Encoder JST connector that is pre-installed on the ZS-X11H marked by thick purple line in wiring diagram. There are 5 wires for hall encoder for hub motor — Gnd, Hc, Hb, Ha, 5v.

Also, connections from Arduino Nano to both ZS-X11H are marked with different colors and text labels in the diagram and I have also provided two pin mapping tables for left and right motor controller to Arduino Pins.

During this test Arduino Nano is powered by the USB cable from laptop computer and we are using the same cable to power and upload the Arduino code.

Pin mapping table for more details:


Basic Test to run motors without PWM Control

After you have completed the prep of the board and finished wiring everything, we can test the running of motors without actually programming via Arduino. In order to do that first make sure power is off to all the boards.

  1. Remove the jumper that shorts the PWM Enable pins [2-pin header you soldered in during prep]
  2. Make sure the Blue potentiometer on the board is turned fully anti-clockwise as far as it can go. [clockwise increases speed and anti-clockwise decreases the speed so we want to start from zero].
  3. Make sure you have propped up the hoverboard on a stand or a strong box so if the wheels are turning its not going to run off the table and damage anything

At this point you can turn the battery power ON and slowly turn the blue potentiometer on Left motor controller ZS-X11H board clockwise. The left motor should start turning slowly and you can slowly increase and decrease the speed. This test can be done one motor at a time. So after you have finished testing Left motor turn the speed down to zero and run the same test on Right motor controller by turning its potentiometer.

After the test is complete turn the blue potentiometer on both of the ZS-X11H boards to zero position. At this point, we know all the power and encoder connections are correct and motors can be controlled by ZS-X11H properly.

Keep in mind this board requires that the encoder wires are plugged in as well otherwise the motors will not turn.

You can also install the PWM control jumper again before we can run PWM control tests.

PWM Control Test

Before running this test make sure of these things:

  1. Blue potentionmeter on both ZS-X11H cards is turn to fully anti-clockwise which is zero position
  2. PWM control enable jumper is installed on the 2-pin header
  3. Encoder cables are connected with correct motor for each card

At this point you can connect the USB cable from laptop to Arduino and upload the code from Final Code section of MAD-EE blog article.

In the code pay attention to these lines at the top. These pin numbers map to our Right Hub motor so when you run the test it will move the right side motor only. You can change the pin numbers here to left motor pin numbers from the tables and you will be able to test the left motor in the same way. However, this example code only runs one motor at a time.

const int PIN_DIR = 2; // Motor direction signal
const int PIN_BRAKE = 3; // Motor brake signal (active low)
const int PIN_PWM = 9; // PWM motor speed control
const int PIN_SPEED = 12; // SC Speed Pulse Output from RioRand board
const int PIN_DIR = 4; // Motor direction signal
const int PIN_BRAKE = 5; // Motor brake signal (active low)
const int PIN_PWM = 10; // PWM motor speed control
const int PIN_SPEED = 11; // SC Speed Pulse Output from RioRand board

After uploading the code to Arduino, launch the serial monitor window and make sure to set the baud rate to 115200 as expected in the code otherwise you’ll see junk characters.

At this point you can run following commands in the serial monitor [make sure newline character is set to carriage return before entering commands in serial monitor].

For starting the motor at low speed enter:


This will run whichever motor you are testing with the pin numbers in the code to duty cycle of 10. You can increase or decrease the speed by entering different duty cycle or stop the motor by entering duty cycle of 0.

You can also break the motor by entering break command:


Break command with 1 will enable the break meaning motor will stop and Break command with 0 will disable the break meaning break is off and motor can move. However, if you previously sent break command with 1 and then send a PWM command with duty cycle non-zero the motor will not move until you run another Break command with 0.

The last command is DIR or direction command. You can change the direction of motor rotation by running:


This will move the motor forward and if you change the direction by sending 0 it will move in backward direction.

Be careful changing the direction of motor while it is running at high speed in one direction. Always stop or break the motor before changing the direction to avoid causing damage to your setup.

If you are interested in controlling both motors at the same time you can refer to the code in this repository that allows you to send PWM commands to both motors at the same time. However, this requires some additional code changes and that is currently work in progress. I’ll share the details when I have successfully tested the code.

It has been a painful journey with lots of stops and starts to find motor controller that can be used to control hoverboard motors that is not going to break the bank and it can be used to convert a hoverboard into a ROS2 controlled robot and this is another small step in that journey.

Thanks so much to MAD-EE for sharing youtube videos and code in public domain it has been a great help. In addition, thanks to folks in robotics/ROS community for sharing ideas to keep this project going.

Hope this was helpful. Have fun building!!


RioRand ZS-X11H link to Amazon —