当前位置: 首页 > 知识库问答 >
问题:

画布中的线条和矩形

微生博简
2023-03-14

我试图创建一个画布,在其中我们可以绘制直线和矩形使用鼠标事件的功能选择的输入。

我将mousedown、mousemove和mouseup事件侦听器附加到画布DOM,并在选择行输入或矩形输入时使用适当的函数

但它什么也没有画出来。

null

var canvas = document.getElementById("canvas");
var ctx = canvas.getContext("2d");
var canvasOffset = $("#canvas").offset();
var offsetX = canvasOffset.left;
var offsetY = canvasOffset.top;
var storedLines = [];
var startX = 0;
var startY = 0;
var isDown;
var isDrawing = false;
ctx.strokeStyle = "orange";
ctx.lineWidth = 3;


function handleRecUp() {
	isDrawing = false;
	canvas.style.cursor = "default";	
}

function handleRecMove(e) {
	if (isDrawing) {
		var mouseX = parseInt(e.clientX - offsetX);
		var mouseY = parseInt(e.clientY - offsetY);				
		
		ctx.clearRect(0, 0, canvas.width, canvas.height);
		ctx.beginPath();
		ctx.rect(startX, startY, mouseX - startX, mouseY - startY);
		ctx.stroke();
		
	}
}

function handleRecDown(e) {
	canvas.style.cursor = "crosshair";		
	isDrawing = true
	startX = parseInt(e.clientX - offsetX);
	startY = parseInt(e.clientY - offsetY);
}





function handleMouseDown(e) {
    e.preventDefault();   
    e.stopPropagation();
    
    var mouseX = parseInt(e.clientX - offsetX);
    var mouseY = parseInt(e.clientY - offsetY);
    
    isDown = true;
    startX = mouseX;
    startY = mouseY;
    
}

function handleMouseMove(e) {
    e.preventDefault();   
    e.stopPropagation();
    
    if (!isDown) {
        return;
    }
    
    redrawStoredLines();
    
    var mouseX = parseInt(e.clientX - offsetX);
    var mouseY = parseInt(e.clientY - offsetY);
    
    // draw the current line
    ctx.beginPath();
    ctx.moveTo(startX, startY);
    ctx.lineTo(mouseX, mouseY);
    ctx.stroke()
    
}


function handleMouseUp(e) {
    e.preventDefault();   
    e.stopPropagation();
    
    isDown = false;
    
    var mouseX = parseInt(e.clientX - offsetX);
    var mouseY = parseInt(e.clientY - offsetY);
    
    storedLines.push({
        x1: startX,
        y1: startY,
        x2: mouseX,
        y2: mouseY
    });
    
    redrawStoredLines();
    
}

function handleMouseOut(e) {
    e.preventDefault();   
    e.stopPropagation();
    
    if(!isDown){return;}
    
    isDown = false;
    
    var mouseX = parseInt(e.clientX - offsetX);
    var mouseY = parseInt(e.clientY - offsetY);
    
    storedLines.push({
        x1: startX,
        y1: startY,
        x2: mouseX,
        y2: mouseY
    });
    
    redrawStoredLines();
    
}


function redrawStoredLines() {
    
    ctx.clearRect(0, 0, canvas.width, canvas.height);
    
    if (storedLines.length == 0) {
        return;
    }
    
    // redraw each stored line
    for (var i = 0; i < storedLines.length; i++) {
        ctx.beginPath();
        ctx.moveTo(storedLines[i].x1, storedLines[i].y1);
        ctx.lineTo(storedLines[i].x2, storedLines[i].y2);
        ctx.stroke();
    }
}
 
    let l = document.getElementById("line");
    let c = document.getElementById("clear");
    let r = document.getElementById("rect");    

    
    
    if(l.checked === true)
    {
        $("#canvas").mousedown(function (e) {
    handleMouseDown(e);
});
$("#canvas").mousemove(function (e) {
    handleMouseMove(e);
});
$("#canvas").mouseup(function (e) {
    handleMouseUp(e);
});
$("#canvas").mouseout(function (e) {
    handleMouseOut(e);
});
       
    }

    if(c.checked === true)
    {
        
    storedLines.length = 0;
    redrawStoredLines();

        
    }

    if(r.checked === true)
    {
       $("#canvas").on('mousedown', function (e) {
    handleRecDown(e);
}).on('mouseup', function(e) {
    handleRecUp();
}).on('mousemove', function(e) {
    handleRecMove(e);
});
      
    }
    
