是否可以使用 SVG 矩形作为具有可变高度的 HTML 元素的边框

Posted

技术标签:

【中文标题】是否可以使用 SVG 矩形作为具有可变高度的 HTML 元素的边框【英文标题】:Is it possible to use an SVG rect as the border for an HTML element with variable height 【发布时间】:2015-06-19 20:54:12 【问题描述】:

我正在尝试使用 SVG 在具有固定宽度但灵活高度的 html 块周围创建虚线边框。我非常接近,但无法显示底部。

这是一个fiddle(小提琴包含了 SVG 图像,因此它可以内联 URL 编码元素,具体而言,#%23

SVG 代码如下所示:

<svg   xmlns="http://www.w3.org/2000/svg">
  <rect x="5" y="5"   
    style="fill: yellow; fill-opacity: 0.5; stroke: #009fe3; stroke-width: 3; stroke-linecap: round; stroke-dasharray: 1 7"/>
</svg>

这样的 CSS:

div.block 
  box-sizing: border-box;
  padding: 10px;
  width: 300px;
  background-image: url("dotted-border.svg");

我想我想要的是从底部偏移矩形,但它需要是一个像素值(5px)。看起来我想要的东西会随着更广泛的 SVG 2 采用 (http://www.w3.org/Graphics/SVG/WG/wiki/Proposals/Stroke_position) 变得微不足道,因为这样笔画就可以定位在形状内。

我知道我可以添加另一个图像并使用 CSS :after,但我很好奇!

【问题讨论】:

您可以使用preserveAspectRatio 属性,但虚线会根据内容高度看起来被拉伸或挤压:jsfiddle.net/eoLppgty/1 【参考方案1】:

为什么不改用简单的 CSS 边框?

div.block 
    box-sizing: border-box;
    padding: 10px;
    width: 300px;
    background-image: url("data:image/svg+xml;utf8,<svg width='300px' height='100%' xmlns='http://www.w3.org/2000/svg'><rect x='5' y='5' width='290' height='100%' style='fill: yellow; fill-opacity: 0.5; stroke: %23009fe3; stroke-width: 3; stroke-linecap: round; stroke-dasharray: 1 7'/></svg>");


div.block2 
    box-sizing: border-box;
    padding: 4px;
    margin:3px;
    width: 294px;
    background-color:rgba(255,255,0,0.5);
    border:3px dotted #009fe3;


/* Alternative method using CSS3 border-image: */
div.block3 
    box-sizing: border-box;
    padding: 4px;
    margin:3px;
    width: 294px;
    background-color:rgba(255,255,0,0.5);
    border:8px solid transparent;
    -webkit-border-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAYAAABzenr0AAAAbklEQVR4nGL4W8zBMJAYmbMCiJ9C8Qosimkijyz5Hw2vQNNME3mYgqdYFDxFMoBm8oPGAQMeBQOeCAdFNhxwB4yWA6PlwGg5MODZcMAdMFoOjJYDo+XAgGfDAXfAaDkwWg6MlgMDggEAAAD//wMAIRKl6nQ6gLIAAAAASUVORK5CYII=) round;
    -o-border-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAYAAABzenr0AAAAbklEQVR4nGL4W8zBMJAYmbMCiJ9C8Qosimkijyz5Hw2vQNNME3mYgqdYFDxFMoBm8oPGAQMeBQOeCAdFNhxwB4yWA6PlwGg5MODZcMAdMFoOjJYDo+XAgGfDAXfAaDkwWg6MlgMDggEAAAD//wMAIRKl6nQ6gLIAAAAASUVORK5CYII=) round;
    border-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAYAAABzenr0AAAAbklEQVR4nGL4W8zBMJAYmbMCiJ9C8Qosimkijyz5Hw2vQNNME3mYgqdYFDxFMoBm8oPGAQMeBQOeCAdFNhxwB4yWA6PlwGg5MODZcMAdMFoOjJYDo+XAgGfDAXfAaDkwWg6MlgMDggEAAAD//wMAIRKl6nQ6gLIAAAAASUVORK5CYII=) round;
    border-image-slice: 25%;
<div class="block">
    <article>Lorem ipsum dolor sit amet, consectetur adipisicing elit. Doloremque quasi officia vero aut. Velit ratione sapiente fugiat rerum eos ipsa praesentium autem similique vitae reprehenderit et tempora optio eveniet facilis. (SVG)</article>
</div>
<p></p>
<div class="block2">
    <article>Lorem ipsum dolor sit amet, consectetur adipisicing elit. Doloremque quasi officia vero aut. Velit ratione sapiente fugiat rerum eos ipsa praesentium autem similique vitae reprehenderit et tempora optio eveniet facilis. (CSS)</article>
</div>
<p></p>
<div class="block3">
    <article>Lorem ipsum dolor sit amet, consectetur adipisicing elit. Doloremque quasi officia vero aut. Velit ratione sapiente fugiat rerum eos ipsa praesentium autem similique vitae reprehenderit et tempora optio eveniet facilis. (CSS3)</article>
</div>

【讨论】:

我想使用点而不是破折号。当它们更大一点(更圆)时更有意义。 @boke_zero 在这种情况下,也许您可​​以使用 CSS3 边框图像。我将编辑我的答案以添加一个示例。 @squeamish ossifrage 经过谨慎处理,这似乎是目前的正确答案,可惜 Safari 中的角落被破坏了,但也许他们会解决这个问题。【参考方案2】:

无法在 svg 中计算正确的高度。而不是使用背景图像,用绝对定位的 div 包装 svg:

HTML

<div class="block">
    <article>Lorem ipsum dolor sit amet, consectetur adipisicing elit. Doloremque quasi officia vero aut. Velit ratione sapiente fugiat rerum eos ipsa praesentium autem similique vitae reprehenderit et tempora optio eveniet facilis.</article>
    <div class="back-svg">
        <svg   xmlns='http://www.w3.org/2000/svg'><rect   style='fill: yellow; fill-opacity: 0.5; stroke: #009fe3; stroke-width: 5; stroke-linecap: round; stroke-dasharray: 1 7'/></svg>
    </div>
</div>

CSS

html,body 
  height:100%;

div.block 
  position: relative;
  box-sizing: border-box;
  padding: 10px;
  width: 300px;
  border: 1px solid green;

div.back-svg 
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  z-index: -1;

小提琴:http://jsfiddle.net/k3v4by34/

【讨论】:

喜欢这个? jsfiddle.net/8ojbf9Lh/2我仍然无法显示底线。 @bloke_zero:我已经简化并添加了小提琴网址 谢谢 - 这确实回答了这个问题,但我认为需要额外的标记是一个问题。 @boke_zero 好的,那么您应该使用 CSS 制作边框,并可选择使用无边框的背景 SVG @boke_zero 您可以在运行时将绝对 div 添加到所有 div.block 元素

以上是关于是否可以使用 SVG 矩形作为具有可变高度的 HTML 元素的边框的主要内容,如果未能解决你的问题,请参考以下文章

是否可以有一个具有固定高度但可变宽度的元素的列流网格?

按矩形中心垂直对齐 SVG 内的矩形元素

如何根据文本宽度动态调整 SVG 矩形的大小?

试图创建一个没有剪辑路径的草率矩形

HTML5/CSS 根据其他列相互高度对齐列表项

具有多个视频源的SVG掩码?