A Childhood Toy With JavaScript

My First Video Game

I spent some time over the holidays working on a video game/app and am very pleased with how it came out. It’s a version of the classic Spirograph, but you can add multiple moving gears (rotors) to the set-up. You can also make the line weight (on most browsers) very thin, so you can create some unexpected and complex shapes. Because of the ability to add multiple rotors, it’s named Spirographⁿ. We’ve got it set up at SeedCode here, and the code is at GitHub.

Please check it out and let us know what you think!

Spirographⁿ In Action



Drawing By Spirographⁿ “lily pad”


Math and Animation

The math here is actually not that tricky. There are parametric equations for Hypotrochoids and Epitrochoids, but as I started to think of this in terms of how I would do this in JavaScript, I realized most of this can be done by calculating a point on a circle given its center, radius and angle of the point from the center. This function basically does almost all the math and is recursively passed from circle to circle, and then finally determines the location of the pen on the last circle.

function circlePoint(a, b, r, ng) {
   var rad = ng * (Math.PI / 180);
   var y = r * Math.sin(rad);
   var x = r * Math.cos(rad);
   x = a + x;
   y = b - y;
   return {
      "x": x,
      "y": y

The drawing and animation is done using canvas. Canvas is an HTML5 element that can be accessed with JavaScript methods for drawing shapes, lines etc.

//sample canvas code
function drawOneCircle(canvas, a, b, r) {
   var ctx = canvas.getContext("2d");
   ctx.arc(a, b, r, 0, 2 * Math.PI);

This works great on all browsers, except for Safari where the line weights can only get so thin. The animation itself is actually done by clearing the current drawing and then recreating it in the new position. This is done recursively using the requestAnimationFrame() document method, which “snaps” the current frame before proceeding. The clearing method is not very precise, and you basically need to clear the entire canvas for each frame. Since I wanted the drawing itself to survive, I ended up creating two overlaid canvas elements with the circles being drawn on the “bottom,” and the curves being drawn on “top.” This way I could clear the canvas for the circles with each frame and leave the drawing intact.

Why A Game?

It’s a great question as I certainly have a lot to do! As with many programmers, games were my first introduction to computers. I vividly remember waiting in line at the Radio Shack to take my turn at the TRS80 for a turn at  Dancing Demon, and could not get enough.

However, I think there’s a more practical reason here as well. These days, and this may be me getting older, it seems like there’s more and more I don’t know. New languages and frameworks seem to pop up daily, and by the way that they’re introduced, you can easily get fooled into the sense that everybody is learning, and benefiting from, these new technologies but you, and that you’ll soon be left behind.

It is true that there is an enormous abundance of technologies out there, but the idea that somebody is learning them all, and is easily bouncing from Angular to React as the wind blows, is illusion. With this in mind, the question we should be asking ourselves as programmers is not “Should I learn all of these new languages?” but rather “Could I learn these languages?” That’s the more realistic question and why I think I finally took up this project. As long as I can keep my confidence high that I can learn new things, that sense of being left behind really goes away.

Featured Posts

Follow Along

Stay up to date with the latest news & examples from SeedCode


  • Hi. Fantastic inspiration. Graphic designer of 18 years here and reconnecting with intersection of play, art and design… can these creations be saved to vector or output beyond simple screen capture?

    Thank you!

    • Jason Young

      Hey Shan,
      Sorry I missed this. The DrawCurve() function is where all the points are established, so capturing the coordinates there and then setting up an export routine of them should be doable. Code is open source at Github: https://github.com/seedcode/SpirographN if you want to give that a try.
      My best,

  • steve_ssh

    Hello Jason.

    Thanks for your post. Especially coming from you, I appreciate the comments towards the end concerning learning. Now more than ever (and I believe related to the abundance of contemporary technologies) I see a great set of essential skills as:
    – The ability to learn new things
    – The ability to collaborate (something I value more as I get older)
    – Freedom to innovate
    – Balance between the fruits of innovation and “tried-and-true”
    – The ability to make the above stimulating/playful/enjoyable

    In my eyes, you routinely demonstrate the above in spades (and then you share your great work with the FM community).

    Thanks, kind regards, and good choice for opting for Spirograph over Lite-Brite.


    • Jason Young

      Thank you Steve! and I like your assessment of the essential skills very much.

Leave a Reply

Your email address will not be published. Required fields are marked *

Check out some of our other posts ...

Improved Resource Selection

We’ve made some big changes to how you filter and assign resources when editing events in DayBack. These changes will make it much easier to

Suggesting Appointment Slots

Show Available Slots that Match Multiple Criteria Schedulers often look for gaps in their schedules to find the open resources for each opportunity. But sometimes,

Introducing Draft Settings Mode

Following up on this idea that people stretch themselves when they feel a little safer, we’ve been very focused on the customization experience for DayBack



Stay up to date with the latest news & examples from SeedCode

© 2024 SeedCode, Inc.