我有一张带有地图的画布。在该画布中,用户可以绘制(红色),最终结果将是:
在用户绘制任何他想要的东西后,我需要计算所有内容的边界框坐标,这样我才能最终拥有:
现在我可以遍历画布的每个像素并根据每个非空像素计算边界框,但这是一个非常繁重的操作。是否有更好的逻辑来实现预期的结果?
答案 0 :(得分:1)
您可以跟踪绘制的内容和点的直径。然后是边界的最小/最大值。
执行此操作的一种方法是跟踪正在绘制的内容的位置和半径(画笔)或边界(不规则形状),然后将其与当前最小/最大绑定合并以更新新绑定(如果需要,实际上“推”)总是匹配内部的界限。
示例强>
var ctx = c.getContext("2d"),
div = document.querySelector("div > div"),
// keep track of min/max for each axis
minX = Number.MAX_SAFE_INTEGER,
minY = Number.MAX_SAFE_INTEGER,
maxX = Number.MIN_SAFE_INTEGER,
maxY = Number.MIN_SAFE_INTEGER,
// brush/draw stuff for demo
radius = 10,
rect = c.getBoundingClientRect(),
isDown = false;
ctx.fillText("Draw something here..", 10, 10);
ctx.fillStyle = "red";
c.onmousedown = function() {isDown = true};
window.onmouseup = function() {isDown = false};
window.onmousemove = function(e) {
if (isDown) {
var x = e.clientX - rect.left;
var y = e.clientY - rect.top;
// When something is drawn, calculate its impact (position and radius)
var _minX = x - radius;
var _minY = y - radius;
var _maxX = x + radius;
var _maxY = y + radius;
// calc new min/max boundary
if (_minX < minX) minX = _minX > 0 ? _minX : 0;
if (_minY < minY) minY = _minY > 0 ? _minY : 0;
if (_maxX > maxX) maxX = _maxX < c.width ? _maxX : c.width;
if (_maxY > maxY) maxY = _maxY < c.height ? _maxY : c.height;
// show new bounds
showBounds();
// draw something
ctx.beginPath();
ctx.arc(x, y, radius, 0, 6.28);
ctx.fill();
}
};
function showBounds() {
// for demo, using bounds for display purposes (inclusive bound)
div.style.cssText =
"left:" + minX + "px;top:" + minY +
"px;width:" + (maxX-minX-1) + "px;height:" + (maxY-minY-1) +
"px;border:1px solid blue";
}
div {position:relative}
div > div {position:absolute;pointer-events:none}
<div>
<canvas id=c width=600 height=600></canvas>
<div></div>
</div>