javascript - Drawing soft brush -
i'm trying create smooth brush in html5, example below.
this tried, it's something. it's not smooth image above.
editor.drawing.context.globalalpha = 0.3; var amount = 3; for(var t = -amount; t <= amount; t += 3) { for(var n = -amount; n <= amount; n += 3) { editor.drawing.context.drawimage(editor.drawing.clipcanvas, -(n-1), -(t-1)); } }
and looks this.
using brushes
choose brush, can image predefined brushes or can make 1 using off-screen canvas , draw radial gradient it. simplicity made simple image brush such these:
then each new point drawn canvas:
- calculate diff between previous , current point
- calculate length of line can use absolute step value independent of length
- iterate on length using normalized value , calculated step value
the step value can looks result - largely depends on smoothness of brush general size (smoother brushes require smaller steps blend each other).
for demo used brush-width, smaller values used, more brushes drawn along line, nicer result, can slow down program, find value compromises quality , speed.
for example:
this called every time new point registered when drawing:
function brushline(ctx, x1, y1, x2, y2) { var diffx = math.abs(x2 - x1), // calc diffs diffy = math.abs(y2 - y1), dist = math.sqrt(diffx * diffx + diffy * diffy), // find length step = 20 / (dist ? dist : 1), // "resolution" = 0, // iterator length t = 0, // t [0, 1] b, x, y; while (i <= dist) { t = math.max(0, math.min(1, / dist)); x = x1 + (x2 - x1) * t; y = y1 + (y2 - y1) * t; b = (math.random() * 3) | 0; ctx.drawimage(brush, x - bw * 0.5, y - bh * 0.5); // draw brush += step; } }
demo
var brush = new image(); brush.onload = ready; brush.src = "http://i.stack.imgur.com/hsbva.png"; function ready() { var c = document.queryselector("canvas"), ctx = c.getcontext("2d"), isdown = false, px, py, bw = this.width, bh = this.height; c.onmousedown = c.ontouchstart = function(e) { isdown = true; var pos = getpos(e); px = pos.x; py = pos.y; }; window.onmousemove = window.ontouchmove = function(e) { if (isdown) draw(e); }; window.onmouseup = window.ontouchend = function(e) { e.preventdefault(); isdown = false }; function getpos(e) { e.preventdefault(); if (e.touches) e = e.touches[0]; var r = c.getboundingclientrect(); return { x: e.clientx - r.left, y: e.clienty - r.top } } function draw(e) { var pos = getpos(e); brushline(ctx, px, py, pos.x, pos.y); px = pos.x; py = pos.y; } function brushline(ctx, x1, y1, x2, y2) { var diffx = math.abs(x2 - x1), diffy = math.abs(y2 - y1), dist = math.sqrt(diffx * diffx + diffy * diffy), step = bw / (dist ? dist : 1), = 0, t = 0, b, x, y; while (i <= dist) { t = math.max(0, math.min(1, / dist)); x = x1 + (x2 - x1) * t; y = y1 + (y2 - y1) * t; b = (math.random() * 3) | 0; ctx.drawimage(brush, x - bw * 0.5, y - bh * 0.5); += step } } }
body {background: #777} canvas {background: #fff;cursor:crosshair}
<canvas width=630 height=500></canvas>
you can use technique simulate variety of brushes (i use code on current landing page simulate chalk pen).
tip: small modification can variate width depending on velocity increase realism (not shown).
Comments
Post a Comment