body {
    background-color: ivory;
    padding:10px;
}
canvas {
    border:1px solid red;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<canvas id="canvas" width=300 height=300></canvas><br/>
<div>        
                <input type="radio" name="shape" id="clear" value="clear" checked>Clear<br>
                
                <input type="radio" name="shape" id="line" value="line">Line<br>
                
                <input type="radio" name="shape" id="rect" value="rect">Rectangle<br>                
              </div>

null

共有1个答案

邵畅
2023-03-14

您的if结构只执行一次,因此当用户单击某些内容时,更改不会被记录下来。

试试这样的方法:

$("input[type=radio]").on("change", handleRadioChanges);

function handleRadioChanges(event){
    if (l.checked === true) {
        $("#canvas").mousedown(function (e) {
            handleMouseDown(e);
        });
        $("#canvas").mousemove(function (e) {
            handleMouseMove(e);
        });
        $("#canvas").mouseup(function (e) {
            handleMouseUp(e);
        });
        $("#canvas").mouseout(function (e) {
            handleMouseOut(e);
        });

    }

    if (c.checked === true) {
        storedLines.length = 0;
        redrawStoredLines();
    }

    if (r.checked === true) {
        $("#canvas").on('mousedown', function (e) {
            handleRecDown(e);
        }).on('mouseup', function (e) {
            handleRecUp();
        }).on('mousemove', function (e) {
            handleRecMove(e);
        });
    }
}

包含更多错误修复的完整Javascript示例:

var canvas = document.getElementById("canvas");
var ctx = canvas.getContext("2d");
var canvasOffset = $("#canvas").offset();
var offsetX = canvasOffset.left;
var offsetY = canvasOffset.top;
var storedLines = [];
var startX = 0;
var startY = 0;
var isDown;
var type = "line"; // current type
ctx.strokeStyle = "orange";
ctx.lineWidth = 3;


function handleMouseDown(e) {
    e.preventDefault();
    e.stopPropagation();

    canvas.style.cursor = "crosshair";

    var mouseX = parseInt(e.clientX - offsetX);
    var mouseY = parseInt(e.clientY - offsetY);

    isDown = true;
    startX = mouseX;
    startY = mouseY;
}

function handleMouseMove(e) {
    e.preventDefault();
    e.stopPropagation();

    if (!isDown) return;

    redrawStoredLines();

    var mouseX = parseInt(e.clientX - offsetX);
    var mouseY = parseInt(e.clientY - offsetY);

    if(type == "rect"){
        ctx.beginPath();
        ctx.rect(startX, startY, mouseX - startX, mouseY - startY);
        ctx.stroke();
    }
    if(type == "line"){
        ctx.beginPath();
        ctx.moveTo(startX, startY);
        ctx.lineTo(mouseX, mouseY);
        ctx.stroke();
    }
}


function handleMouseUp(e) {
    canvas.style.cursor = "default";

    e.preventDefault();
    e.stopPropagation();

    isDown = false;

    var mouseX = parseInt(e.clientX - offsetX);
    var mouseY = parseInt(e.clientY - offsetY);

    storedLines.push({
        type: type,
        x1: startX,
        y1: startY,
        x2: mouseX,
        y2: mouseY
    });

    redrawStoredLines();
}

function handleMouseOut(e) {
    e.preventDefault();
    e.stopPropagation();

    if (!isDown) return;

    isDown = false;

    var mouseX = parseInt(e.clientX - offsetX);
    var mouseY = parseInt(e.clientY - offsetY);

    storedLines.push({
        type: type,
        x1: startX,
        y1: startY,
        x2: mouseX,
        y2: mouseY
    });

    redrawStoredLines();
}


function redrawStoredLines() {

    console.log(storedLines);

    ctx.clearRect(0, 0, canvas.width, canvas.height);

    if (storedLines.length == 0) return;

    // redraw each stored line
    for (var i = 0; i < storedLines.length; i++) {
        if(storedLines[i].type == "line"){
            ctx.beginPath();
            ctx.moveTo(storedLines[i].x1, storedLines[i].y1);
            ctx.lineTo(storedLines[i].x2, storedLines[i].y2);
            ctx.stroke();
        }
        if(storedLines[i].type == "rect"){
            ctx.beginPath();
            ctx.rect(storedLines[i].x1, storedLines[i].y1, 
                storedLines[i].x2 - storedLines[i].x1, storedLines[i].y2 - storedLines[i].y1);
            ctx.stroke();
        }
    }
}




let l = document.getElementById("line");
let c = document.getElementById("clear");
let r = document.getElementById("rect");

$("input[type=radio]").on("change", handleRadioChanges);

function handleRadioChanges(event) {
    if(l.checked){
        type = "line";
    }
    if(r.checked){
        type = "rect";
    }
    if (c.checked === true) {
        storedLines.length = 0;
        redrawStoredLines();
    }
}

$("#canvas").mousedown(function (e) {
    handleMouseDown(e);
});
$("#canvas").mousemove(function (e) {
    handleMouseMove(e);
});
$("#canvas").mouseup(function (e) {
    handleMouseUp(e);
});

 类似资料:
  • 我有以下代码应该在图像中绘制线条。我的代码是: 如果我编写,它实际上可以工作。但是我的数组很长并且来自一个输入。

  • 问题内容: 我有一个和画布,使用以下方式绘制: 绘图看起来很模糊(lineWidth小于1会产生更差的图片),并且在div的边界附近没有任何内容。是否可以使用画布获得与HTML相同的绘图质量? 问题答案: 在画布上绘制线条时,实际上需要跨越像素。我认为这是API中的一个奇怪选择,但易于使用: 代替这个: 做这个: 深入了解HTML5的画布一章,就可以很好地讨论这一点(寻找“ ASK PROFESS

  • 在IE9画布中现在是否支持虚线/点线?目前我正在做与以下内容非常相似的事情: 这在IE7、IE8、IE9兼容模式和FireFox中工作很好,然而,在IE9和Chrome中,为每条虚线绘制一个实心笔画。 对为什么会发生这种情况有什么想法吗?

  • 我在试着用画布画一个网格。逻辑相当简单:对于网格中的每个节点,我使用其左上角和右下角绘制一个矩形[代码如下]。 我没有做任何奇怪的事情,只是根窗口上的一个简单画布。

  • 根据之前的经验和在线文档,下面的代码应该生成两条垂直线,一条红色,另一条绿色。 取而代之的是,我得到两条绿线或者我最后设置的任何。 我看不出这个代码哪里错了。此外,可能是我的浏览器让事情变得一团糟。 JS小提琴和代码:

  • 实际上,我可以使用函数来完成。我从“HTML5画布-如何在图像背景上画一条线?”中得到的东西。但是我需要在不使用from函数的情况下绘制图像,如下所示: