CSS “position:fixed”: mobile zoom

I'm trying to solve an issue with css "position:fixed" property on mobile browsers. I have a fixed div:

<div id="logo">
...other content here...
</div>

with css:

#logo{
    position: fixed;
    -webkit-backface-visibility: hidden;
    bottom: 100px;
    right: 0px;
    width: 32px;
    height: 32px;
}

So, usually the behaviour is exactly the desired one, with the div position always on the bottom right of the window, indipendently of the scroll position. My issue is that on mobile browsers, when the users zoom the page, after a certain zoom level the div position is wrong (sometimes the div disappear out of the window).

I know that fixed position is not well supported on mobile browsers, but I wonder if there is some workaround. I tried with this js code onScroll event:

window.addEventListener('scroll', function(e){
    drag.style['-webkit-transform'] = 'scale(' +window.innerWidth/document.documentElement.clientWidth + ')';\I want to avoid zoom on this element
    var r = logo.getBoundingClientRect();
    var w = window.innerWidth;
    var h = window.innerHeight;
    if(r.right != w){
        rOff = r.right - w;
        logo.style.right = rOff;
    }
    if(r.top+132 != h){
        tOff = r.top + 132 - h;
        logo.style.bottom = tOff;
    }
});

Unfortunately, the code seems to return the wrong position.

Does anyone have any tip?

Asked By: user3098549
||

Answer #1:

Ok, that's how I solved the issue...I hope that could help anyone to simulate fixed position on iOS devices.

  1. I switched the position from fixed to absolute;
  2. Attach to window a listener to get the new position when the page is scrolled or zoomed, setting window.onscroll and window.onresize events with the following function:
function position() {
    drag.style.left = window.innerWidth + window.pageXOffset - 32 + 'px';
    drag.style.top = window.innerHeight + window.pageYOffset - 132 + 'px';
}
Answered By: user3098549

Answer #2:

Do you want to catch if zoom is active?

There's no window.onZoom listener, but you can read this thread: Catch browser's "zoom" event in JavaScript

and this answer: https://stackoverflow.com/a/995967/3616853

There's no way to actively detect if there's a zoom. I found a good entry here on how you can attempt to implement it. I’ve found two ways of detecting the zoom level. One way to detect zoom level changes relies on the fact that percentage values are not zoomed. A percentage value is relative to the viewport width, and thus unaffected by page zoom. If you insert two elements, one with a position in percentages, and one with the same position in pixels, they’ll move apart when the page is zoomed. Find the ratio between the positions of both elements and you’ve got the zoom level. See test case. http://web.archive.org/web/20080723161031/http://novemberborn.net/javascript/page-zoom-ff3 You could also do it using the tools of the above post. The problem is you're more or less making educated guesses on whether or not the page has zoomed. This will work better in some browsers than other. There's no way to tell if the page is zoomed if they load your page while zoomed.

Answered By: grubino

Answer #3:

Just a theory, but you may want to try setting the bottom/right positions in % rather than px.

I think what you're seeing when using pixel measurements is just the zoom effecting the pixels. Or to put it better, when you zoom-in the pixels appear larger and that throws off the position of the element, even pushing it out of the view-port on smaller screens.

Example using pixel positioning
Notice that even on a desktop as you zoom-in and out the element appears to move up and down?

Example using percent positioning
In this example the element appears to stay in the bottom right corner, because it is always positioned at 10% from the bottom of the view-port.

#logo{
    position: fixed;
    -webkit-backface-visibility: hidden;
    bottom:10%;
    right: 0; 
    width: 32px;
    height: 32px;
}
Answered By: apaul

Answer #4:

Having two different z-index for the logo and the rest of the page could help. Allowing zooming only to the rest of the page and not to the z-index layer where logo is included. So, this might not affect the stretching on the logo.

We can

  1. Implement a ZOOM listener
  2. Attach it to browser
  3. Make the zoom listener change the zoom level of the element (modify the elements position) using z-index as a factor.
Answered By: Satt
The answers/resolutions are collected from stackoverflow, are licensed under cc by-sa 2.5 , cc by-sa 3.0 and cc by-sa 4.0 .



# More Articles