Javascript programming - Part II (My setup)
Javascript and Node.js
As you may suspect by the name, Javascript is a scripting language. The word script is typically used to describe small programs that are designed to perform simple tasks. However, I found that Javascript can actually be used to efficiently execute rather complex tasks too. While Javascript natively runs within a browser (making visualisation etc. very easy), the Node.js runtime environment allows one to run it outside of the browser too. However, Node.js also comes with a slightly different synthax. Fortunately, we don't have to bother with all these syntax changes ourselves if we get the setup right. There are probably multiple ways to do this, but below I show you my setup with Visual Studio Code.
Setting up Visual Studio Code
Visual Studio Code (VSC, https://code.visualstudio.com) is a light-weight coding environment that is available for all operating systems. It comes with syntax highlighting for pretty much all coding languages, and it has some great extensions that made my setup much easier to work with.
After installing VSC, let's start with the biggest coding cliche ever:
let codingcliche = "world"
console.log('Hello, ' + codingcliche + "!")
user@computer:~/Desktop/Javascript_tutorial$ sudo apt install nodejsuser@computer:~/Desktop/Javascript_tutorial$ sudo apt install npm
Then, you can simply run the following command:
user@computer$ nodejs main.js
Hello, world!
A basic object-oriented program
Object-oriented programming (OOP) is a programming convention many people enjoy, as it keeps your code modular and transparent. For the remaining parts of this series, I will focus on how to apply OOP to Javascript, and how to visualise the results.
As a minimal example, I wrote a simple program consisting of three files:
circle.js containing the class definition for a "Circle" object
main.js containing the main code which produces two circles
index.html which embeds the code into a webpage (used later in this tutorial)
circle.js
circle.js:
Unique identifier functionality
let _unique_circle_id = 1;
let fetchCircleID = () => _unique_circle_id++;
class Circle {
constructor(radius)
{
this.uid = fetchCircleID(); // Give each circle a unique identifyer
this.radius = radius;
console.log('Created circle ' + this.uid + ' with radius ' + this.radius)
}
}
module.exports = Circle;
main.js:
let Circle = require("./circle.js")
circle_1 = new Circle(10)
circle_2 = new Circle(5)
index.html:
<html><head><title>Javascript example</title></head><body><div id="content"></div><script src="./main.js"></script></body></html>
To run this code from the command-line, we can again simply use:
user@computer$ nodejs main.js
Created circle 1 with radius 10
Created circle 2 with radius 5
Alright, so this simple OOP works from the command line. But if we'd want to draw the actual circles for example on a HTML canvas, we'd need it to also run from within a browser. Let's try and set that up next.
Run it from the command line
As stated earlier, there are two ways to run the above code: from the command line via Node.js, or within the browser. The browser is nice for debugging, as it allows direct visual feedback and a GUI. However, let's first do the basic command-line stuff*. Only a few things need to be installed, namely nodejs, and the node package manager (npm) for installing useful packages later.
*all the commands above require a UNIX (bash) environment, so make sure you're either on Linux, Mac OSX, or have install windows subsystem for linux (WSL).
Javascript in the browser
VSC comes with a neat plugin called "Live Server" that allows you to quickly show your code from within the browser. But you need to install that first from the VSC-package manager:
Then, let's open index.html (which includes our main.js file) with this plugin by righclicking the HTML-file, and choosing “Open with Live Server”
Now you'll see an empty web page. Since the code isn't generating any visuals, let's open up the developer console and see if the code ran succesfully (Ctrl+Shift+i in Chrome, Ctrl+Shift+K in Firefox). Unfortunately, the code above didn't work properly just yet. You'll see the error:
Uncaught ReferenceError: require is not definedat main.js:1
This is because the syntax used by Nodejs and plain javascript from within the browser isn't 100% identical. Luckily, other people have already developed tools to convert them into one another. The tools browserify and watchify are useful to install here:
user@computer$ npm install -g browserifyuser@computer$ npm install -g watchify
user@computer$ npm install -g browserifyuser@computer$ npm install -g watchify
Browserify converts your code to something your browser can parse. Watchify is a wrapper that automatically calls browserify whenever files have changed. So, when you run:
user@computer$ watchify main.js -o main_browser.js
user@computer$ watchify main.js -o main_browser.js
You will notice the program never exits. This is because it continues to check if files have been changed, and will recompile when needed. Now, if we include main_browser.js in our HTML file, the code will run:
As you can see above, the browser also allows you to interact with the created Circle objects, and inspect their properties! That's definitely going to be useful for debugging later!
If you also want to print some output to the HTML page instead (e.g. when dynamically modifying the name of a graph), you can put an ID-tagged "div" in your HTML page (e.g. <div id="content"></div> in the example HTML file above), and fill up the content using the following code:
//Overwrite...
document.getElementById("content").innerHTML = "Circle with ID " + circle_1.uid
// ... or append...
document.getElementById("content").innerHTML += "Circle with ID " + circle_2.uid;
Note however that the above code will not run within the command-line, as the runtime environment, of course, does not contain these HTML elements. A way to work around this is using the following code to recognise whether or not we are running the code from the browser:
if (typeof window !== 'undefined')
document.getElementById("content").innerHTML += "Circle with ID " + circle_2.uid;
else
console.log("Circle with ID " + circle_1.uid)
Alright, that's it for the setup part. Now we should be able to make some cool programs that will (in principle) be compatible with both the browser and the command-line!