iOS 7 iPad Safari Landscape内部高度/外部高度布局问题


72

我们发现在iOS 7中的Safari上高度为100%的Web应用程序出现问题。看来window.innerHeight(672px)与window.outerHeight(692px)不匹配,但仅在横向模式下有效。最终发生的事情是,在高度为100%的应用程序中,您将获得20px的额外空间。这意味着,当用户在我们的应用程序上向上滑动时,导航元素将被拉到浏览器镶边之后。这也意味着,位于屏幕底部的所有绝对定位的元素最终都会偏离20px。

此问题也在此处概述: IOS 7-CSS-HTML高度-100%= 692px

可以在这个模糊的屏幕截图中看到: iOS 7 Safari externalHeight问题

我们正在尝试解决此问题,以便在Apple修复该错误之前,我们不必担心它。

一种方法是仅在iOS 7中绝对定位主体,但这几乎将多余的20px放置在页面顶部而不是底部:

body {
    position: absolute;
    bottom: 0;
    height: 672px !important;
}

我们将非常感谢您提供的有关强制externalHeight匹配innerHeight或对其进行破解以使我们的用户无法看到此问题的帮助。


2
有关更多详细信息,请参见以下URL:krpano.com/ios/bugs/ios7-ipad-landscape
Vikash Pandey

1
附带说明:此错误似乎已在iOS8上修复。解决方法仅应针对iOS7。
帕特里克·鲁道夫2014年

Answers:


60

就我而言,解决方案是将定位更改为固定:

@media (orientation:landscape) {
    html.ipad.ios7 > body {
        position: fixed;
        bottom: 0;
        width:100%;
        height: 672px !important;
    }
}

我还使用脚本在iOS 7中检测iPad:

if (navigator.userAgent.match(/iPad;.*CPU.*OS 7_\d/i)) {
    $('html').addClass('ipad ios7');
}

5
我将其与window.scrollTo(0,0);更改方向结合起来,看来已经解决了我们99%的问题。给我几天在生产中使用它的时间,我想我们可能会有答案。
hisnameisjimmy

我只是发现一个使用iPad mini OS 7的朋友没有这个问题,想知道是否是iPad mini?
2014年

1
我有一台配备视网膜的iPad mini,也遇到了同样的问题
chrishawn

哇...我不敢相信我花了这么长时间才找到这个。我整夜都在搜索奇怪的javascript hack,但是几乎没有用。这真太了不起了。
Christopher Reid

OMG在ipad sim上浪费了大约两天时间,以为我的立场是:绝对的;在造成这个。谢谢!
克里斯·古纳瓦德纳

16

简单,简洁的仅CSS解决方案:

html {
     height: 100%;
     position: fixed;
     width: 100%;
   }

iOS 7似乎可以正确设置高度。同样,也不需要调整javascript事件的大小等。由于您使用的是全高度应用程序,因此始终保持位置固定并不重要。


奇怪的是,这可以在带有Retina的普通iPad上使用,但不能在iPad Mini上使用。672px修复程序似乎对两者均有效。
jscharf 2014年

14

特里·索尔森(Terry Thorsen)也指出,塞缪尔(Samuel)的回答效果很好,但如果该网页已添加到iOS主目录中,则答案会失败。

一个更直观的解决方法是检查window.navigator.standalonevar。

if (navigator.userAgent.match(/iPad;.*CPU.*OS 7_\d/i) && !window.navigator.standalone) {
    $('html').addClass('ipad ios7');
}

这样,它仅在Safari内部打开时才适用,而不是在家中启动时才适用。


另一个不起作用的情况是显示收藏夹栏时。因此,有了这个答案,我的吼叫声-涵盖了所有问题(据我所知!)
Nick H247

2

塞缪尔(Samuel)的回答是最好的,尽管如果用户将页面添加到主屏幕(主屏幕页面未显示错误),该回答就会中断。像这样添加类之前检查innerHeight:

if (navigator.userAgent.match(/iPad;.*CPU.*OS 7_\d/i)) {
    if(window.innerHeight==672){
        $('html').addClass('ipad ios7');
    }
}

请注意,该错误也不会在webview下显示。


2
我的iPad报告window.innerHeight为671(带有console.log),因此672并不总是准确的。
Esger 2014年

2

我使用此JavaScript解决方案来解决该问题:

    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);
    }
  }.bind(this);

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

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

1

塞缪尔(Samuel)方法的一种变体,但具有以下位置:在html上设置-webkit-sticky对我来说效果最好。

@media (orientation:landscape) {
    html.ipad.ios7 {
        position: -webkit-sticky;
        top: 0;
        width: 100%;
        height: 672px !important;
    }
}

注意“ top:0”,而不是“ bottom:0”,目标元素是“ html”,而不是“ body”


0

基本上有两个错误-横向模式下窗口的高度和用户从纵向模式重新写入窗口时的滚动位置。我们已经通过以下方式解决了它:

窗口的高度由以下方式控制:

// window.innerHeight is not supported by IE
var winH = window.innerHeight ? window.innerHeight : $(window).height();

// set the hight of you app
$('#yourAppID').css('height', winH);

// scroll to top
window.scrollTo(0,0);

现在,可以将以上内容放入函数中并绑定到窗口调整大小和/或方向更改事件。就这样...参见示例:

http://www.ajax-zoom.com/examples/example22.php


