以下是SVG2 specification的一些相关摘录:
8.3. The initial viewport
除非满足以下条件,否则初始视口的宽度必须是最外层svg元素上宽度表示属性的值:SVG内容是通过引用嵌入的单独存储的资源(例如HTML中的对象元素) ,或SVG内容嵌入在包含文档中;并使用CSS设置引用元素或包含文档的样式;并且在引用元素(例如,对象元素)上或在包含文档的最外面的svg元素上指定的CSS兼容定位属性足以 Build 视口的宽度 . 在这些条件下,必须通过定位属性 Build 视口的宽度 . [同样适用于身高]
8.12. Intrinsic sizing properties of SVG content
必须使用以下算法计算固有宽高比 . 如果算法返回null,则没有固有的宽高比 . 如果svg元素上的宽度和高度大小属性都是绝对值:返回宽度/高度如果SVG视图处于活动状态:让viewbox成为活动SVG视图定义的视图框返回viewbox.width / viewbox.height如果viewBox on正确指定了svg元素:让viewbox成为svg元素上viewBox属性定义的视图框返回viewbox.width / viewbox.height返回null
The Code
我在svg中制作了一个汉堡包按钮,我试图弄清楚它的视口尺寸究竟是怎么回事,因为我们用svg表示属性和CSS指定它 .
svg#ham-btn {
margin: 2rem;
border: 1px solid black;
fill: #383838;
width: 10vw;
height: auto;
}
<svg id="ham-btn" width="107.5px" height="80px" viewBox="0 0 80 80" preserveAspectRatio="xMidYMid meet" xmlns="http://www.w3.org/2000/svg">
<style>
#ham-btn {
cursor: pointer;
}
#ham-btn rect {
transform-box: fill-box;
transform-origin: 50% 50%;
outline: 1px solid transparent;
transition: transform 0.2s;
}
#ham-btn:hover #r2 {
transform: translate(118%, 0);
}
#ham-btn:hover #r1 {
transform: translate(0%, 191.66%) rotate(36deg) scaleX(1.1);
}
#ham-btn:hover #r3 {
transform: translate(0%, -191.66%) rotate(-36deg) scaleX(1.1);
}
</style>
<rect id="r3" x="0" y="71.25%" width="100%" height="15%" rx="5%" />
<rect id="r2" x="0" y="42.5%" width="100%" height="15%" rx="5%"/>
<rect id="r1" x="0" y="13.75%" width="100%" height="15%" rx="5%" />
</svg>
The Question
我的解决方案取决于视口比率(107.5 / 80)与 viewBox
比率(80/80)不同的事实 . 这是导致居中的原因(通过 preserveAspectRatio
) . 如果更改视口宽高比,则会破坏解决方案 .
因此,我的问题是:为什么CSS中的设置尺寸与直接在svg中设置它不一样?为什么CSS高度和宽度似乎没有覆盖SVG中指定的高度和宽度(因为上面的第一个规范摘录表明它应该) .
My Best Guess
-
svg
width
/height
表示属性定义了svg元素的内在宽高比(从上面的第二个规范摘录中可以看出) -
然后,CSS完全覆盖了宽度和高度(从上面的第一个规范摘录中可以看出)
-
这解释了为什么有必要在CSS中明确地将高度设置为
auto
. 如果我们没有这样做,svg的高度将回落到指定的80px,从而扭曲形状
关于这个猜测是否正确的任何想法?