I am developing a PhoneGap/Cordova app that should run on iOS and Android devices, and uses SVG images embedded as <img/>
tags, using HTML attributes width=""
and height=""
to set their dimensions, and style="left: ...px; top: ...px; zoom: ...;"
to set their relative position, with a zoom coefficient that is uniform between multiple image objects.
My problem is that when zooming in and out, the images are rendered with different sizes, both in Safari and in Chrome. This can also be seen in the desktop versions of these browsers, and I think I can narrow it down to a rounding issue with respect to the left
and top
CSS property. The problem is aggravated when using fractional values for the zoom
CSS property, and the width
and height
HTML attributes.
I have created a demo here and a downloadable version here. In this demo, I have used two SVG images, identical except for their fill color, which I use for color contrast. There are three pairs in the demo: the top-most uses a fractional zoom
value, the middle uses fractional width
and height
values, and the last uses round multiples of the width
and height
values. There is a button that starts an animations that simply moves all images to the right, by a single pixel in each step. It'll be easy to notice in Chrome that the middle images jiggle substantially, while a little harder to notice changes in the other two - but they are also there. I'm using Windows 10 and Chrome 65.0 -- though I can see variations of the problem in Firefox and Edge as well (though -- they are rendered differently).
Here is an animation of the demo. Note that all I am changing between frames is the left
position of all images - and doing so in a uniform manner.
For my application, the images must have consistent rendering across zoom
levels and in different positions on the page. When changing the zoom
, left
and top
properties smoothly, the images should change dimensions and position smoothly, respectfully. They should not change dimensions when changing the left
and top
properties. Is there a method that ensures that when multiple images use the same (possibly fractional) width
and height
values, but varying left
and top
positions, they will be rendered identically? Is there a way to ensure that smooth transition of the zoom
property results in smooth rendering?
A proper answer would either explain why this is not possible using current browsers, pointing to a confirmed bug report that describes this problem and shows that it affects popular devices in either platform; or present an alternative way to size and position the images, while retaining the possibility to use fractional values, and that obtains uniformity and smooth zoom transitions when all images use the same dimensions.
Thanks for any help you may offer!
I think it's because the zoom
property support is not quite consistent between the browsers (as you can see here https://caniuse.com/#feat=css-zoom). Try rather the transform: scale()
property:
function budgeRight() {
var imgs = document.querySelectorAll('img');
imgs = Array.prototype.slice.apply(imgs);
imgs.forEach(function(img) {
var left = parseInt(img.style.left);
img.style.left = (left + 1).toString() + "px";
});
}
var interval = null;
var button = document.getElementById('button-click-me');
button.addEventListener('click', function() {
if (interval) {
clearInterval(interval);
interval = null;
}
else {
interval = setInterval(budgeRight, 500);
}
});
img { position: absolute; }
body { background-color: #000; }
<img style="-webkit-transform: scale(2.3); -moz-transform: scale(2.3); -ms-transform: scale(2.3); -o-transform: scale(2.3); transform: scale(2.3); -webkit-transform-origin: top left; -moz-transform-origin: top left; -ms-transform-origin: top left; -o-transform-origin: top left; transform-origin: top left; left: 41px; top: 25px;" src="https://gist.githubusercontent.com/kwikwag/74b991206c5fd197c70a6ec2c02fd238/raw/3f4070dbb97c69f716ad6b32ca5f6abd1f4fd702/rect_white.svg?sanitize=true">
<img style="-webkit-transform: scale(2.3); -moz-transform: scale(2.3); -ms-transform: scale(2.3); -o-transform: scale(2.3); transform: scale(2.3); -webkit-transform-origin: top left; -moz-transform-origin: top left; -ms-transform-origin: top left; -o-transform-origin: top left; transform-origin: top left; left: 40px; top: 25px;" src="https://gist.githubusercontent.com/kwikwag/74b991206c5fd197c70a6ec2c02fd238/raw/3f4070dbb97c69f716ad6b32ca5f6abd1f4fd702/rect_red.svg?sanitize=true">
<img style="-webkit-transform: scale(2.3); -moz-transform: scale(2.3); -ms-transform: scale(2.3); -o-transform: scale(2.3); transform: scale(2.3); -webkit-transform-origin: top left; -moz-transform-origin: top left; -ms-transform-origin: top left; -o-transform-origin: top left; transform-origin: top left; left: 31px; top: 35px;" width="9.35" height="23.35" src="https://gist.githubusercontent.com/kwikwag/74b991206c5fd197c70a6ec2c02fd238/raw/3f4070dbb97c69f716ad6b32ca5f6abd1f4fd702/rect_red.svg?sanitize=true">
<img style="-webkit-transform: scale(2.3); -moz-transform: scale(2.3); -ms-transform: scale(2.3); -o-transform: scale(2.3); transform: scale(2.3); -webkit-transform-origin: top left; -moz-transform-origin: top left; -ms-transform-origin: top left; -o-transform-origin: top left; transform-origin: top left; left: 32px; top: 35px;" width="9.35" height="23.35" src="https://gist.githubusercontent.com/kwikwag/74b991206c5fd197c70a6ec2c02fd238/raw/3f4070dbb97c69f716ad6b32ca5f6abd1f4fd702/rect_white.svg?sanitize=true">
<img style="left: 91px; top: 130px;" width="18" height="42" src="https://gist.githubusercontent.com/kwikwag/74b991206c5fd197c70a6ec2c02fd238/raw/3f4070dbb97c69f716ad6b32ca5f6abd1f4fd702/rect_red.svg?sanitize=true">
<img style="left: 94px; top: 130px;" width="18" height="42" src="https://gist.githubusercontent.com/kwikwag/74b991206c5fd197c70a6ec2c02fd238/raw/3f4070dbb97c69f716ad6b32ca5f6abd1f4fd702/rect_white.svg?sanitize=true">
<button id="button-click-me">Click me</button>
Notice I added transform-origin: top left
, to scale each image from its top left corner.
And I also used all the vendor-prefixes -webkit-
, -moz-
, etc. to have a maximum compatibility on these 2 properties...
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With