svg固定字体大小

时间:2017-04-25 07:33:33

标签: html css svg

我有一个SVG内联到HTML代码。它的尺寸适合宽度,保留纵横比。有没有办法将字体大小设置为可以通过媒体查询控制的视口?

修改 问题是当我在宽度范围内设置固定的字体大小时,无论如何相对于svg大小调整字体大小。

#svg-container {
  width: 100%;
  padding-bottom: 70%;
  overflow: hidden;
  border: 1px solid red;
}

#svg-container svg text tspan {
  font-size: 14px;
}


@media (min-height: 800px) {
  #svg-container svg text tspan {
    font-size: 50px;
  }
}
<div id="svg-container">
<svg
   xmlns:dc="http://purl.org/dc/elements/1.1/"
   xmlns:cc="http://creativecommons.org/ns#"
   xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
   xmlns:svg="http://www.w3.org/2000/svg"
   xmlns="http://www.w3.org/2000/svg"
   xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
   xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
   version="1.1"
   viewBox="0 0 500 350"
   data-name="Layer 1"
   id="Layer_1"
   inkscape:version="0.91 r13725"
   sodipodi:docname="Desktop_Enhanced.svg"
   width="100%"
   style="position: absolute; left: 0; top: 0;"   
  >
  <sodipodi:namedview
     pagecolor="#ffffff"
     bordercolor="#666666"
     borderopacity="1"
     objecttolerance="10"
     gridtolerance="10"
     guidetolerance="10"
     inkscape:pageopacity="0"
     inkscape:pageshadow="2"
     inkscape:window-width="1280"
     inkscape:window-height="961"
     id="namedview51"
     showgrid="false"
     inkscape:zoom="1.0054235"
     inkscape:cx="231.42799"
     inkscape:cy="361.93137"
     inkscape:window-x="1272"
     inkscape:window-y="-8"
     inkscape:window-maximized="1"
     inkscape:current-layer="Layer_1"
     fit-margin-bottom="150" />
  <metadata
     id="metadata75">
    <rdf:RDF>
      <cc:Work
         rdf:about="">
        <dc:format>image/svg+xml</dc:format>
        <dc:type
           rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
        <dc:title>Desktop</dc:title>
      </cc:Work>
    </rdf:RDF>
  </metadata>
  <defs
     id="defs3">
    <style
       id="style5">.cls-1{fill:#da1f26;}.cls-2{fill:#252e43;}.cls-3{fill:#d1d3d4;}</style>
  </defs>
  <title
     id="title7">Desktop</title>
  <polyline
     id="polyline9"
     points="329.4 62.24 343.54 76.39 329.4 90.53"
     class="cls-1"
     style="fill:#da1f26"
     transform="translate(59.579252,-43.513817)" />
  <polyline
     id="polyline11"
     points="333.56 328.83 347.7 342.97 333.56 357.11"
     class="cls-2"
     style="fill:#252e43"
     transform="translate(59.579252,-43.513817)" />
  <path
     id="path35"
     d="m 394.84925,294.48618 -25,0 c -57.81,0 -77.28,-34.66 -96.1,-68.18 -15.35,-27.34 -29.86,-53.16 -63.9,-53.16 l -31.27,0 0,10 31.3,0 c 28.19,0 40.7,22.27 55.18,48.06 9.68,17.23 19.69,35.06 35.5,49.13 18.26,16.22 40.93,24.15 69.33,24.15 l 25,0 z"
     class="cls-2"
     inkscape:connector-curvature="0"
     style="fill:#252e43" />
  <path
     id="path43"
     d="m 390.97925,27.876183 -21.09,0 c -28.4,0 -51.07,7.9 -69.32,24.15 -15.81,14.08 -25.82,31.9 -35.5,49.129997 -14.48,25.79 -27,48.06 -55.18,48.06 l -31.31,0 0,10 31.3,0 c 34,0 48.54,-25.82 63.9,-53.16 18.8,-33.569997 38.3,-68.179997 96.11,-68.179997 l 21.09,0 z"
     class="cls-1"
     inkscape:connector-curvature="0"
     style="fill:#da1f26" />
  <path
     id="path45"
     d="m 429.38925,17.956183 a 14.92,14.92 0 1 0 14.92,14.92 14.92,14.92 0 0 0 -14.92,-14.92 z m 0,21 a 6.08,6.08 0 1 1 6.08,-6.08 6.08,6.08 0 0 1 -6.08,6.08 z"
     class="cls-1"
     inkscape:connector-curvature="0"
     style="fill:#da1f26" />
  <path
     id="path47"
     d="m 433.38925,284.53618 a 14.92,14.92 0 1 0 14.92,14.95 14.92,14.92 0 0 0 -14.92,-14.95 z m 0,21 a 6.08,6.08 0 1 1 6.09,-6.05 6.08,6.08 0 0 1 -6.09,6.05 z"
     class="cls-2"
     inkscape:connector-curvature="0"
     style="fill:#252e43" />
  <flowRoot
     style="font-style:normal;font-weight:normal;font-size:40px;line-height:125%;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
     id="flowRoot4236"
     xml:space="preserve"
     transform="translate(0,-72.53)"><flowRegion
       id="flowRegion4238"><rect
         y="179.54243"
         x="18.988897"
         height="58.373276"
         width="94.241196"
         id="rect4240" /></flowRegion><flowPara
       id="flowPara4242">ZakładaZ</flowPara></flowRoot>  <text
     x="27.791037"
     y="169.90349"
     font-size="20px"
     id="text49-1"
     style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:15px;line-height:125%;font-family:sans-serif;-inkscape-font-specification:'sans-serif, Bold';text-align:start;writing-mode:lr-tb;text-anchor:start;fill:#252e43;fill-opacity:1"
     sodipodi:linespacing="125%">
    <tspan
       sodipodi:role="line"
       id="tspan4528"
       x="27.791037"
       y="169.90349">PLEASE CHOOSE</tspan>
  </text>
</svg>


</div>

5 个答案:

答案 0 :(得分:6)

简短的回答是否定的。

如果文本位于带有viewBox的SVG中,并且SVG被缩放,则其内容也会缩放。没有办法使文本具有不受SVG缩放影响的“全局”大小。

唯一可行的解​​决方案是使用Javascript计算缩放因子,并在每次SVG大小更改时动态更新字体大小。

答案 1 :(得分:3)

我建议嵌套SVG标签。您可以将最外面的SVG保留为没有viewBox,并在此标签下添加所有文本,同时使用viewBox添加第二个SVG以覆盖整个区域。

您需要将文本的位置从绝对值更改为相对值,但是效果很好。

这样,您的文本将随svg大小而改变位置,但不会缩放文本。但是,由于您设置了viewBox,因此内部SVG将会出现。

示例:JS用于变量容器,SVG始终填充div。 缩放比例是纯SVG。

function changeCircleDiv(element) {
  s = document.getElementById("container").style;
  s.width=element.value + 'px';
  s.height = s.width;
}
body {
  font-size: 2em;
}
<input type="number" onchange="changeCircleDiv(this);" value="100"></input>
<div id="container" style="width: 100px; height: 100px;">
    <svg xmlns="http://www.w3.org/2000/svg" version="1.1" width="100%" height="100%">
        <svg width="100%" height="100%" viewBox="0 0 20 20">
            <circle cx="10" cy="10" r="8" stroke="black" fill="none"/>
        </svg>
      <text x="50%" y="50%" dominant-baseline="middle" text-anchor="middle">Center</svg>
    </svg>
</div>

答案 2 :(得分:2)

最后......

我已从svg中删除了文本,并在共享的html容器中添加了绝对定位的div文本块。这很有效。 Div的外观通过媒体查询控制css - 它独立于svg缩放。

您可以在以下位置查看图表:https://www.xtech.pl/jak-to-dziala-dla-dostawcy(向下滚动到页面上的第二部分,然后您可以调整屏幕大小以查看其工作原理)。

答案 3 :(得分:0)

您可以通过“带有粘性文本的自适应SVG”方式进行操作 看到这里:https://bl.ocks.org/veltman/5cd1ba0b3c623e7b5146

或者...如果您想对SVG中的字体使用媒体查询,答案是肯定的。运行此代码段。

<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100" width="100%" height="200px">
  <style>
    text {
      font-size: 10px;
    }

    @media (max-width: 600px) {
      text {
        font-size: 20px;
      }
    }

    @media (max-width: 800px) {
      text {
        font-size: 16px;
      }
    }

  </style>
  <circle cx="50" cy="50" r="50" fill="orange"/>
  <text x="50" y="60" text-anchor="middle">Testing</text>
</svg>

答案 4 :(得分:0)

我实际上找到了一个相对简单的解决方法。

使用D3的scaleSqrt(),您可以根据svg占用的像素宽度进行一些数学运算。

例如,如果svg视图框的宽度为800,则当svg的宽度为800px时,比例将为1。当svg的像素宽度为400px时,相对于视图框,则为比例的1/2

scaleRatio = d3.scaleSqrt()
    .domain([1600, 800, 600, 400, 200, 100])
    .range([0.5, 1, 1.5, 2, 4, 8]);
const svgWidth = d3.select(svg).node().getBoundingClientRect().width;
someD3Element.attr('transform', `scale(${scaleRatio(svgWidth)})`);