Page 1 of 1

HTML5 - Basic Canvas Drawing Rate Topic: ***** 1 Votes

#1 modi123_1  Icon User is online

  • Suitor #2
  • member icon



Reputation: 9387
  • View blog
  • Posts: 35,242
  • Joined: 12-June 08

Posted 15 December 2012 - 05:45 PM

*
POPULAR

Topics covered:
  • HTML5 Canvas
  • Javascript events


Tools Required:
  • an HTML5 compliant browser
  • your development IDE of choice (I am using Eclipse)


Drawing on the HTML5 canvas is deceptively simple. A quick object tag in the HTML and a bit of javascript to link to that canvas and context and you are off and running!

In this tutorial I went the route that one long and curvy drawn line is just really a smaller conglomeration of smaller lines that are tracked between a given start and end point (with an appropriate width and coloring).

At the heart - the canvas is a quick object call that you specify a height and width for - and if you are feeling generous a small message inside the tags for people who have browsers that are not quite up to snuff..

<canvas id="myCanvas" width="500" height="500">
Your browser doesn't support HTML5 canvas tags.
</canvas>


Just a word of warning - my first inclination was to put the height and width in a CSS file, but javascript has a difficult time locating the values. It's best to keep them with the tag.

To draw on the canvas we need is to:
get an object that is the handle to the object.
Create a context from that handle
... and from there bob's your uncle!
http://www.w3schools...tml5_canvas.asp

In this example I am drawing a white square that should be in the top left corner and be fifty pixels big.

(FYI this code goes in your javascript file)
	oCanvas = document.getElementById("myCanvas");
	oContext = oCanvas.getContext("2d");
	oContext.fillStyle = "#FFFFFF";
	oContext.fillRect(0, 0, 50, 50);


To make this more interesting we are going to track the mouse movements and mouse clicks inside the canvas object. This requires us to hook into some javascript functionality and keep tabs on the mouse's location (remember we are drawing one big line with smaller little line segments), the user's selected width, and when the user is releasing the mouse click. One last bit of clean up - I will include a 'clear' button that takes all the rendered line segments and removes them to start a new canvas!

Here's the opening set of variables - tracking if the pen is down, the color, width, the canvas, context, and the mouse's location.
// -- Variables
var bPenDown = false; // determine if the pen is down to write or not.
var rgbLineColor = "FFFFFF"; // default color is white - this could be

var lLineWidth = 1; // the line width holder

// the context and canvas of our html5 canvas object
var oCanvas;
var oContext;

// the point array to track the pen while it is down.
var myPen =
{};

window.onload = init;// just load the initialization when the form loads.

// initalize our canvas and all the events we will need.
function init()
{
	// get the canvas object
	oCanvas = document.getElementById("myCanvas");
	// set the context to plain 2d dreawing
	oContext = oCanvas.getContext("2d");
	// setup the fill style to the default (white)
	oContext.fillStyle = "#" + rgbLineColor;
	// set the default selector for the pen
	document.getElementById("penWidth").selectedIndex = 1;
	// set the initial pen width
	lLineWidth = 3;
	// register the rest of the events.
	registerEvents();

}


The register events hooks into given canvas events and assigns their proper functions to call when fired. I am also hooking up the select drop down for the pen width (to quickly change the width when the user requests).
// the main events needed to be caught
function registerEvents()
{
	// mouse evens.
	oCanvas.onmousedown = mouseDownListener;
	oCanvas.onmousemove = mouseMoveListener;
	oCanvas.onmouseup = mouseUpListener;

	// if the user wants a new pen make sure to change the width.
	document.getElementById("penWidth").onchange = penWidthListener;
}


The events are pretty straight forward with the exception of utilizing the event argument. The canvas events (especially the mouse movements) have an event arg that says "hey - when I was fired here was the mouse's location!". We can take those values and construct a begin and end point to draw!


/*
 * ============================== EVENTS ========================
 */