您实际上并没有解决问题,因为页面底部有一个奇怪的空白(请看此处),用户仍然可以滚动页面。
agudulin

0

您需要JavaScript来解决此错误。window.innerHeight具有正确的高度。这是我能想到的最简单的解决方案:

$(function() {
    function fixHeightOnIOS7() {
        var fixedHeight = Math.min(
            $(window).height(), // This is smaller on Desktop
            window.innerHeight || Infinity // This is smaller on iOS7
        );
        $('body').height(fixedHeight);
    }

    $(window).on('resize orientationchange', fixHeightOnIOS7);
    fixHeightOnIOS7();
});

您还需要在position: fixed上进行设置<body>

这是一个完整的工作示例:

<!DOCTYPE html>
<html>
    <head>
        <meta charset="UTF-8"/>
        <meta name="viewport" content="width=device-width, initial-scale=1"/>
        <meta name="apple-mobile-web-app-capable" content="yes"/>
        <title>iOS7 height bug fix</title>
        <script src="http://code.jquery.com/jquery-1.10.1.min.js"></script>
        <script>
            $(function() {
                function fixHeightOnIOS7() {
                    var fixedHeight = Math.min(
                        $(window).height(),
                        window.innerHeight || Infinity
                    );
                    $('body').height(fixedHeight);
                }

                $(window).on('resize orientationchange', fixHeightOnIOS7);
                fixHeightOnIOS7();

                // Generate content
                var contentHTML = $('#content').html();
                for (var i = 0; i < 8; i++) contentHTML += contentHTML;
                $('#content').html(contentHTML);
            });
        </script>
        <style>
            html,
            body
            {
                margin: 0;
                padding: 0;
                height: 100%;
                width: 100%;
                overflow: auto;
                position: fixed;
            }
            #page-wrapper
            {
                height: 100%;
                position: relative;
                background: #aaa;
            }
            #header,
            #footer
            {
                position: absolute;
                width: 100%;
                height: 30px;
                background-color: #666;
                color: #fff;
            }
            #footer
            {
                bottom: 0;
            }
            #content
            {
                position: absolute;
                width: 100%;
                top: 30px;
                bottom: 30px;
                overflow: auto;
                -webkit-overflow-scrolling: touch;
            }
        </style>
    </head>
    <body>
        <div id="page-wrapper">
            <div id="header">Header</div>
            <div id="content">
                <p>Lorem ipsum dolor sit amet.</p>
            </div>
            <div id="footer">Footer</div>
        </div>
    </body>
</html>

0

关于公认的答案,我还很幸运遵守以下规则:

html.ipad.ios7 {
    position: fixed;
    width: 100%;
    height: 100%;
}

这具有附加的优点,因为它似乎停止了html元素在固定的body元素“下方”滚动。


0

如果我使用这个:

if (navigator.userAgent.match(/iPad;.*CPU.*OS 7_\d/i) && !window.navigator.standalone) {
    $('html').addClass('ipad ios7');
}

我在Mac上的Safari显示了相同的html类...因此无法正常工作。

我试图结合一些对我有用的东西,因此我可以在浏览器中进行管理,而无需浏览器视图。

jQuery的

if (navigator.userAgent.match(/iPad/i) && (window.orientation) ){
     $('html').addClass('ipad ');
        if (window.innerHeight !=  window.outerHeight ){
          $('html').addClass('browser  landscape');              
    }
    else{
         $('html').addClass('browser portrait');                   
    }
} 

的CSS

@media (orientation:landscape) {
   html.ipad.browser > body {
       position: fixed;  
       height: 671px !important;
   }
}

/////有了这个,您可以更灵活地使用其他操作系统和浏览器


0

我遇到了同一问题的本页。这里有很多有用的答案,而其他答案不是(对我来说)。

但是,我找到了一种解决方案,该解决方案适用于我自己的情况,并且完全独立于当前或过去或将来的操作系统版本和错误。

说明:开发具有全尺寸固定大小的几个模块的Web应用程序(无本机应用程序),类名为“模块”

.module {position:absolute; top:0; right:0; bottom:0; left:0;}

其中包含一个类名为“ footer”的页脚

.module > .footer {position:absolute; right:0; bottom:0; left:0; height:90px;}

没关系,如果以后将页脚的高度设置为另一个高度,或者甚至通过其内容来设置其高度,也可以使用以下代码进行更正:

function res_mod(){
    $('.module').css('bottom', 0); // <-- need to be reset before calculation
    var h = $('.module > .footer').height();
    var w = window.innerHeight;
    var o = $('.module > .footer').offset();
    var d = Math.floor(( w - o.top - h )*( -1 ));
    $('.module').css('bottom',d+'px'); // <--- this makes the correction
}

$(window).on('resize orientationchange', res_mod);

$(document).ready(function(){
    res_mod();
});

多亏了Matteo Spinelli的技能,我仍然可以毫无问题地使用iScroll,因为幸运的是它的更改事件被触发。如果不是,则必须在更正后再次调用iScroll-init。

希望这对某人有帮助


0

显示收藏夹栏时,无法接受接受的答案。这是改进的捕获所有修复程序:

@media (orientation:landscape) {
  html.ipad.ios7 > body {
    position: fixed;
    height: calc(100vh - 20px);
    width:100%;
  }
}

-1

如果你尝试怎么办

html{ bottom: 0;padding:0;margin:0}body {
position: absolute;
bottom: 0;
height: 672px !important;
}
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.