HTML5 canvas – Custom brush (BezierCurveBrush)
Join the DZone community and get the full member experience.
Join For FreeI hope that you still remember when we did our first Paint program with HTML5.
Today I have decided to enhance it by adding new additional brush to
it. This brush will use ‘bezierCurveTo’ function. As a result we will have
an interesting effect; just check out it!
Here are our demo and downloadable package:
Live Demo
download in package
Ok, download the source files and lets start coding !
Step 1. HTML
Here is the html code for our enhanced Paint:
index.html
<!DOCTYPE html> <html lang="en" > <head> <meta charset="utf-8" /> <title>HTML5 canvas - Custom brush (BezierCurveBrush) for your paing program | Script Tutorials</title> <link href="css/main.css" rel="stylesheet" type="text/css" /> <script src="js/jquery-1.5.2.min.js"></script> <script src="js/script.js"></script> </head> <body> <header> <h2>HTML5 canvas - Custom brush (BezierCurveBrush) for your paing program</h2> <a href="http://www.script-tutorials.com/html5-canvas-custom-brush1/" class="stuts">Back to original tutorial on <span>Script Tutorials</span></a> </header> <div class="container"> <div class="column1"> <canvas id="color" width="500" height="128"></canvas> </div> <div class="column2"> <div>Preview:</div> <div id="preview"></div> <div id="pick"></div> </div> <div style="clear:both;"></div> </div> <canvas id="panel" width="1000" height="600"></canvas> </body> </html>
Step 2. CSS
Here are the CSS styles used:
css/main.css
/* page layout styles */ *{ margin:0; padding:0; } body { background-color:#eee; color:#fff; font:14px/1.3 Arial,sans-serif; } header { background-color:#212121; box-shadow: 0 -1px 2px #111111; display:block; height:70px; position:relative; width:100%; z-index:100; } header h2{ font-size:22px; font-weight:normal; left:50%; margin-left:-400px; padding:22px 0; position:absolute; width:540px; } header a.stuts,a.stuts:visited{ border:none; text-decoration:none; color:#fcfcfc; font-size:14px; left:50%; line-height:31px; margin:23px 0 0 110px; position:absolute; top:0; } header .stuts span { font-size:22px; font-weight:bold; margin-left:5px; } .container { color: #000; margin: 20px auto; overflow: hidden; position: relative; width: 800px; } /* custom styles */ .column1 { float:left; width:500px; } .column2 { float:left; padding-left:20px; width:170px; } #panel { border:1px #000 solid; box-shadow:4px 6px 6px #444444; cursor:crosshair; display:block; margin:0 auto; height:600px; width:1000px; } #color { border:1px #000 solid; box-shadow:0px 4px 6px #444444; cursor:crosshair; } .column2 > div { margin-bottom:10px; } #preview, #pick { border:1px #000 solid; box-shadow:2px 3px 3px #444444; height:40px; width:80px; border-radius:3px; -moz-border-radius:3px; -webkit-border-radius:3px; }
Step 3. JS
js/script.js
var canvas; var canvasColor; var ctx; var ctxColor; var bMouseDown = false; var selColorR = 0; var selColorG = 0; var selColorB = 0; var BezierCurveBrush = { // inner variables iPrevX : 0, iPrevY : 0, points : null, // initialization function init: function () { }, startCurve: function (x, y) { this.iPrevX = x; this.iPrevY = y; this.points = new Array(); }, getPoint: function (iLength, a) { var index = a.length - iLength, i; for (i=index; i< a.length; i++) { if (a[i]) { return a[i]; } } }, draw: function (x, y) { if (Math.abs(this.iPrevX - x) > 5 || Math.abs(this.iPrevY - y) > 5) { this.points.push([x, y]); // draw main path stroke ctx.beginPath(); ctx.moveTo(this.iPrevX, this.iPrevY); ctx.lineTo(x, y); ctx.lineWidth = 1; ctx.strokeStyle = 'rgba(' + selColorR + ', ' + selColorG + ', ' + selColorB + ', 0.9)'; ctx.stroke(); ctx.closePath(); // draw extra strokes ctx.strokeStyle = 'rgba(' + selColorR + ', ' + selColorG + ', ' + selColorB + ', 0.2)'; ctx.beginPath(); var iStartPoint = this.getPoint(25, this.points); var iFirstPoint = this.getPoint(1, this.points); var iSecondPoint = this.getPoint(5, this.points); ctx.moveTo(iStartPoint[0],iStartPoint[1]); ctx.bezierCurveTo(iFirstPoint[0], iFirstPoint[1], iSecondPoint[0], iSecondPoint[1], x, y); ctx.stroke(); ctx.closePath(); this.iPrevX = x; this.iPrevY = y; } } }; $(function(){ // creating canvas objects canvas = document.getElementById('panel'); ctx = canvas.getContext('2d'); canvasColor = document.getElementById('color'); ctxColor = canvasColor.getContext('2d'); drawGradients(ctxColor); BezierCurveBrush.init(); $('#color').mousemove(function(e) { // mouse move handler var canvasOffset = $(canvasColor).offset(); var canvasX = Math.floor(e.pageX - canvasOffset.left); var canvasY = Math.floor(e.pageY - canvasOffset.top); var imageData = ctxColor.getImageData(canvasX, canvasY, 1, 1); var pixel = imageData.data; var pixelColor = 'rgba('+pixel[0]+', '+pixel[1]+', '+pixel[2]+', '+pixel[3]+')'; $('#preview').css('backgroundColor', pixelColor); }); $('#color').click(function(e) { // mouse click handler var canvasOffset = $(canvasColor).offset(); var canvasX = Math.floor(e.pageX - canvasOffset.left); var canvasY = Math.floor(e.pageY - canvasOffset.top); var imageData = ctxColor.getImageData(canvasX, canvasY, 1, 1); var pixel = imageData.data; var pixelColor = 'rgba('+pixel[0]+', '+pixel[1]+', '+pixel[2]+', '+pixel[3]+')'; $('#pick').css('backgroundColor', pixelColor); selColorR = pixel[0]; selColorG = pixel[1]; selColorB = pixel[2]; }); $('#panel').mousedown(function(e) { // mouse down handler bMouseDown = true; var canvasOffset = $(canvas).offset(); var canvasX = Math.floor(e.pageX - canvasOffset.left); var canvasY = Math.floor(e.pageY - canvasOffset.top); BezierCurveBrush.startCurve(canvasX, canvasY, false, false, false, false, false, false, canvasX, canvasY, 0, 0); }); $('#panel').mouseup(function(e) { // mouse up handler bMouseDown = false; }); $('#panel').mousemove(function(e) { // mouse move handler if (bMouseDown) { var canvasOffset = $(canvas).offset(); var canvasX = Math.floor(e.pageX - canvasOffset.left); var canvasY = Math.floor(e.pageY - canvasOffset.top); BezierCurveBrush.draw(canvasX, canvasY, false, false, false, false, false, false, canvasX, canvasY, 0, 0); } }); }); function drawGradients() { var grad = ctxColor.createLinearGradient(20, 0, canvasColor.width - 20, 0); grad.addColorStop(0, 'red'); grad.addColorStop(1 / 6, 'orange'); grad.addColorStop(2 / 6, 'yellow'); grad.addColorStop(3 / 6, 'green') grad.addColorStop(4 / 6, 'aqua'); grad.addColorStop(5 / 6, 'blue'); grad.addColorStop(1, 'purple'); ctxColor.fillStyle=grad; ctxColor.fillRect(0, 0, canvasColor.width, canvasColor.height); }
What I have added here – BezierCurveBrush object. This is a pretty easy
object, with its own Draw function where we use ‘bezierCurveTo’ function to
draw curves between the first point (in the beginning of drawing) and all next
stored points.
Live Demo
download in package
Conclusion
Hope that today’s lesson was interesting for you. I will be glad to see your thanks and comments. Good luck!
Source: http://www.script-tutorials.com/html5-canvas-custom-brush1/
Opinions expressed by DZone contributors are their own.
Trending
-
Scaling Site Reliability Engineering (SRE) Teams the Right Way
-
How To Use Pandas and Matplotlib To Perform EDA In Python
-
The SPACE Framework for Developer Productivity
-
Part 3 of My OCP Journey: Practical Tips and Examples
Comments