I have a HTML webpage with SVG image. I get a problem (excess white line, shown on the picture below) on the webpage when I visit it using iOS Safari or Android Browser. The screenshot resolution is 2x, the saw edge is a SVG image.
I've found out that it happens when the page Y-position of the SVG image is not an integer amount of CSS pixels (px
), i.e. with ½px
. The browser rounds the SVG image position to integer px
when it renders the webpage while doesn't round the other elements positions. That's why the ½px
line appears.
You can reproduce the problem using the snippet below (or this CodePen). You should run the snippet on a device with a high pixel density. You can also reproduce it in desktop Safari if you go to the responsive design mode and pick iPhone or iPad.
.common-bg {
background: #222;
fill: #222;
}
.block {
max-width: 300px;
margin: 20px auto;
}
.block_content {
height: 50.5px;
}
.block_edge {
display: block;
}
<div class="block">
<div class="block_content common-bg"></div>
<svg
class="block_edge"
width="100%"
height="10"
xmlns="http://www.w3.org/2000/svg"
version="1.1"
xmlns:xlink="http://www.w3.org/1999/xlink"
>
<defs>
<pattern id="sawPattern" x="50%" width="20" height="10" patternUnits="userSpaceOnUse">
<path d="M 0 0 L 10 10 L 20 0 Z" class="common-bg"/>
</pattern>
</defs>
<rect x="0" y="0" width="100%" height="10" fill="url(#sawPattern)"/>
</svg>
</div>
How to prevent ½px
SVG shift on iOS Safari and Android Browser? Is it a bug and I should report it to WebKit developers? Maybe there is a way to make browsers round to px
the other elements on the page?
I can solve this problem without preventing ½px
shift:
- Remove non-integer height of
.block_content
- Make such layout in which half-pixel shift doesn't lead to while line
But I wonder is there a way to prevent ½px
shift because the solutions above are not always possible.
preserveAspectRatio="xMidYMin"
or similar on the svg element? – Caldeira::after
css rule – CaldeirapreserveAspectRatio
doesn't change anything – Hisakohisbe