使用某种映射门户。使用了@SimonSarris的教程:A Gentle Introduction to Making HTML5 Canvas Interactive
一直顺利,但我遇到了路径中风问题。我一直试图找到需要添加beginPath()
的位置,以确保在选择Shape时,背景中的网格线不会更改为相同的lineWidth
值。到目前为止,有很多代码,我在这里运行:http://jsfiddle.net/Twisty/me4fkthe/
当我添加形状时,我看到:
当我选择并移动形状时,我会看到:
以下是我的代码的基础知识:
function rTent(x, y, w, h, fill, lbl) {
// Rect / Square tent
this.x = x || 0;
this.y = y || 0;
this.w = (w * 10) || 100;
this.h = (h * 10) || 100;
this.fc = fill || "rgba(255, 125, 125, 0.65)";
this.lbl = lbl || "Tent";
this.sqft = (w * h) || 100;
}
rTent.prototype.draw = function (ctx) {
ctx.beginPath();
ctx.fillStyle = this.fc;
ctx.fillRect(this.x, this.y, this.w, this.h);
ctx.strokeStyle = "#000";
ctx.lineWidth = 1.5;
ctx.strokeRect(this.x, this.y, this.w, this.h);
console.log("Draw Rect Tent Completed, W:" + this.w + ", L:" + this.h + " (" + this.x + "," + this.y + ") Color: " + this.fc);
ctx.textBaseLine = "top";
ctx.textAlign = "center";
ctx.font = "11px Verdana";
ctx.fillStyle = "#000";
ctx.fillText(
this.lbl, (this.x + this.w / 2), (this.y + this.h / 2) - 14);
ctx.fillText(
"SQFT:" + (this.w / 10) * (this.h / 10), (this.x + this.w / 2), (this.y + this.h / 2)
);
ctx.closePath();
};
rTent.prototype.contains = function (mx, my) {
return (this.x <= mx) && (this.x + this.w >= mx) && (this.y <= my) && (this.y + this.h >= my);
};
// skipping CanvasState definition - see jsFiddle ...
CanvasState.prototype.addShape = function (shape) {
this.shapes.push(shape);
this.valid = false;
};
CanvasState.prototype.clear = function () {
this.ctx.clearRect(0, 0, this.width, this.height);
};
// While draw is called as often as the INTERVAL variable demands,
// It only ever does something if the canvas gets invalidated by our code
CanvasState.prototype.draw = function () {
// if our state is invalid, redraw and validate!
if (!this.valid) {
var ctx = this.ctx;
var shapes = this.shapes;
this.clear();
// ** Add stuff you want drawn in the background all the time here **
// This is where GridLine are redrawn in the background
this.drawGrid();
// draw all shapes
var l = shapes.length;
for (var i = 0; i < l; i++) {
var shape = shapes[i];
// We can skip the drawing of elements that have moved off the screen:
if (shape.x > this.width || shape.y > this.height || shape.x + shape.w < 0 || shape.y + shape.h < 0) continue;
shapes[i].draw(ctx);
}
// draw selection
// right now this is just a stroke along the edge of the selected Shape
if (this.selection !== null) {
ctx.beginPath();
ctx.strokeStyle = this.selectionColor;
ctx.lineWidth = this.selectionWidth;
var mySel = this.selection;
ctx.strokeRect(mySel.x, mySel.y, mySel.w, mySel.h);
}
// ** Add stuff you want drawn on top all the time here **
this.valid = true;
}
};
// More code skipped - see js Fiddle ...
CanvasState.prototype.drawGrid = function () {
var gridOptions = {
minorLines: {
separation: 10,
color: '#ddd'
},
majorLines: {
separation: 100,
color: '#ccc'
},
majorLabel: {
font: 'Verdana',
fontSize: '8px',
fontColor: '#000'
}
};
this.drawGridLines(gridOptions.minorLines, '');
this.drawGridLines(gridOptions.majorLines, gridOptions.majorLabel);
};
CanvasState.prototype.drawGridLines = function (lineOptions, labelOptions) {
var iWidth = this.width;
var iHeight = this.height;
var ctx = this.ctx;
ctx.strokeStyle = lineOptions.color;
ctx.strokeWidth = 1;
ctx.beginPath();
var iCount = null;
var gc = 0;
var gi = null;
var gx = null;
var gy = null;
var labelOff = 10;
iCount = Math.floor(iWidth / lineOptions.separation);
if (typeof labelOptions !== 'string') {
ctx.textBaseline = "top";
ctx.textAlign = "center";
ctx.font = labelOptions.fontSize + " " + labelOptions.font;
ctx.fillText("0", 10, 2);
gc = ((iWidth + 1) / 10);
ctx.fillText(gc.toString(), iWidth - labelOff, 2);
}
for (gi = 1; gi <= iCount; gi += 1) {
gx = (gi * lineOptions.separation);
if (typeof labelOptions != 'string') {
gc = gx / 10;
ctx.fillText(gc.toString(), gx, 2);
}
ctx.beginPath()
ctx.moveTo(0.5 + gx, labelOff);
ctx.lineTo(0.5 + gx, iHeight - labelOff + 1);
ctx.stroke();
}
iCount = Math.floor(iHeight / lineOptions.separation);
if (typeof labelOptions !== 'string') {
ctx.textBaseline = "middle";
ctx.textAlign = "left";
ctx.fillText("0", 2, 11);
gc = ((iHeight + 1) / 10);
ctx.fillText(gc.toString(), 0, iHeight - labelOff);
}
for (gi = 1; gi <= iCount; gi += 1) {
gy = (gi * lineOptions.separation);
if (typeof labelOptions != 'string') {
gc = gy / 10;
ctx.fillText(gc.toString(), 0, gy);
}
ctx.beginPath();
ctx.moveTo(labelOff, 0.5 + gy);
ctx.lineTo(iWidth - labelOff, 0.5 + gy);
ctx.stroke();
}
ctx.closePath();
};
$(function () {
var s = new CanvasState(document.getElementById('fpCanvas'));
$("#add_tent_btn").click(function () {
if ($("#tent_shape_choice").val() == "hex") {
s.addShape(new hTent(
120,
120,
$("#tent_w").val(),
50,
$("#tent_color_choice").val()
));
} else {
s.addShape(new rTent(
120,
120,
$("#tent_w").val(),
$("#tent_l").val(),
$("#tent_color_choice").val()
));
}
});
});
当我选择一个形状时会发生这种情况,在lineWidth = 2;
的对象周围添加一个笔划。将beginPath()
添加到我能想到的很多地方之后,它仍会导致背景发生变化。
答案 0 :(得分:2)
您使用了两种不同的方法来设置lineWidth:
lineWidth和strokeWidth。通过在函数CanvasState.prototype.drawGridLines
中添加一行来解决您的问题。
以下是代码的快照:
CanvasState.prototype.drawGridLines = function (lineOptions, labelOptions) {
var iWidth = this.width;
var iHeight = this.height;
var ctx = this.ctx;
ctx.lineWidth = 1; //<-- the new line
ctx.strokeStyle = lineOptions.color;
ctx.strokeWidth = 1;
//The rest of the code...