This is an edited copy of which I will remove, because it asked 2 related but technically different questions.
as I already explained in my last question, I'm trying to make a navigation-div with 4 buttons, one to go left, one to go right, another one to go down and yet another one to go up. Plus there needs to be an OK-button in the middle.
That worked really well with the explanation given here: Using CSS and HTML5 to create navigation buttons using trapezoids
I created the SVG like:
<div class="function height3x svg-container" style="height: 112px; width: 200px;">
<svg xmlns="" version="1.1" id="mySVG" width="100%" height="100%" viewBox="0 0 100 100" preserveAspectRatio="none" style="background-color: whitesmoke">
<g class="function" id="keyboard_btn_24">
<polygon id="ok" points="25,25 75,25 75,75 25,75"></polygon>
<text id="ok_text" x="39" y="55">OK</text>
</g>
<g class="function" id="keyboard_btn_25">
<polygon id="up" stroke="black" stroke-width="0.1" points="0,0 100,0 65,35 35,35"></polygon>
<text x="42" y="20"></text>
</g>
<g class="function" id="keyboard_btn_26">
<polygon id="right" stroke="black" stroke-width="0.1" points="100,0 100,100 65,65 65,35"></polygon>
<text x="81" y="53"></text>
</g>
<g class="function" id="keyboard_btn_27">
<polygon id="down" stroke="black" stroke-width="0.1" points="0,100 35,65 65,65 100,100"></polygon>
<text x="42" y="91"></text>
</g>
<g class="function" id="keyboard_btn_28">
<polygon id="left" stroke="black" stroke-width="0.1" points="0,0 35,35 35,65 0,100"></polygon>
<text x="5" y="53"></text>
</g>
</svg>
</div>
But I have two problems that I seem not to be able to figure out.
First of all: While I want the SVG to be responsive, I don't want to scale the text without keeping the aspect-ratio given by the font.
I already tried (unsuccessfully) preserveAspectRatio, which does not seem to do much to the text.
Questions: How can you make the tag keep it's aspect ratio, while changing the aspect ratio of the svg?
You can view and edit the minimal example: jsFiddle
Paulie_D - Commented on my old question:
As for the Aspect Ratio, you should remove the width & height 100% values. They aren't really needed. The SVG will scale to the required size based on the div size. - jsfiddle/2qqrL7ng/1 –
This is not an option, because the SVG Element needs to respond to size changes that can not keep the aspect ratio. Just the text needs to keep the ratio, everything else should be as responsive as possible.
EDIT
Switching the svg argument of perserveAspectRatio from "none" to "xMidYMid" keeps the aspect ratio of the SVG, but the desired effect is, that the SVG itself does not keep it's aspect ratio, but the -tags do. Which means the following would NOT be a solution:
<div class="function height3x svg-container" style="height: 112px; width: 200px;">
<svg xmlns="" version="1.1" id="mySVG" width="100%" height="100%" viewBox="0 0 100 100" preserveAspectRatio="xMidYMid" style="background-color: whitesmoke">
<g class="function" id="keyboard_btn_24">
<polygon id="ok" points="25,25 75,25 75,75 25,75"></polygon>
<text id="ok_text" x="39" y="55">OK</text>
</g>
<g class="function" id="keyboard_btn_25" preserveAspectRatio="xMidYMid">
<polygon id="up" stroke="black" stroke-width="0.1" points="0,0 100,0 65,35 35,35"></polygon>
<text x="42" y="20"></text>
</g>
<g class="function" id="keyboard_btn_26">
<polygon id="right" stroke="black" stroke-width="0.1" points="100,0 100,100 65,65 65,35"></polygon>
<text x="81" y="53"></text>
</g>
<g class="function" id="keyboard_btn_27">
<polygon id="down" stroke="black" stroke-width="0.1" points="0,100 35,65 65,65 100,100"></polygon>
<text x="42" y="91"></text>
</g>
<g class="function" id="keyboard_btn_28">
<polygon id="left" stroke="black" stroke-width="0.1" points="0,0 35,35 35,65 0,100"></polygon>
<text x="5" y="53"></text>
</g>
</svg>
</div>
/EDIT
Thanks in advance.
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 2 related but technically different questions.
as I already explained in my last question, I'm trying to make a navigation-div with 4 buttons, one to go left, one to go right, another one to go down and yet another one to go up. Plus there needs to be an OK-button in the middle.
That worked really well with the explanation given here: Using CSS and HTML5 to create navigation buttons using trapezoids
I created the SVG like:
<div class="function height3x svg-container" style="height: 112px; width: 200px;">
<svg xmlns="http://www.w3.org/2000/svg" version="1.1" id="mySVG" width="100%" height="100%" viewBox="0 0 100 100" preserveAspectRatio="none" style="background-color: whitesmoke">
<g class="function" id="keyboard_btn_24">
<polygon id="ok" points="25,25 75,25 75,75 25,75"></polygon>
<text id="ok_text" x="39" y="55">OK</text>
</g>
<g class="function" id="keyboard_btn_25">
<polygon id="up" stroke="black" stroke-width="0.1" points="0,0 100,0 65,35 35,35"></polygon>
<text x="42" y="20"></text>
</g>
<g class="function" id="keyboard_btn_26">
<polygon id="right" stroke="black" stroke-width="0.1" points="100,0 100,100 65,65 65,35"></polygon>
<text x="81" y="53"></text>
</g>
<g class="function" id="keyboard_btn_27">
<polygon id="down" stroke="black" stroke-width="0.1" points="0,100 35,65 65,65 100,100"></polygon>
<text x="42" y="91"></text>
</g>
<g class="function" id="keyboard_btn_28">
<polygon id="left" stroke="black" stroke-width="0.1" points="0,0 35,35 35,65 0,100"></polygon>
<text x="5" y="53"></text>
</g>
</svg>
</div>
But I have two problems that I seem not to be able to figure out.
First of all: While I want the SVG to be responsive, I don't want to scale the text without keeping the aspect-ratio given by the font.
I already tried (unsuccessfully) preserveAspectRatio, which does not seem to do much to the text.
Questions: How can you make the tag keep it's aspect ratio, while changing the aspect ratio of the svg?
You can view and edit the minimal example: jsFiddle
Paulie_D - Commented on my old question:
As for the Aspect Ratio, you should remove the width & height 100% values. They aren't really needed. The SVG will scale to the required size based on the div size. - jsfiddle.net/2qqrL7ng/1 –
This is not an option, because the SVG Element needs to respond to size changes that can not keep the aspect ratio. Just the text needs to keep the ratio, everything else should be as responsive as possible.
EDIT
Switching the svg argument of perserveAspectRatio from "none" to "xMidYMid" keeps the aspect ratio of the SVG, but the desired effect is, that the SVG itself does not keep it's aspect ratio, but the -tags do. Which means the following would NOT be a solution:
<div class="function height3x svg-container" style="height: 112px; width: 200px;">
<svg xmlns="http://www.w3.org/2000/svg" version="1.1" id="mySVG" width="100%" height="100%" viewBox="0 0 100 100" preserveAspectRatio="xMidYMid" style="background-color: whitesmoke">
<g class="function" id="keyboard_btn_24">
<polygon id="ok" points="25,25 75,25 75,75 25,75"></polygon>
<text id="ok_text" x="39" y="55">OK</text>
</g>
<g class="function" id="keyboard_btn_25" preserveAspectRatio="xMidYMid">
<polygon id="up" stroke="black" stroke-width="0.1" points="0,0 100,0 65,35 35,35"></polygon>
<text x="42" y="20"></text>
</g>
<g class="function" id="keyboard_btn_26">
<polygon id="right" stroke="black" stroke-width="0.1" points="100,0 100,100 65,65 65,35"></polygon>
<text x="81" y="53"></text>
</g>
<g class="function" id="keyboard_btn_27">
<polygon id="down" stroke="black" stroke-width="0.1" points="0,100 35,65 65,65 100,100"></polygon>
<text x="42" y="91"></text>
</g>
<g class="function" id="keyboard_btn_28">
<polygon id="left" stroke="black" stroke-width="0.1" points="0,0 35,35 35,65 0,100"></polygon>
<text x="5" y="53"></text>
</g>
</svg>
</div>
/EDIT
Thanks in advance.
Share Improve this question edited May 23, 2017 at 12:18 CommunityBot 11 silver badge asked Mar 18, 2015 at 8:36 Sebastian van WickernSebastian van Wickern 1,7493 gold badges15 silver badges33 bronze badges 8 | Show 3 more comments3 Answers
Reset to default 13I 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>
apart 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!
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.
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 */
<g>
element. The only way you're going to be able to do what you want is to calculate the aspect ratio yourself in javascript and apply an inverse transform to the text elements. – Robert Longson Commented Mar 18, 2015 at 10:08<div>
one with the text which is preserveAspectRatio="xMidYMid" and one with the rest of it which isn't. – Robert Longson Commented Mar 18, 2015 at 10:10