{"id":239,"date":"2009-09-04T10:51:14","date_gmt":"2009-09-04T14:51:14","guid":{"rendered":"https:\/\/htmlcssjs.wpengine.com\/?p=239"},"modified":"2014-10-08T16:41:21","modified_gmt":"2014-10-08T20:41:21","slug":"html5-notes-my-first-time-using-the-canvas-element","status":"publish","type":"post","link":"https:\/\/htmlcssjavascript.com\/javascript\/html5-notes-my-first-time-using-the-canvas-element\/","title":{"rendered":"HTML5 Notes: My First Time Using the Canvas Element"},"content":{"rendered":"<p>Quick verdict? It&#8217;s fun.<\/p>\n<p>The long verdict (albeit one not base on the work I did here?) The <a href=\"http:\/\/www.paciellogroup.com\/blog\/?p=362\">accessibility concerns are valid<\/a> and will need to be addressed before we end up with a replay of Flash circa 2000. And no one wants that.<\/p>\n<p>Anyway, the example I did do for the demo is actually one of the use cases imagined when the <code>Canvas<\/code> element was introduced. I took a simple <code>data table<\/code> and turned it into a simple chart. This is obviously not the most complicated, impressive example of the technology, but it&#8217;s an easy one to digest so it&#8217;s a perfect way to highlight the technology as part of a 45 minute presentation. Especially since I&#8217;ve got to run through another five or six features of the spec.<\/p>\n<p>Anyway, here&#8217;s the example.<br \/>\n<!--more--><br \/>\n<iframe loading=\"lazy\" src=\"\/samples\/html5\/canvas.html\" width=\"525\" height=\"425\" style=\"overflow:hidden\"><\/iframe><\/p>\n<p>Here&#8217;s some code.<\/p>\n<p>The HTML is very simple. The new <code>Canvas<\/code> element is the only interesting part and without JavaScript all it does is just sit there.<\/p>\n<div class=\"code-sample\"><code><\/p>\n<pre>\r\n&lt;table id=&quot;data-table&quot;&gt;<br \/>\r\n    &lt;tr&gt;<br \/>\r\n        &lt;td&gt;15&lt;\/td&gt;<br \/>\r\n        &lt;td&gt;25&lt;\/td&gt;<br \/>\r\n        &lt;td&gt;10&lt;\/td&gt;<br \/>\r\n        &lt;td&gt;25&lt;\/td&gt;<br \/>\r\n        &lt;td&gt;50&lt;\/td&gt;<br \/>\r\n    &lt;\/tr&gt;<br \/>\r\n&lt;\/table&gt;<br \/>\r\n&lt;button id=&quot;canvas-controller&quot;&gt;Chart It!&lt;\/button&gt;<br \/>\r\n&lt;canvas id=&quot;canvas-sample&quot; width=&quot;350&quot; height=&quot;200&quot;&gt;<br \/>\r\n&lt;\/canvas&gt;<br \/>\r\n<\/pre>\n<p><\/code><\/div>\n<p>Here&#8217;s the JavaScript. Comments inline.<\/p>\n<div class=\"code-sample wide\"><code><\/p>\n<pre>\r\ndocument.getElementById(&quot;canvas-controller&quot;).addEventListener(&quot;click&quot;, writeCanvas, false);<br \/>\r\n<br \/>\r\nfunction writeCanvas(e){<br \/>\r\n\/\/we need a reference to the canvas. Typical DOM stuff\r\n    var canvas = document.getElementById(&quot;canvas-sample&quot;);<br \/>\r\n\/\/Then we get the \"context.\" It's the reference to the drawing surface. \r\n\/\/There is not 3d yet. I can't imagine there wouldn't be some day\r\n    var context = canvas.getContext(&quot;2d&quot;); <br \/>\r\n\/\/get the data cells\r\n    var tds = document.getElementById(&quot;data-table&quot;).getElementsByTagName(&quot;td&quot;);<br \/>\r\n\/\/set up a list of colors. I could have calculated some colors\r\n\/\/or something, but I was more focused on the canvas \r\n\/\/element itself than being fancy with the charting stuff.\r\n    var colors = [&quot;#3366FF&quot;,<br \/>\r\n        &quot;#6633FF&quot;,<br \/>\r\n        &quot;#003DF5&quot;,<br \/>\r\n        &quot;#002EB8&quot;,<br \/>\r\n        &quot;#66FF33&quot;<br \/>\r\n    ];<br \/>\r\n\/\/Let's draw some grid lines\r\n\/\/this is basically right out of the <a href=\"http:\/\/diveintohtml5.org\/\">dive into html5<\/a> demo\r\n    for (var y = 0; y &lt; canvas.offsetHeight; y += 10) {<br \/>\r\n\/\/moveTo and lineTo are pretty clearly named functions.\r\n\/\/move the \"point\" to a new place\r\n\t    context.moveTo(0, y);<br \/>\r\n\/\/and plot a line\r\n    \tcontext.lineTo(canvas.offsetWidth, y);<br \/>\r\n    }<br \/>\r\n\/\/what's not clear is that running the above commands doesn't \r\n\/\/actually draw anything. These next two commands do\r\n\/\/set a style for line \"stroke\"\r\n    context.strokeStyle = &quot;#ccc&quot;;<br \/>\r\n\/\/and then call the function that makes the lines happen\r\n    context.stroke();<br \/>\r\n\/\/set a bunch of variables\r\n    var basewidth, spacing, width, height, posx, posy;\r\n\/\/loop through- this is a reversed loop, just because \r\n\/\/I want to actually code this faster pattern\r\n\/\/a regular (for = 0; i&lt;test; i++) would work just as well\r\n    for (i = tds.length - 1; i &gt;= 0; i--) {<br \/>\r\n\/\/calculate a uniform \"base\" width for the bars \r\n   \tbasewidth = canvas.offsetWidth\/tds.length;<br \/>\r\n\/\/set up some spacing\r\n    \tspacing = basewidth\/4;<br \/>\r\n\/\/calculate the actual width of the bars\r\n    \twidth = basewidth - spacing;<br \/>\r\n\/\/set up a height. This isn't actually to any scale. \r\n\/\/It just looked good :)\r\n    \theight = parseInt(tds[i].innerHTML)*3;<br \/>\r\n\/\/calculate the x position with some spacing between the bars\r\n    \tposx = (i * basewidth) + spacing\/2;<br \/>\r\n\/\/pin the bars to the bottom of the canvas\r\n    \tposy= canvas.offsetHeight-height;<br \/>\r\n\/\/set the color\r\n    \tcontext.fillStyle = colors[i];<br \/>\r\n\/\/and then fill it. The fillRect takes (x,y,width,height) as arguments\r\n    \tcontext.fillRect(posx, posy, width , height );<br \/>\r\n    }<br \/>\r\n\/\/stop the clicks.\r\n    e.preventDefault();<br \/>\r\n}\r\n<\/pre>\n<p><\/code><\/div>\n<p>And there you have it. All things considered it&#8217;s a clearly written, powerful interface. If they can sort out the accessibility issues and if we don&#8217;t go mad with power it&#8217;ll end up being a great benefit to web developers for years to come.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Quick verdict? It&#8217;s fun. The long verdict (albeit one not base on the work I did here?) The accessibility concerns are valid and will need to be addressed before we end up with a replay of Flash circa 2000. And no one wants that. Anyway, the example I did do for the demo is actually [&hellip;]<\/p>\n","protected":false},"author":2,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[5],"tags":[41,10],"class_list":["post-239","post","type-post","status-publish","format-standard","hentry","category-javascript","tag-canvas","tag-html5"],"_links":{"self":[{"href":"https:\/\/htmlcssjavascript.com\/wp-json\/wp\/v2\/posts\/239","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/htmlcssjavascript.com\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/htmlcssjavascript.com\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/htmlcssjavascript.com\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/htmlcssjavascript.com\/wp-json\/wp\/v2\/comments?post=239"}],"version-history":[{"count":0,"href":"https:\/\/htmlcssjavascript.com\/wp-json\/wp\/v2\/posts\/239\/revisions"}],"wp:attachment":[{"href":"https:\/\/htmlcssjavascript.com\/wp-json\/wp\/v2\/media?parent=239"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/htmlcssjavascript.com\/wp-json\/wp\/v2\/categories?post=239"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/htmlcssjavascript.com\/wp-json\/wp\/v2\/tags?post=239"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}