Introduction: Javascript Robotics and Browser-based Arduino Control

Picture of Javascript Robotics and Browser-based Arduino Control

Use your JavaScript and web development knowledge to control Arduino projects and even robots (node + robots = nodebots)!

This is made easy with node.js, Firmata and Johnny-Five. Let's get started!

Johnny-Five logo by Mike Sgier. Arduino photo CC-BY Raeky.

Step 1: Install Node.js

Picture of Install Node.js
Node.js is a javascript runtime based on Chrome's V8 engine. If you haven't used it before, node lets you run Javascript code on the server-side, it's designed around non-blocking I/O and asynchronous events. Node includes modules for accessing the filesystem, a web server, sockets and other basic tasks.

Download and install the node for your platform. Source and binaries are available for Windows, OS X and Linux.

http://nodejs.org/download/

If you're using Ubuntu/Debian, you can use apt-get install nodejs (not node). If you're using a distro's package manager, make sure your node version is recent!

node --version
v0.10.26

Step 2: Install Johnny-five

Picture of Install Johnny-five
Johnny-Five is an Arduino control framework for Node. It works with Firmata firmware to enable you to do things like blink lights and control servos.

Create a folder for your project and use Node's package manager, npm, to install johnny-five.

At the command line use npm install as follows:

npm install johnny-five


If you'd like to create a web interface you'll need socket.io too:

npm install socket.io
 

Step 3: Upload Firmata to Your Arduino

Firmata is a protocol for communicating with microcontrollers via a host computer. There are interface libraries available in Python, Processing, Javascript, Ruby and many other languages. Firmata sketches are included with the Arduino IDE.
  1. Download and open the Arduino IDE
  2. Go to File -> Examples -> Firmata -> StandardFirmata
  3. Upload Firmata to your Arduino board

Step 4: Blink Sketch ... in Javascript

Picture of Blink Sketch ... in Javascript
As is tradition our first sketch will make the on-board LED blink!

Create a file called ledtest.js with your favorite text editor. Connect your Arduino, copy the code below and run node ledtest.js at the command line. You should see a blinky LED!
var five = require("johnny-five"),board, led;

board = new five.Board();

board.on("ready", function() {
  led = new five.Led(13);
  led.strobe(1000); // on off every second
});

Troubleshooting:

Johnny-five will try to find your Arduino automatically. If this doesn't work you can specify a serial port in the Board constructor, like so:
board = new five.Board({ port: "/dev/tty.usbmodem1234" });
 
LED c/o OpenClipart
 

Step 5: WebSockets

WebSockets allow full-duplex communication between your browser and the server. You can use them to pass messages and events, and as you might imagine this is quite useful for data-logging or controlling a microcontroller or robot!

We're using socket.IO, a wrapper that makes using WebSockets very simple. It takes into account the differences between browsers, handles gnarly back-end tasks like disconnections, heartbeats and timeouts so we can focus on the fun stuff.

Socket.io provides example code, we can use it with a little modification to control our Arduino with johnny-five.

Socket.IO Usage

Emit an event called 'message'

socket.emit('message', { hello: 'world' });
 

Process an event called 'incoming' and print out the data

socket.on('incoming', function(data) {
    console.log(data);
});

Step 6: Create a Web Interface With Bootstrap

Picture of Create a Web Interface With Bootstrap
The attached code uses Bootstrap, a responsive front-end framework, to create a simple web interface that can set a servo position, change a LED blink interval and read data from an analog pin.

If you followed the previous steps you should be able to run node webtest.js at the command line, visit http://localhost/ to start controlling your Arduino!

Once you can understand this you're well on your way to advanced Browser-to-Arduino hacking and nodebots (the johnny-five repo is an excellent resource for example code)

An example: on the browser side, when you click on 'Set Delay' emit a socket event 'led'

$('#ledSet').on('click',function(){
        // parse number from led delay value
        var tmp = parseInt($('#ledDelay').val(),10);
        // print out
        console.log("Setting LED Delay:",tmp)
        // send socket message of delay
        socket.emit('led',{delay:tmp});
  });

On the server side, your message is processed and the strobe value adjusted:

socket.on('led', function (data) {
    console.log(data);
     if(board.isReady){    led.strobe(data.delay); }
  });

Step 7: Additional Resources

Picture of Additional Resources
Further reading and resources:

Pictured, "phantombot" a Sumobot Jr at JSFest

Comments

FuatA1 (author)2017-04-01

