首页 文章

如何清除画布以进行重绘

提问于
浏览
832

在尝试复合操作和在画布上绘制图像后,我现在正在尝试删除图像和合成 . 我该怎么做呢?

我需要清除画布以重绘其他图像;这可以持续一段时间,所以我不认为每次都会画一个新的矩形是最有效的选择 .

20 回答

  • 2
    • Chrome响应良好:@163277_正如@ Pentium10所建议的那样,但IE9似乎完全忽略了这条指令 .

    • IE9似乎响应: canvas.width = canvas.width; 但它没有't clear lines, just shapes, pictures and other objects unless you also use @John Allsopp'首先改变宽度的解决方案 .

    所以如果你有一个像这样创建的画布和上下文:

    var canvas = document.getElementById('my-canvas');
    var context = canvas.getContext('2d');
    

    你可以使用这样的方法:

    function clearCanvas(context, canvas) {
      context.clearRect(0, 0, canvas.width, canvas.height);
      var w = canvas.width;
      canvas.width = 1;
      canvas.width = w;
    }
    
  • 1032
    const context = canvas.getContext('2d');
    
    context.clearRect(0, 0, canvas.width, canvas.height);
    
  • 4

    通过传递x,y坐标以及画布的高度和宽度来使用clearRect方法 . ClearRect将整个画布清除为:

    canvas = document.getElementById("canvas");
    ctx = canvas.getContext("2d");
    ctx.clearRect(0, 0, canvas.width, canvas.height);
    
  • 4

    这是2018年,仍然没有完全清除画布重绘的本机方法 . clearRect() does 完全不清楚画布 . 非填充类型图纸未清除(例如 rect()

    1.无论你如何画画,都要用 completely 清晰画布:

    context.clearRect(0, 0, context.canvas.width, context.canvas.height);
    context.beginPath();
    

    优点:保留strokeStyle,fillStyle等;没有滞后;

    缺点:如果您在绘制任何内容之前已经在使用beginPath,则不必要

    2.使用宽度/高度黑客:

    context.canvas.width = context.canvas.width;
    

    要么

    context.canvas.height = context.canvas.height;
    

    优点:适用于IE Cons:将strokeStyle,fillStyle重置为黑色; Laggy;

    我想知道为什么本机解决方案不存在 . 实际上, clearRect() 被视为单行解决方案,因为大多数用户在绘制任何新路径之前都会执行 beginPath() . 虽然beginPath只用于绘制线条而不是像 rect(). 那样的封闭路径

    这就是为什么接受的答案没有解决我的问题,我最终浪费时间尝试不同的黑客 . 诅咒你mozilla

  • 110
    function clear(context, color)
    {
        var tmp = context.fillStyle;
        context.fillStyle = color;
        context.fillRect(0, 0, context.canvas.width, context.canvas.height);
        context.fillStyle = tmp;
    }
    
  • 13

    我发现在我测试的所有浏览器中,最快的方法是实际用白色填充颜色,或者你想要的颜色 . 我有一个非常大的显示器,在全屏模式下,clearRect令人痛苦地慢,但fillRect是合理的 .

    context.fillStyle = "#ffffff";
    context.fillRect(0,0,canvas.width, canvas.height);
    

    缺点是画布不再透明 .

  • 19

    如果你只使用clearRect,如果你在一个表格中提交你的图纸,你将得到一个提交而不是清算,或者可以先清除它然后上传一个空白图纸,所以你需要添加一个在函数开始时阻止默认:

    function clearCanvas(canvas,ctx) {
            event.preventDefault();
            ctx.clearRect(0, 0, canvas.width, canvas.height);
        }
    
    
    <input type="button" value="Clear Sketchpad" id="clearbutton" onclick="clearCanvas(canvas,ctx);">
    

    希望它可以帮到某人 .

  • 199

    最快的方式:

    canvas = document.getElementById("canvas");
    c = canvas.getContext("2d");
    
    //... some drawing here
    
    i = c.createImageData(canvas.width, canvas.height);
    c.putImageData(i, 0, 0); // clear context by putting empty image data
    
  • 4
    Context.clearRect(starting width, starting height, ending width, ending height);
    

    示例: context.clearRect(0, 0, canvas.width, canvas.height);

  • 0

    使用:context.clearRect(0,0,canvas.width,canvas.height);

    这是清除整个画布的最快,最具描述性的方法 .

    不要使用:canvas.width = canvas.width;

    重置 canvas.width 重置所有画布状态(例如转换,lineWidth,strokeStyle等),它非常慢(与clearRect相比),它没有描述你实际上想要做的事情 .

    处理变换后的坐标

    如果您修改了变换矩阵(例如,使用 scalerotatetranslate ),那么 context.clearRect(0,0,canvas.width,canvas.height) 可能无法清除画布的整个可见部分 .

    解决方案?在清除画布之前重置转换矩阵:

    // Store the current transformation matrix
    context.save();
    
    // Use the identity matrix while clearing the canvas
    context.setTransform(1, 0, 0, 1, 0, 0);
    context.clearRect(0, 0, canvas.width, canvas.height);
    
    // Restore the transform
    context.restore();
    

    Edit: 我刚刚进行了一些分析,并且(在Chrome中)在不重置转换的情况下清除300x150(默认大小)画布的速度提高了约10% . 随着画布的大小增加,这种差异会下降 .

    这已经相对微不足道了,但在大多数情况下,你的吸引力远远超过你的清理范围,我认为这种性能差异无关紧要 .

    100000 iterations averaged 10 times:
    1885ms to clear
    2112ms to reset and clear
    
  • 3

    其他人已经完成了回答这个问题的出色工作,但是如果上下文对象上的一个简单的 clear() 方法对你有用(对我来说是这样的),那么这就是我根据答案使用的实现:

    CanvasRenderingContext2D.prototype.clear = 
      CanvasRenderingContext2D.prototype.clear || function (preserveTransform) {
        if (preserveTransform) {
          this.save();
          this.setTransform(1, 0, 0, 1, 0, 0);
        }
    
        this.clearRect(0, 0, this.canvas.width, this.canvas.height);
    
        if (preserveTransform) {
          this.restore();
        }           
    };
    

    用法:

    window.onload = function () {
      var canvas = document.getElementById('canvasId');
      var context = canvas.getContext('2d');
    
      // do some drawing
      context.clear();
    
      // do some more drawing
      context.setTransform(-1, 0, 0, 1, 200, 200);
      // do some drawing with the new transform
      context.clear(true);
      // draw more, still using the preserved transform
    };
    
  • 1

    这里有很多好的答案 . 还需要注意的是,有时仅部分清除画布会很有趣 . 也就是说,“淡出”前一个图像而不是完全删除它 . 这可以给出好的小道效果 .

    这很简单 . 假设您的背景颜色为白色:

    // assuming background color = white and "eraseAlpha" is a value from 0 to 1.
    myContext.fillStyle = "rgba(255, 255, 255, " + eraseAlpha + ")";
    myContext.fillRect(0, 0, w, h);
    
  • 677

    一个简单但不太可读的方法是写这个:

    var canvas = document.getElementId('canvas');
    
    // after doing some rendering
    
    canvas.width = canvas.width;  // clear the whole canvas
    
  • 4
    context.clearRect(0,0,w,h)
    

    用RGBA值填充给定的矩形:
    0 0 0 0:使用Chrome
    0 0 0 255:使用FF和Safari

    context.clearRect(0,0,w,h);    
    context.fillStyle = 'rgba(0,0,0,1)';  
    context.fillRect(0,0,w,h);
    

    让矩形填充
    0 0 0 255
    无论是浏览器!

  • 0

    这是我使用的,无论边界和矩阵变换:

    function clearCanvas(canvas) {
      const ctx = canvas.getContext('2d');
      ctx.save();
      ctx.globalCompositeOperation = 'copy';
      ctx.strokeStyle = 'transparent';
      ctx.beginPath();
      ctx.lineTo(0, 0);
      ctx.stroke();
      ctx.restore();
    }
    

    基本上,它保存上下文的当前状态,并绘制 copyglobalCompositeOperation的透明像素 . 然后,恢复先前的上下文状态 .

  • 0

    在webkit中,您需要将宽度设置为不同的值,然后您可以将其设置回初始值

  • -2

    这适用于chart.js中的pieChart

    <div class="pie_nut" id="pieChartContainer">
        <canvas id="pieChart" height="5" width="6"></canvas> 
    </div>
    
    $('#pieChartContainer').html(''); //remove canvas from container
    $('#pieChartContainer').html('<canvas id="pieChart" height="5" width="6"></canvas>'); //add it back to the container
    
  • 9

    这些都是很好的例子你清除标准画布,但如果你使用paperjs,那么这将工作:

    在JavaScript中定义全局变量:

    var clearCanvas = false;
    

    从您的PaperScript定义:

    function onFrame(event){
        if(clearCanvas && project.activeLayer.hasChildren()){
            project.activeLayer.removeChildren();
            clearCanvas = false;
        }
    }
    

    现在,只要将clearCanvas设置为true,它就会清除屏幕上的所有项目 .

  • 34

    如果你画线,请确保你不要忘记:

    context.beginPath();
    

    否则线路将不会被清除 .

  • 4

    一个快速的方法是做

    canvas.width = canvas.width
    

    Idk它是如何工作但它确实如此!

相关问题