代码之家  ›  专栏  ›  技术社区  ›  Temani Afif

为什么框大小调整不适用于画布元素的宽度/高度属性?

  •  1
  • Temani Afif  · 技术社区  · 6 年前

    .canvas {
      width:150px;
      height:150px;
    }
    canvas {
      box-sizing:border-box;
      border:5px solid;
    }
    <canvas height="150" width="150"></canvas>
    <canvas class="canvas"></canvas>

    我们有两个 canvas 使用相同的宽度/高度、相同的边框和 box-sizing:border-box . 我们可以清楚地看到,我们使用CSS属性的画布尊重 box-sizing (边框从宽度/高度减少),但使用属性定义的第一个边框将被忽略 盒子尺寸

    我首先认为它与attribute的使用有关,但在使用attribute时,它似乎没有达到预期的效果 img iframe

    .canvas {
      width:150px;
      height:150px;
    }
    iframe,img {
      box-sizing:border-box;
      border:5px solid;
    }
    <iframe height="150" width="150"></iframe>
    <iframe class="canvas"></iframe>
    
    <img height="150" width="150" src="https://picsum.photos/200/300?image=1069">
    <img class="canvas" src="https://picsum.photos/200/300?image=1069">

    为什么会有这样的行为 帆布 元素?


    var canvas = document.querySelector("canvas"),
    ctx = canvas.getContext("2d");
    ctx.fillRect(0, 0, 150, 150);
    canvas {
      width: 150px;
      height: 150px;
      border:1px solid red;
    }
    <canvas ></canvas>

    直观地说,上面的代码应该生成一个 150x150 正方形,但我们以长方形结束!这是因为画布最初是 300x150

    但是,使用属性将创建所需的结果:

    var canvas=document.querySelector(“canvas”),
    ctx.fillRect(0,0,150,150);
    canvas {
      border:1px solid red;
    }
    <canvas height="150" width="150"></canvas>

    这从某种程度上解释了为什么浏览器忽略了它 为了避免收缩效应,但它仍然会违反直觉,因为它可能会导致系统之外的其他不需要的问题 帆布 . 如果这是原因,那么broswer也应该对 img 因为它们面临着同样的收缩效应。

    那么,为什么会有这样的行为呢?为什么浏览器决定忽略 而不是缩小画布?

    最重要的问题:

    我无法找到规范的哪一部分处理此问题。

    1 回复  |  直到 6 年前
        1
  •  5
  •   Alohci    6 年前

    我猜是的 this paragraph from the spec

    这就是问题所在 必须从“高度”和“宽度”属性中获取。盒子大小不起作用。

    还请注意,HTML5呈现部分指出:

        2
  •  1
  •   Kaiido NickSlash    5 年前

    A<帆布> intrinsic width and height 是由它的 width height
    这些 default to 300 and 150 respectively .

    因此,要使<img>案例与您的<帆布>在这种情况下,您实际上必须在第一个<img>第二个是300x150px。

    .canvas {
      width:150px;
      height:150px;
    }
    iframe,img {
      box-sizing:border-box;
      border:5px solid;
    }
    <!-- equivalent to 
    <canvas width="150" height="150"></canvas>
    load a 150x150px image -->
    <img src="https://picsum.photos/150/150?image=1069">
    
    <!-- equivalent to 
    <canvas class="canvas"></canvas>
    load a 300x150px image -->
    <img class="canvas" src="https://picsum.photos/300/150?image=1069">

    现在我们看到了<帆布>及<img>实际上,他们的行为完全相同:他们遵循 inline-replaced elements rules (CSS2) 这是在重新编码 CSS-images-3 ,以获得大致相同的结果 .

    当他们计算 高度 auto box-sizing 不扮演任何角色,其固有的 宽度 高度 正在使用。
    当您通过CSS设置它时,CSS将赢得 大师。