Programming Dynamic Drawings & Animations With Angular JS and Two JS

Naren Yellavula
Dev bits
Published in
7 min readMar 5, 2017

--

Campfire by dreamingincodezh using TwoJS

Namaste folks. In some part of your life, you are in need of creating drawings and animations based on a set of conditions. Sometimes the drawing can be dynamic. It means user changes the input and drawing updates itself dynamically. We all have seen the Ajax, a mechanism for updating a web page without refreshing. Similarly, think this as a combination of Two JS & Angular JS that gives the power of dynamic 2 dimensional(2D) drawings without refresh. This article mostly allocates its time discussing Two JS.

Everything started from HTML5 canvas

HTML5 canvas allows one to draw on a canvas element on the web page. It is like painting on a whiteboard(it can be of any color) with a paintbrush dipped in a color. If you ever worked with it, you might feel how naive and basic it is. I initially played with Canvas API in a hackathon while developing a webRTC application with audio conferencing between teachers and students. The teacher can draw anything on her tablet PC and students see it instantly. At the same time, they can listen to what teacher is explaining.

But native Canvas API is painful. It is so basic that you need to write many wrapper functions on top of that.

Why Two JS?

We need to use a framework to keep it DRY(Don’t Repeat Yourself). There are many good libraries like Fabric JS, Two JS to make 2D paintings on a web page. But I personally prefer Two JS over Fabric JS because of the easiness the library offers us.

Two JS has API to draw many kinds of geometrical structures onto a Canvas or SVG. It uses Backbone JS and Underscore JS under the hood to provide a fantastic API to do things much faster. If you need to add more functionality to it, just raise a pull request in their git repository.

For more Two JS related information visit the official documentation

Let us begin (Part 1: Being comfortable with Two JS)

Any 2D drawing starts with a line. Other geometrical structures like square, rectangle, polygon, circle and ellipse are formed from the line. So we go through each of them step by step. Using Two JS we can draw following:

  • Path(A path of line along with points)
  • Line
  • Rectangle/ Rounded Rectangle
  • Ellipse
  • Star
  • Polygon
  • Vector
  • Text
  • Anchor(points or pins in a path)

We here illustrate some important items and leave others for readers to explore themselves.

Initialization

We need to create a canvas or SVG element on our HTML page. Then in JavaScript, we need to instantiate Two JS and use its API. So HTML page looks like this.

<!DOCTYPE html>
<html>
<head>
<title> Two JS Tutorial</title>
</head>
<body>
<div id="myCanvas"></div>
<script src='https://cdnjs.cloudflare.com/ajax/libs/two.js/0.6.0/two.min.js'></script>
<script>
var elem = document.getElementById('myCanvas');
var two = new Two({
type: Two.Types.canvas,
fullscreen: true
}).appendTo(elem);
two.update();
</script>
</body>
</html>

In order to draw a picture, we need to setup canvas. So in the code first we are importing Two JS from CDN and then we are initializing a Two object with two parameters. type and fullscreen. We can pass height and width of the canvas to be formed. Here for illustration, I chose full screen drawing.

two.update() is the function that updates the elements on the canvas. So don’t forget to include this line after your Two JS script.

Line

A line can be drawn between two points. In Two JS, you can provide the points to a function called makeLine and library draws a line between them. The API is this (x1, y1, x2, y2) where

x1 — X coordinate of the first point

y1 — Y coordinate of the first point

x2 — X coordinate of the second point

y2 — Y coordinate of the second point

Now let me add this code before two.update(); in above HTML

var line = two.makeLine(450, 140, 900, 140);// linewidth property sets width of the line
line.linewidth = 5;
// stroke property sets the color
line.stroke = "blue";
Line can be drawn so easily

In this figure, we are drawing a blue line from (450, 140) to (900, 140). Then we set its width as 5. Check out the live action here.

Rectangle

Now let us play with the rectangle. Here instead of showing a simple example let us draw a simple colorful art. From Two JS rectangle API, we can draw a rectangle with makeRectangle(x-coordinate, y-coordinate, width, height)

Window tiles. Remembering bit art?

In the above code, we created tiles of rectangles in topRight, topLeft, bottomLeft, bottomRight directions. We selected random colors for both stroking and filling rectangles. This example is just to show how to draw rectangles.

Ellipse & Star

You need to draw an ellipse and star some or other point of time. Two JS provides nice API for that too. Let us build a frog eye in the anime shows. Remember that Circle is an Ellipse with equal height and width.

Note: Here first two coordinates of the ellipse are points of center.

An eye of Gamakichi, a Ninja Frog

Similar way, you can draw all the diagrams the Two JS provides. Even the complex structures can be drawn by using mathematical formulae.

Giving power to your Two JS diagrams with Angular JS (Part 2)

Now comes the juicy part. The diagrams we constructed above are lifeless. But with the help of Angular JS, we can take actions from the user and change the diagram automatically. This is a three step process.

  • Render initial screen
  • Receive user input
  • Rub off the canvas/SVG
  • Re-paint the diagram with new information

It is a good practice to keep a diagram stateless. It means, your diagram should be drawn from a data object(single source). It provides you the comfort of re-painting with the updated data object. Since this cycle goes on very fast, the user may think that diagram changing rapidly.

Adding spokes to the wheel

Here we can do a small experiment. In this experiment, we define two HTML elements

  • Circle or Wheel
  • Button for adding spokes

Whenever one hits the button, a new spoke will be added to the wheel.

First, we are going to create an app.js file with angular app and controller. The code is self-explanatory. I used mathematical formulae to find points on the circumference of a circle.

var app = angular.module('plunker', []);app.controller('MainCtrl', function($scope) {
var self = $scope;
self.spokes = 1;
self.two = new Two({
type: Two.Types.svg
}).appendTo(document.getElementById('myCanvas'));

self.drawWheel = function() {
var center_X = 420;
var center_Y = 140;
var radius = 100;
var ellipse = self.two.makeEllipse(center_X, center_Y, radius, radius);
ellipse.linewidth = 0;
ellipse.fill = "#66BB6A";
var spoke_color = "#FF5722";
var x1 = center_X;
var y1 = center_Y;
for (var i = 0; i < self.spokes; i++) {
var x2 = x1 + radius * Math.cos(i * 5);
var y2 = y1 + radius * Math.sin(i * 5);
var line = self.two.makeLine(x1, y1, x2, y2);
line.linewidth = 3;
line.stroke = "white";
}
self.two.update();
}
// Function resets the drawing screen & repaints
self.repaint = function() {
$("myCanvas").empty();
self.drawWheel();
}

and HTML looks like this

<!DOCTYPE html>
<html ng-app="plunker">
<head>
<meta charset="utf-8" />
<title>AngularJS Plunker</title>
<link rel="stylesheet" href="style.css" />
<script src="https://cdnjs.cloudflare.com/ajax/libs/two.js/0.6.0/two.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.10/angular.min.js">
</script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js">
</script>
<script src="app.js"></script>
</head>
<body>
<div ng-controller="MainCtrl">
<div class="row">
<div id="myCanvas"></div>
</div>
<div class="row" ng-init="drawWheel()">
<center>
<button type="button" ng-click="spokes = spokes + 1; repaint()" class="btn btn-primary">Add Spoke</button>
</center>
</div>
</div>
</body>
</html>

We are performing these actions:

  • Whenever button is clicked calculate and repaint the screen
  • Attach Two JS instance to controller so that it is accessible to any part of HTML

See it in action here:

In this way we can use combined power of Angular JS and Two JS to create dynamic diagrams. These might sound basic, but advanced diagrams can be built using these.

Hint: Use Two JS & Physics JS to draw excellent digital photography.

Hope you all enjoyed the post. Keep trying new things. :)

References

--

--