Skip to content Skip to sidebar Skip to footer

Preserve Aspect Ratio For Svg Text

This is an edited copy of https://stackoverflow.com/questions/29105120/preserve-aspect-ratio-for-svg-text-and-react-to-javascript-touch-events which I will remove, because it asked

Solution 1:

I know this is an old question but I did find a way to do what is asked in pure SVG, no JS, and I've used it in prod without issues!

The trick is to define a parent <svg> element without a viewBox so that it takes the container's dimensions, and then define children <svg> elements for the different kind of preserveAspectRatio values that you want!

In the following snippet, I just took the SVG used in the question and put all the <polygon> appart in a <svg viewBox="0 0 100 100" preserveAspectRatio="none">.

div {
  height: 112px;
  width: 200px;
}

div > svg {
  height: 100%;
  width: 100%;
  background-color: whitesmoke;
}

polygon {
  fill: none;
  stroke: black;
  stroke-width: 0.1;
}
<div>
  
  <!-- SVG wrapper without viewBox to take parent's dimensions -->
  <svg>
  
    <!-- sub SVG that will be resized -->
    <svg viewBox="0 0 100 100" preserveAspectRatio="none">
      <g>
        <polygon points="0,0 100,0 65,35 35,35"></polygon>
        <text x="42" y="20"></text>
      </g>
      <g>
        <polygon points="100,0 100,100 65,65 65,35"></polygon>
        <text x="81" y="53"></text>
      </g>
      <g>
        <polygon points="0,100 35,65 65,65 100,100"></polygon>
        <text x="42" y="91"></text>
      </g>
      <g>
        <polygon points="0,0 35,35 35,65 0,100"></polygon>
        <text x="5" y="53"></text>
      </g>
    </svg>
    
    <!-- regular SVG elements that won't be resized -->
    <text id="ok_text" 
          x="50%" y="50%" 
          text-anchor="middle" 
          alignment-baseline="middle">
      OK
    </text>
    
  </svg>
</div>

PS: the end result can even be used as the src of a regular image <img src="./my-weird-responsive-svg.svg" /> which makes this trick really robust!


Solution 2:

Questions: How can you make the tag keep it's aspect ratio, while changing the aspect ratio of the svg?

You cannot. If the text is part of the SVG it gets scaled with the SVG. There is no way to make a part of the SVG exempt from the scaling.

Possible solutions:

(1) Remove the text from the SVG and position it on top. For example use a positioned <div> in your HTML or something.

(2) Use JS to calculate the aspect ratio of the SVG and apply an inverse scaling transform to the <text> element.


Solution 3:

If you have javascript control on the current dimensions (like going fullscreen, for instance, or simply by checking what viewport size the user is using), you can add a simple class in a parent div outside the SVG.

Then, style the SVG text's font-size for both cases: when the parent div has such class (it tells you that your svg has scaled), and when the parent div hasn't such a class (i.e., the SVG is non-scaled). If this is your case, this simple solution works.

.svg_text {font-size: 12px;} /* normal non-scaled SVG */
.case_for_big_screen_thus_SVG_scaled .svg_text {font-size: 6px;} /* this parent class only is added when viewport dimensions make your SVG to be scaled */

Post a Comment for "Preserve Aspect Ratio For Svg Text"