Кисть с эффектом кривой Безье
Создадим ещё одну кисть, теперь уже с эффектом кривой Безье, для созданной нами ранее paint программы.
HTML
<div class="container">
<div class="column1">
<canvas id="color" width="500" height="128"></canvas>
</div>
<div class="column2">
<div>Предпросмотр:</div>
<div id="preview"></div>
<div id="pick"></div>
</div>
<div style="clear:both;"></div>
</div>
<canvas id="panel" width="1000" height="600"></canvas>
CSS
/* page layout styles */
*{
margin:0;
padding:0;
}
body {
background-color:#eee;
color:#fff;
font:14px/1.3 Arial,sans-serif;
}
.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;
}
jаvascript
Похожий код, только добавлена новая кисть:
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);
}
Ссылки