【问题标题】:Canvas resize throwing off listeners x y画布调整大小以摆脱听众 x y
【发布时间】:2014-05-03 07:11:10
【问题描述】:

在我的 html 中,我有以下内容可将画布调整为宽度和高度百分比。

#canvas,
#canvasCursor {
    cursor: none;
    background: #fff;
    position: absolute;
    left: 50px;
    top: 30px;
    width: 62%;
    height: 80%;
    z-index: 1;
}

但是,这似乎增加了绘图的大小和 x y 侦听器。
只需 click here,您就会明白我的意思。

【问题讨论】:

    标签: javascript jquery canvas html5-canvas


    【解决方案1】:

    两个问题:

    1) 您正在使用 CSS 规则设置画布的宽度。这不会很好地工作。如果您没有为画布设置大小,则无论您通过 CSS 设置什么,它都会默认为 300 x 150 像素。这意味着其中的所有内容都被缩放(就好像它是一个固定大小的图像,基本上就是画布)。如果您确实设置了尺寸但仍使用 CSS,该尺寸将被缩放。

    您会降低性能和质量,并且还需要重新计算鼠标位置。

    您需要通过 Javascript 更新大小。

    #canvas, #canvasCursor {
        cursor: none;
        background: #fff;
        position: absolute;
        left: 50px;
        top: 30px;
        width: 62%; /* REMOVE */
        height: 80%;  /* REMOVE */
        z-index: 1;
    }
    

    2) 您不会从任何地方更新画布大小。您可以通过设置其宽度和高度属性来更新画布 - 将其设置为您可以使用的窗口大小:

        window.onresize = function() {
            canvas.width = window.innerWidth;
            canvas.height = window.innerHeight;
    
            //call redraw
       }
    

    或者,如果您想将其设置为百分比,则需要自己计算,因为画布不采用 % 值。

        window.onresize = function() {
            canvas.width = window.innerWidth * 0.62; //ie. 62% of width
            canvas.height = window.innerHeight * 0.8; //ie. 80% of height
    
            //call redraw
       }
    

    Canvas 仅使用像素大小,因为此元素是一种特殊情况。

    为什么是innerWidth/Height?这代表您看到的窗口的实际视口(使用移动设备会更清楚地看到)。

    如果你只想要一个固定的大小,你可以直接设置:

    canvas.width = 800;
    canvas.height = 600;
    

    为什么需要更新(重绘所有内容)? Canvas 只保存绘制到它的任何内容的快照 - 它不保留它的副本。就是屏幕上的内容。

    调整大小时,它会重新初始化,因此您需要再次更新它。除非您有很多东西要重绘,否则这将几乎没有性能成本。这只会在用户调整浏览器窗口大小时发生。

    【讨论】:

    • 它有效,谢谢。然而听众不是他们搞砸了。我认为它们是基于我的画布宽度/高度的任何想法? taffatech.com/Paint.html 这是监听器的代码:mouseX = e.pageX - this.offsetLeft; mouseY = e.pageY - this.offsetTop;
    • @StevenBarrett 啊,鼠标坐标请看我的回答:stackoverflow.com/questions/17130395/…
    • 算了!谢谢! - 对于其他人,请记住更改所有画布图层的大小,而不仅仅是主要图层,否则听众将不会排队!
    【解决方案2】:

    问题出在您的 javascript 中。我在您提供的网站上检查了您的 Paint.js。 你用过

    var canvas = document.getElementById('canvas'),
    ctx = canvas.getContext('2d'),
    canvasWidth = canvas.width,
    canvasHeight = canvas.height;
    

    同时,您的 html 中的画布宽度和高度设置为 800*600。

    <canvas id="canvas" width="800" height="500"></canvas>
    

    因此,canvas.width(height) 将返回 html 中的任何内容。然后您使用 800 和 600 进行计算,而不是画布的实际尺寸。这就是为什么画布看起来以一种奇怪的方式放大的原因。

    您应该使用canvas.scrollWidthcanvas.scrollHeight 来获取实际的宽度和高度信息。祝你好运!

    【讨论】:

    • 我已经删除了宽度和高度并按百分比设置,但没有什么不同。
    【解决方案3】:

    请注意,当画布调整大小时,它会自动清理,这意味着画在上面的所有东西都完全消失了。所以我建议你要么不要选择百分比,要么在 resize 事件上附加重绘功能!

    【讨论】:

    • 在这种情况下,我必须将每个形状保存到一个数组中,对吧?这会减慢一切吗?
    【解决方案4】:

    当画布调整大小时,您需要相应地重置其宽度和高度。您可以在onresize 事件中执行此操作:

    window.onresize = function () {
        canvas.width  = canvas.offsetWidth;
        canvas.height = canvas.offsetHeight;
    
        // repaint everything
    }
    

    您需要为绘图画布和光标画布执行此操作。请记住,当画布调整大小和you will need to repaint 时,所有内容都会被清除。

    【讨论】:

    • 这是否意味着我需要保存在画布上绘制的所有内容。这会减慢绘图程序的速度吗?
    猜你喜欢
    • 1970-01-01
    • 2021-07-29
    • 1970-01-01
    • 2010-10-09
    • 2013-10-06
    • 2011-03-14
    • 2013-12-15
    • 2013-11-19
    • 2014-11-04
    相关资源
    最近更新 更多