IOS 7 - css - html height - 100% = 692px

2019-01-13 01:09发布

问题:

I have a weird bug on iPad iOS7 landscape mode.

What i was able to investigate is that in iOS7 window.outerHeight is 692px and window.innerHeight 672px; while in previous versions both values are 672px.

Even though my <html> and <body> tags have height 100% there seems to be space for scrolling, and the weird thing is that this problem only shows up on landscpae

You can see what i am talking about by visiting t.cincodias.com, for example, in a iOS 7 iPad the footer bar (or the header sometimes) will be cut. But on previous iOS versions the content displays fine at fullscreen.

Even when i set the height of both tags to height: 672px !important and position:absolute; bottom: 0;, you can still scroll the content vertically by touching an iframe (the ads are iframes).

I'm running the release candidate version of iOS7

thanks for any help.

回答1:

I believe this is a bug in iOS 7 - if you rotate it to portrait mode, it sets both (innerHeight/outerHeight) to the same value. If it isn't a bug, then portrait mode has one because the behavior isn't consistent.

You could detect iOS 7/mobile Safari and use window.innerHeight if iOS 7.



回答2:

I used this JavaScript solution for solving that problem:

if (
    navigator.userAgent.match(/iPad;.*CPU.*OS 7_\d/i) && 
    window.innerHeight != document.documentElement.clientHeight
) {
    var fixViewportHeight = function() {
        document.documentElement.style.height = window.innerHeight + "px";
        if (document.body.scrollTop !== 0) {
            window.scrollTo(0, 0);
        }
    };

    window.addEventListener("scroll", fixViewportHeight, false);
    window.addEventListener("orientationchange", fixViewportHeight, false);
    fixViewportHeight();

    document.body.style.webkitTransform = "translate3d(0,0,0)";
}


回答3:

I'll combine the answers. Thanks all!

You can do something like this:

if (navigator.userAgent.match(/iPad;.*CPU.*OS 7_\d/i)) {
    $('#yourDivID').height(window.innerHeight);
    window.scrollTo(0, 0);
}

The window.scrollTo solves the issue of the bar overlapping in landscape when rotating.

Cheers!



回答4:

I reproduce the same problem in iOS 8.

Here is my solution.

I listened resize, scroll, orientationChange event, to ensure when user trigger screen size change, will call reset height function.

I wrote a debounce to prevent multiple call.

And It's in a closure and no dependent (no jQuery).

(function(){
  var setViewportHeight = (function(){
    function debounced(){
      document.documentElement.style.height = window.innerHeight + "px";
      if (document.body.scrollTop !== 0) {
          window.scrollTo(0, 0);
      }
    }
    var cancelable = null;

    return function(){
      cancelable && clearTimeout(cancelable);
      cancelable = setTimeout(debounced, 100);
    };
  })();

  //ipad safari
  if(/iPad/.test(navigator.platform) && /Safari/i.test(navigator.userAgent)){  
    window.addEventListener("resize", setViewportHeight, false);
    window.addEventListener("scroll", setViewportHeight, false);
    window.addEventListener("orientationchange", setViewportHeight, false);
    setViewportHeight();
  }
})();