使用CSS时画布会被拉伸,但是具有“ width” /“ height”属性的普通画布


194

我有2个画布,一个使用HTML属性width并调整height其大小,另一个使用CSS:

<canvas id="compteur1" width="300" height="300" onmousedown="compteurClick(this.id);"></canvas>
<canvas id="compteur2" style="width: 300px; height: 300px;" onmousedown="compteurClick(this.id);"></canvas>

Compteur1会像应该显示的那样显示,但不会像compteur2那样显示。内容是使用JavaScript在300x300画布上绘制的。

为什么会有显示差异?

替代文字

Answers:


215

似乎widthheight属性确定了画布坐标系的宽度或高度,而CSS属性仅确定了将在其中显示框的大小。

http://www.whatwg.org/html#attr-canvas-width(需要JS)或http://www.whatwg.org/c#attr-canvas-width(可能会占用您的计算机)中对此进行了说明。:

canvas元素有两个属性来控制元素的位图的大小:widthheight。指定这些属性时,它们的值必须是有效的非负整数。必须使用解析非负整数规则来获取其数值。如果缺少属性,或者解析其值返回错误,则必须使用默认值。该width属性默认为300,该height属性默认为150。


11
的确..我一直以为像“宽度”和“高度”属性直接在最近的HTML版本中不建议..
Sirber

4
哦,显然,在whatwg.org/specs/web-apps/current-work/multipage/…(部分#attr-canvas-width)中对此进行了很好的描述。麻烦的是,我width之前单击的是错误的,#dom-canvas-width而是转到了该部分。关于此文件,提起了w3.org/Bugs/Public/show_bug.cgi?id=9469
SamB 2010年

3
拥有一个看起来像但与其他API根本不同的API(css宽度,高度)。哇。
本阿斯顿

1
当您希望内部坐标系不同时,区分这些时间很重要。(即用于视网膜显示器或8bit风格的游戏)
Samy Bencherif

1
这真令人困惑。我们在哪里尝试在CSS中设置宽度和高度。花了我们两天的时间拉扯头发,找出有关宽度和高度的这两种不同的解释。只是哇...
NME新媒体娱乐

39

要设置widthheight您需要的,您可以使用

canvasObject.setAttribute('width', '475');

6
+1 el.setAttribute('width', parseInt($el.css('width')))做到了,谢谢
Shanimal 2012年

9
如果我希望画布具有相对大小该怎么办?也就是说,如何模仿width: 100%;CSS属性?
2013年

1
很好的答案,但是也不要忘记添加canvasObject.setAttribute('height','123')!
汤姆·威尔斯

我认为您不需要使用.setAttribute()我一直使用.width和.height属性
Zorgatone

4
使用getComputedStyle:的 JavaScript版本(无jQuery)canvas.setAttribute('width', window.getComputedStyle(canvas, null).getPropertyValue("width"));。重复该高度。
本J

25

对于<canvas>元素,CSS 会为要绘制到页面上的canvas元素确定规则widthheight设置其实际大小。另一方面,HTML属性widthheight设置画布API将使用的坐标系或“网格”的大小。

例如,考虑以下(jsfiddle):

var ctx = document.getElementById('canvas1').getContext('2d');
ctx.fillStyle = "red";
ctx.fillRect(10, 10, 30, 30);

var ctx2 = document.getElementById('canvas2').getContext('2d');
ctx2.fillStyle = "red";
ctx2.fillRect(10, 10, 30, 30);
canvas {
  border: 1px solid black;
}
<canvas id="canvas1" style="width: 50px; height: 100px;" height="50" width="100"></canvas>
<canvas id="canvas2" style="width: 100px; height: 100px;" height="50" width="100"></canvas>

相对于canvas元素的内部坐标,两者具有相同的绘制效果。但是在第二个画布中,红色矩形的宽度将是原来的两倍,这是因为CSS规则将整个画布拉伸到更大的区域。

注意:如果未指定width和和的CSS规则,height则浏览器将使用HTML属性来调整元素的大小,以使这些值中的1个单位等于页面上的1px。如果未指定这些属性,则它们将默认为widthof 300heightof 150


16

如果在CSS中设置宽度和高度,则画布将被拉伸。如果要动态控制画布的尺寸,则必须使用JavaScript,如下所示:

canvas = document.getElementById('canv');
canvas.setAttribute('width', '438');
canvas.setAttribute('height', '462');

1
大!感谢您的回答。我只好把canvas.setAttribute之前canvas.getContext('2d')避免图像拉伸。
hhh 2015年

6

浏览器使用CSS的宽度和高度,但是canvas元素根据画布的宽度和高度缩放。在javascript中,读取css的宽度和高度,并将画布的宽度和高度设置为该高度。

var myCanvas = $('#TheMainCanvas');
myCanvas[0].width = myCanvas.width();
myCanvas[0].height = myCanvas.height();

2

胫骨矫正

var el = $('#mycanvas');
el.attr('width', parseInt(el.css('width')))
el.attr('height', parseInt(el.css('height')))

0

CSS设置canvas元素的宽度和高度,以便影响坐标空间,使绘制的所有内容都倾斜

这是我如何使用Vanilla JavaScript设置宽度和高度的方法

canvas.width = numberForWidth

canvas.height = numberForHeight

-1

如果要基于CSS媒体查询等动态行为,请不要使用canvas的width和height属性。使用CSS规则,然后在获取画布渲染上下文之前,将CSS宽度和高度样式分配给width和height属性:

var elem = document.getElementById("mycanvas");

elem.width = elem.style.width;
elem.height = elem.style.height;

var ctx1 = elem.getContext("2d");
...

显然,如果仅在CSS中指定尺寸,则画布将获得默认的坐标尺寸(300 x 150)。但是,此建议对我不起作用,但以下解决方案可以。
林德伯格

@PerLindberg-如果您为canvas元素定义了CSS宽度和高度(以像素为单位),则此解决方案有效。
Manolo
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.