Adding some canvas love to Hexo

tl;dr: Rik shows his love for the HTML5 canvas element by getting down and dirty with Hexo markdown and stuff

Growing up with canvas

The HTML5 <canvas> element was born from hatred. There were people in the world - good people, some of them even coders - who developed a hatred of Flash and decided that all the ‘goodness’ that Flash and ActionScript supplied should instead be handled natively as part of HTML.

Thus was born the Canvas API. Many many (many) web developers wept and gnashed their teeth as Flash got flushed from the World Wide Web, alongside their jobs.

Of course, as with every Great Plan, there was a glitch: it turns out that the Canvas API introduced with HTML5 is a right bugger to work with. Seriously! You have to write a shedload of code to display something pretty on a web page. If you want to animate your creation, you have to clear the canvas and do another shedload of calculations and then redraw your creation - 60 times a second.

Most coders looked at the Canvas API and, still sore at losing Flash, said: nope. Not doing that. Alternatives were developed, mainly in the world of CSS. Now color me stupid but, to me, style sheets are for styling pages; trying to make a style sheet do complex animations is begging for a world of hurt.

But all is not lost for the <canvas> element. A few developers decided to do the obvious thing and build some Javascript libraries to make working with the Canvas API a lot simpler (namechecking Fabric, Pixi and Easel as personal favourites). And, because some of those developers wanted to reclaim their lost Flash knowledge, many of those libraries follow a structure and coding process similar to ActionScript - such as building and animating stage heirarchies.

I, too, built a canvas library - though my motives were entirely different. I was desperate to find a way into the web development industry but, with no ‘professional’ experience, nobody would hire me. I needed to have some useful code in GitHub to sidestep the (clearly malfunctioning) recruitment agency algorithms and talk directly to tech leaders who didn’t yet know they wanted to employ me.

It worked! I now get to code up stuff (which I love doing) and - bonus! - I get paid for doing it. Life is truly sweet!

Adding my Scrawl-canvas library to my Hexo-based blog

I have a huge amount to learn about Hexo, so attempting this as one of my first serious Hexo experiments is a begging bowl to failure. But if I don’t fail, I don’t learn. It took me a while, but I got there eventually.

Behold! A <canvas> animation thing!

Seek to:

It works! But … it’s a messy compromise.

The problem is that Hexo has an index page at the root level which lists all my blogposts. Each blogpost can also be presented in its own page with its own (unique and very deep) url.

I’ve saved the Scrawl-canvas files into my theme. I could now adapt my theme layouts to load the core file for every post page, and the index page - but I don’t want to do that: most of my blog posts won’t be about the <canvas> library, thus it’s wasteful to keep uploading it just because.

So, for this experiment, I’ve decided to duck the whole issue and load the core file from both possible locations - a kludge fix. Markup code allows us to include raw html code in the post through a tag plugin called ‘raw’:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
{% raw %}
<!-- Adding all the demo architecture to the blogpost -->
<div style="text-align: center; border: 1px solid red; width: 400px; margin: 0 auto; padding: 10px;">
<div>
<button class="controls" style="font-size: 1em; padding: 4px; width: 100px;" id="run">Run</button>
<button class="controls" style="font-size: 1em; padding: 4px; width: 100px;" id="halt">Halt</button>
<button class="controls" style="font-size: 1em; padding: 4px; width: 100px;" id="resume">Resume</button>
</div>

<!-- the all-important <canvas> element -->
<canvas id="myCanvas" width="400" height="400" style="display: block; margin: 10px 0;">
</canvas>

<div class="slideContainer controls">Seek to:
<input id="seeker" type="range" value="0" min="0" max="13500" step="20" style="width: 70%"/>
</div>
</div>

<!--
This is the first kludge: importing the scrawl core file twice
- as the two alternative post views are in different places in Hexo architecture
-->
<script src="js/min_7-0-0/scrawlCore-min.js"></script>
<script src="../../../../js/min_7-0-0/scrawlCore-min.js"></script>

<!--
My scrawl display and animation code is vanilla javascript with added Scrawl goodness
-->
<script>

var mycode = function() {
'use strict';
// all the scrawl display and animate code goes here
};

// this is the function that sets Scrawl up and gets everything running
// - had to use a windows.location kludge here because of the uncertainty
// - over where the page displaying the canvas originated (post or index)
scrawl.loadExtensions({
path: window.location.origin + '/js/min_7-0-0/',
minified: true,
extensions: ['animation', 'wheel', 'images'],
callback: function() {
window.addEventListener('load', function() {
scrawl.init();
mycode();
}, false);
},
});
</script>
{% endraw %}

I’m gonna call this experiment a partial success. The solution I came up with does the job of animating a (rather pretty) <canvas> element. But it’s not a simple solution. More work needs to be done.

I’m sure I can write a Hexo plugin to both sort out the url stuff, and also let me separate the demo infrastructure and code out of the blog post itself. If my head was not throbbing from too much thinking right at this moment.

Maybe next week. Or the weekend after. Maybe.

For anyone interested, the full demo code can be found over at the Scrawl-canvas site. Enjoy!