Hi, thanks for tutorial. I want to control my Arduino via my web page ( http://www.safehouse.besaba.com/ ). I want to use wifi shield. Is Johnny Five support this? I know it using usb cable and Firmata library. Is Johnny Five works on just local host? Any way to use it in a server in hosting firm like Go-daddy?
Thanks.

ankur198923 (author)2016-08-02

Great tutorial!!

I am newbie to arduino as well as to node.js. I followed the steps as it mentioned in the tutorial but not able to run the code. I am getting below error -

Error: Cannot find module 'johnny-five'
at Function.Module._resolveFilename (module.js:440:15)
at Function.Module._load (module.js:388:25)
at Module.require (module.js:468:17)
at require (internal/module.js:20:19)
at Object.<anonymous> (C:\Ankur\Arduino\ledtest.js:1:72)
at Module._compile (module.js:541:32)
at Object.Module._extensions..js (module.js:550:10)
at Module.load (module.js:458:32)
at tryModuleLoad (module.js:417:12)
at Function.Module._load (module.js:409:3)

Could you please help me in resolving the same.

Thanks and Regards,

Ankur

tyrellperera made it! (author)2016-05-21

Thanks!

This got me started on a proof of concept I'm working on.

LeonardoM15 made it! (author)2016-05-03

Thanks!

HannahMitchiell14 (author)2016-04-23

Hi, I'm a newb to all of this and having an issue. I'm on mac and using MAMP to upload to my localhost. I managed to get all the steps working until Step 6. In my console on my localhost I get 'Failed to load resource: the server responded with a status of 404 (Not Found) http://localhost:8888/socket.io/socket.io.js' as well as 'ReferenceError: Can't find variable: io'. My Arduino has the LED on but none of the HTML controls do anything to change it. When trying to run 'node webtest.js' in terminal when in the MAMP localhost folder, I also get a ' events.js:141 throw er; // Unhandled 'error' event' appear. If anyone can help at all it would be very appreciated!

Lewism18 (author)2016-04-18

Hi I am looking for a forum to discuss the johnny five module. Do you have any good suggestions of online communities?

Onairam (author)2015-11-19

Awesome! , thanks for the tutorial, but:

i dont have any servos, so the web page doesn't do anything to my arduino; how can i turn on and off different leds depending on which button i press?

I couldn't figure out how to do it

MathieuH2 (author)Onairam2015-12-13

You would have to wright a function that does that.

moises.serrano.3956 (author)2014-09-04

exelent port :D

i was trying to acces localhost from other computer on my network and i can look the page but dont allow me to make change, what can i do ?

You cannot access localhots via another computer. localhost always* refer the curent computer. If you want to access one computer via another, you'll have to find it's IP address and use it instead of localhost. If you localhost computer IP is 192.168.1.100, then on the other computer you should use http://192.168.1.100 instead of http://localhost.

*Not always, but if it's not the case, your either a ninja in networking, or should call tech support.

snoop911 (author)2015-02-13

Instead of an arduino, could an launchpad msp430 be used?

I have the latest firmata running correctly (or so I think) on the launchpad, but I don't have any way of seeing if it speaks firmata to the pc. I'm new to node.js but I believe it installed correctly.. same with Johnny5.

Is there a sample script that will query the launchpad for the firmata version string?

Also, the instruction:

If you'd like to create a web interface you'll need socket.io too:

How do you run node.js scripts without the use of the web interface? I thought you execute a node.js script by opening a browser with the url : http://localhost:3000 . Is there another way to run node.js?

MathieuH2 (author)snoop9112015-12-13

"How do you run node.js scripts without the use of the web interface?"

You have to run it via terminal `node scriptToRun.js`

GregS15 (author)2015-04-18

This may be obvious to some, but where does the JavaScript code execute? Is it on the computer or the Arduino?

MathieuH2 (author)GregS152015-12-13

On your computer. Node.js execute the code.

pete54321 (author)2015-10-03

Great tutorial!

I'm having a little trouble when I get to the websockets section. When I run 'node webtest.j's' I receive an error message stating "TypeError object Serialport has no method 'write'"

Any ideas on what I'm doing wrong?

Dutchess1 (author)pete543212015-10-03

Try installing without npm;

git clone git://github.com/rwaldron/johnny-five.git && cd johnny-five



npm install

Rahul27 (author)2015-09-21

Nice project. Is there a way to use this with esp8266? Here is the plot: start an ACcess point and webserver on esp8266 programmed using arduino ide. Run code on esp8266 that can intercept data from a smartphohe running webapp that communicates via websocket. Is this possible?

hthl85 (author)2015-06-06

excellent!!! :)

carolinebuttet (author)2015-03-13

Thank you! I hooked up a simple force sensor to an Arduino and managed to browse Google Maps with it!



danasf (author)carolinebuttet2015-03-13

Well done, very cool :D

rrider2 (author)2015-02-01

thanks! https://www.youtube.com/watch?v=ps-6U2mv5JY

jelimoore (author)2014-05-03

I cannot get it to work when I specify a board like so:

board = new five.Board({ port: "/dev/tty.usbmodem1431”});

My Terminal says:

/path/to/file/but/this/isn't/it/ledtest.js:3

board = new five.Board({ port: "/dev/tty.usbmodem1431”});

^^^^^^^^^^^^^^^^^^^^^^^^^^

SyntaxError: Unexpected token ILLEGAL

at Module._compile (module.js:439:25)

at Object.Module._extensions..js (module.js:474:10)

at Module.load (module.js:356:32)

at Function.Module._load (module.js:312:12)

at Function.Module.runMain (module.js:497:10)

at startup (node.js:119:16)

at node.js:906:3

danasf (author)jelimoore2014-05-03

Hello, check your trailing quotation mark, it's curly, I think that may be tripping things up!

board = new five.Board({ port: "/dev/tty.usbmodem1431"});

About This Instructable

73,938views

121favorites

License:

Bio: Sharing knowledge and ideas. Constantly learning!
More by danasf:Intel Edison and Addressable LEDsInternet of DucksLighting In A Bottle
Add instructable to: