Wow, look at that – Day 31! I made it!
There were some rough points in the middle there, but I managed to pull off some filler posts until I figured out the next topic. I hope you’ve enjoyed this month of posts and learned at least a fraction of what I learned. It was fantastic for me to force myself to dive into all this new stuff. I’ve always said the best way to learn something is to teach it. When you have to explain something to someone else, you find you need to understand it on an entirely new level. So really, this was all a selfish, self-motivated effort. And if you learned anything at all, that was an unintended byproduct. 😉
As for what’s next, I’m going to enjoy a few weeks of not having to come up with a new post each day. I plan to take a deep dive into Android and create at least a couple of apps/games. I’d like to do another series like this for Android, though I doubt I’ll pull off a whole month of it. Maybe a week here or there.
And onto today’s, the final post. In the back of my mind, one thing I’v ewanted to do in JavaScript was create a Verlet Integration physics simulation. So, while on the train to New York for Geeky By Nature, I did just that! You can take a look at the source for the system itself here:
http://www.bit-101.com/jscanvas/VerletSystem.js
I’m not going to go through the code for this line by line. You should be able to understand what’s going on with the functions and prototypes and general structure by now. As for Verlet Integration, I refer you to my book, AdvancED ActionScript Animation 3.0, where I discuss it in depth and give an AS3 implementation of it. This is generally following the same concepts there. But note that I wrote the JS version straight out of my head while on the train, so implementation details may be a bit different. It’s not a straight port of what’s in the book.
To use it, you create a new VerletSystem object, passing in a canvas that it will draw to. Then you add points. Each point has an index, an x and y position, and optionally, an initial velocity x and y. Finally, you connect the points by adding sticks. A stick consists of two points, identified by their indexes, and optionally a stroke style and line width. Finally, you call update() and draw() repeatedly on the system to animate it. Here’s just about the minimal functionality you could have:
[php lang=”JavaScript”]$(function () {
var canvas, vs;
canvas = $(“#canvas”)[0];
vs = new VerletSystem(canvas);
vs.addPoint(0, 100, 100);
vs.addPoint(1, 110, 200);
vs.addStick(0, 1);
setInterval(function() {
vs.update();
vs.draw();
}, 1000/24);
});[/php]
This just sets up two points with a stick between them. You can see this in action here:
http://www.bit-101.com/jscanvas/mar31.html
You can start making rough forms like a box like so:
[php lang=”JavaScript”]vs.addPoint(0, 100, 100, 0, 20);
vs.addPoint(1, 200, 100);
vs.addPoint(2, 200, 200);
vs.addPoint(3, 100, 200);
vs.addStick(0, 1);
vs.addStick(1, 2);
vs.addStick(2, 3);
vs.addStick(3, 0);
vs.addStick(0, 2);[/php]
I omitted all but the point and stick definitions here. This creates four points in a square and connects them. Note that the last point adds a diagonal cross beam for stability. Try taking it out and you’ll see the box collapses. Also note that the first point has a bit of y velocity on it. This gives the box an initial spin.
You can see this one here:
http://www.bit-101.com/jscanvas/mar31-0.html
Here’s a more complex example:
[php lang=”JavaScript”]vs = new VerletSystem(canvas);
for(i = 0; i < 5; i += 1) { angle = Math.PI * 2 / 5 * i; vs.addPoint(i, 200 + Math.cos(angle) * 100, 200 + Math.sin(angle) * 100); } vs.showPoints = false; vs.addStick(0, 2, "#ff0000", 3); vs.addStick(2, 4, "#ff0000", 3); vs.addStick(4, 1, "#ff0000", 3); vs.addStick(1, 3, "#ff0000", 3); vs.addStick(3, 0, "#ff0000", 3); vs.addStick(0, 1, "rgba(0, 0, 0, 0.5)"); vs.addStick(1, 2, "rgba(0, 0, 0, 0.5)"); vs.addStick(2, 3, "rgba(0, 0, 0, 0.5)"); vs.addStick(3, 4, "rgba(0, 0, 0, 0.5)"); vs.addStick(4, 0, "rgba(0, 0, 0, 0.5)");[/php] I create 5 points arranged in a circle. Then I connect them by joining every other point with sticks. This makes a star shape. Here, I also specify a red, 3-pixel thick line for the star. But again, this is not a stable shape, so I add some more sticks around the circumference. These, I give a 50% transparent black stroke. Also, notice that I set vs.showPoints to false. This turns of the drawing of points. You can see the result here: http://www.bit-101.com/jscanvas/mar31-1.html
Finally, something that really shows the power of this seemingly simple system.
[php lang=”JavaScript”]vs.addPoint(0, 250, 0);
vs.addPoint(1, 0, 500);
vs.addPoint(2, 500, 500);
vs.addPoint(3, 200, 50);
vs.addPoint(4, 150, 100);
vs.addPoint(5, 100, 150);
vs.addPoint(6, 50, 130);
vs.addPoint(7, 50, 170);
// large triangle
vs.addStick(0, 1);
vs.addStick(1, 2);
vs.addStick(2, 0);
// a “rope”
vs.addStick(0, 3);
vs.addStick(3, 4);
vs.addStick(4, 5);
// a weight
vs.addStick(5, 6);
vs.addStick(6, 7);
vs.addStick(7, 5);[/php]
First we create a large triange for a base. Then three sticks hang in a row from the top point of the triangle. At the end of this is another triangle that acts as a weight. When this runs, the weight will fall and swing back and forth. Check it:
http://www.bit-101.com/jscanvas/mar31-2.html
With this example, I’ve at least proven to myself that JavaScript and canvas totally rocks and is a viable platform for all kinds of fun experimentaion. I’m most definitely going to be doing a lot more of this in the future.
Have a good April!
Keith, awesome effort! 🙂
Been so busy I haven’t had a chance to go through your posts yet but i’ve been smiling as my RSS turns your feed blue everyday 🙂
Looking forward to reading through it all, hope you enjoyed doing it!
Cheers,
Matt / MSFX
Hi Keith,
Thanks for this JS month, I really enjoyed reading the posts and actually learned quite a lot.
As usual awesome stuff. I can’t wait to read your Android posts.
Cheers.
Thanks for the month – It has been very informative and – as always – clear and precise.
Incredible even you had to sustain your presentation @geekebynature you did the last post. Thumbs up for your great effort!
Great month. Thanks!
Amazing samples, thanks so much!
Thanks for the month.i study a lot js.
Great stuff. I loved wirelib and now this is just awesome.
http://bit.ly/hXlv98
I made small rabbit. Click and hold down the mouse.
(It is a processing.js dialect though, but with sticks and points.)
nice.
Thanks Kieth,
Really appreciate the month. Very timely info and instruction. I donated and hope others do too.
Best,
Dave
Can you put this up on github for the community to use/share?
Hi Keith,
Great tutorial.
A post (or page) with sequential links to each post in this series would be great. I’d like to be able to point/tweet people towards a single, clearly-indexed page. Maybe some way to do this already exists but I’m missing it? I think even a tag unique to this tutorial would do it…
– Patrick
Thanks much for the lessons.