// When the mouse is clicked in the canvas get the coordinates it is clicked and
// set the boolean for the mouse is down
function mouseDownListener(e)
{

	// grab the event object which contains our mouse locations.
	var event = e || window.event;// IE -> window.event, not e

	// depeneding on where this canvas is we need to do a bit of math to get the
	// right coordinates
	var tempRect = oCanvas.getBoundingClientRect();
	var mouseX = event.clientX - tempRect.left;
	var mouseY = event.clientY - tempRect.top;

	// send those coordinates to the the pen down and track'm
	penDown(mouseX, mouseY);
}

// When the mouse moves track that too!
function mouseMoveListener(e)
{

	var event = e || window.event; // IE -> window.event, not e
	// depeneding on where this canvas is we need to do a bit of math to get the
	// right coordinates
	var rect = oCanvas.getBoundingClientRect();
	var mouseX = event.clientX - rect.left;
	var mouseY = event.clientY - rect.top;

	// draw a line with these two end coordiantes.
	penMove(mouseX, mouseY);
}

// When the mouse button is released
function mouseUpListener(e)
{
	// tell the drawing and pen boolean that we are done drawing.
	penUp();
}

// when the pen is down start drawing save those coordinates as the start of the
// line
function penDown(x, y)
{
	bPenDown = true;
	myPen.x = x;
	myPen.y = y;
}

// When the pen moves these coordinates are the 'end point' of the line we want
// to draw.
function penMove(x, y)
{
	// only do this if the pen is down.
	if (bPenDown)
	{
		// Actually draw the line on our screen.
		drawLine(rgbLineColor, lLineWidth, myPen.x, myPen.y, x, y);

		// Shift the last points in as the start of the new line line
		myPen.x = x;
		myPen.y = y;
	}
}

// flips the boolean so we are not drawing lines when the mouse moves.
function penUp()
{
	bPenDown = false;
}



All that is great, but the real meat is in the drawing, right? This is nothing more complex than the example of drawing a square, but here we are drawing a quick small line!

// takes the color, width, and two coordinates to draw a small line on the
// canvas.
function drawLine(color, thickness, x1, y1, x2, y2)
{
	// we are storing the color in the database so add the hash mark.
	oContext.strokeStyle = "#" + color;
	oContext.lineWidth = thickness;

	// it's all about small paths
	oContext.beginPath();
	oContext.moveTo(x1, y1);
	oContext.lineTo(x2, y2);
	oContext.stroke();
}


The final two events are the clear and the pen width events. The clear takes the context and just says "here's how big of an area I want to remove anything drawn on". In our case - the whole thing!

// clears the screen of the canvas and clears the coordinates from the table.
function Clear_Down()
{
	oContext.clearRect(0, 0, oCanvas.width, oCanvas.height);
}

// when the user selects a different pen - update our size.
function penWidthListener(e)
{
	lLineWidth = this.options[this.selectedIndex].value;
}



In a more advanced section I will cover transmitting these values to other users who are on the same drawing page as well! Nothing beats collaborative work! (link)

Advanced topics you can try out:
  • A color selector for the lines
  • A background color changer
  • Tightening up the timing to get a smoother line
  • Adding shapes and other basic drawing polygons


Attached Image

Code
HTML
Spoiler


CSS
Spoiler


Javascript
Spoiler


Is This A Good Question/Topic? 9
  • +

Replies To: HTML5 - Basic Canvas Drawing

#2 Sho Ke  Icon User is offline

  • D.I.C Regular
  • member icon

Reputation: 110
  • View blog
  • Posts: 250
  • Joined: 13-October 11

Posted 07 February 2013 - 09:33 AM

Great tutorial. I noticed that every now and then a line won't be drawn completely, leaving out a few pixels at the end and only drawing the last part upon the user starting his next line. weird..
Was This Post Helpful? 0
  • +
  • -

#3 modi123_1  Icon User is online

  • Suitor #2
  • member icon



Reputation: 9387
  • View blog
  • Posts: 35,242
  • Joined: 12-June 08

Posted 07 February 2013 - 10:17 AM

Yeah I noticed that glitch as well. I am thinking it has to do with the up and down events not getting registered fast enough. Cest la vie.
Was This Post Helpful? 0
  • +
  • -

#4 cpricelandscapes  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 2
  • Joined: 17-October 13

Posted 21 October 2013 - 04:51 AM

Helpful tutorial. Thanks
Was This Post Helpful? 0
  • +
  • -

Page 1 of 1