页面在Chrome,Firefox和IE中运行良好,但会导致iPad Safari闪烁或崩溃

时间:2012-08-16 19:17:46

标签: javascript jquery html ipad mobile-safari

我正在尝试使用jQuery和CSS3创建内容滑块。

This是我的代码。 Page在Chrome中工作得很好,在Firefox中几乎没问题,它在IE中很有用(但几乎没有效果)。

但它在iPad Safari中无效...

当页面在iPad Safari中完成加载时,Page开始闪烁(连续,永不完成),然后浏览器崩溃!

但是我找不到my slider的哪个部分有问题,我不知道究竟是什么问题......

很抱歉,如果我的代码很乱,但我找不到问题所在,所以我不能做一个更简单的例子......


更新

我的代码有window.resize jQuery事件,我在其中调用CorrectPages()

我已将此代码放在该事件的第一行:alert("windowResize" + window.innerWidth + " , " + window.innerHeight);

在PC中,在我调整窗口大小之前没有警报。但在iPad中,警报在页面加载后开始。这些是iPad上的消息:

windowResize1767 , 1074
windowResise1767 , 2078
windowResize2099 , 4136
windowResize2099 , 8355
windowResize2099 , 17004
windowResize2099 , 34735
...

更新2

正如ahmadali所说,现在我们解决了以前的问题。 This is my fixed code。但现在,还有另一个问题:当页面加载时,Safari会说错window.innerWidthwindow.innerHeight

当页面加载时,它看起来是正确的,但随后,它会发生变化。这是片刻之后的结果: enter image description here

你的想法是什么?

2 个答案:

答案 0 :(得分:3)

马赫迪

我无法发现任何明显的事情,但效率可能是一个问题。可以进行大量改进。

以下是一些通用指示:

  • 将全局beginXbeginY等放入$(document).ready(function(){...})封闭内。
  • 尽量减少查找DOM节点的需求 - 缓存jQuery对象并尽可能使用方法链接。
  • .removeclass()将删除多个空格分隔的类。无需单独陈述
  • $("#d_page" + i + " #overlay")令人担忧。 ID应该是唯一的,为什么不$("#overlay")$(".... .overlay")
  • 让jQuery方法.eq().not()做一些艰苦的工作。
  • 给页面class =“page”。设$pages = $(".page"),然后$("#d_page" + i.toString())应简化为$pages.eq(i)。这种类型的许多表达式都会简化。

通过逐步改进,我设法将函数correctPages()从大约170多行减少到只有26行。

这就是我最终的结果:

function correctPages() {
    var $pages = $(".page"),//relies on pages having class="page"
        prefix = (isLandscape(window.innerWidth, window.innerHeight)) ? 'd_landscape_activepage_' : 'd_portrait_activepage_',
        classes = ["whitebackground", prefix+"1", prefix+"2", prefix+"3", prefix+"4"].join(' '),
        $np = [$pages.eq(currentPage), $pages.eq(nextPage(currentPage)), $pages.eq(nextPage(nextPage(currentPage))), $pages.eq(nextPage(nextPage(nextPage(currentPage))))];
    $pages.removeClass(classes);
    $pages.find(".overlay").css({top:0, opacity: 0.6});//relies on overlays having class="overlay"
    $pages.not($np[0]).not($np[1]).not($np[2]).addClass(prefix+"1");
    $pages.not($np[2]).removeClass(prefix+"5").addClass("transition");
    $pages.eq(prevPage(currentPage)).addClass(prefix+"2");
    $np[0].addClass(prefix+"3").find(".overlay").css("opacity", "0.1");
    $np[1].addClass(prefix+"4");
    $np[2].addClass(prefix+"5");
    $np[isNext ? 2 : 3].removeClass("transition");
    setTimeout(function() {
        $np[2].addClass("transition");
    }, 100);
    $(".articlecontent").css("background", "rgba(250,250,250,0)");
    $(".d_landscape_activepage_3 .articlecontent").css("background", "rgba(250,250,250,1)");
    $(".d_portrait_activepage_3 .articlecontent").css("background", "rgba(250,250,250,1)");
    correctDivs();
    $("#d_pagefix").css("opacity", "0");
    setTimeout(function() {
        $np[0].find(".overlay").css("top", "10000px");
    }, 400);
}

此代码未经测试,因此可能不是100%正确,但应该为您提供一些有关如何改进的线索。

修改

作为持续重新触发resize事件的变通方法,请尝试动态分离和重新附加resize处理程序。

替换:

$(window).resize(function() {
    correctPages();
});

with;

function attachResizeHandler() {
    $(window).on('resize', resizeHandler);
}
function resizeHandler() {
    $(window).off('resize');
    correctPages();
    setTimeout(attachResizeHandler, 600);
}

我选择600毫秒,因为它比correctPages或checkhash代码中的最长超时略长。根据确切触发不需要的调整大小事件的原因,您可以减少使用。

在代码的其他地方,替换以下所有实例:

`correctPages();` 

with:

`resizeHandler();`

当在页面加载时调用resizeHandler时,将发生checkhash();的初始附件。

答案 1 :(得分:2)

嗯,我和Mahdi用iPad测试了很多代码,最后我们知道问题来自JqueryMobile。我有这个代码

$(window).resize(function() {
  $('#log').append('<div>Handler for .resize() called.</div>'+$(window).height()+","+$(window).width());
});​

当我在iPad中没有添加对JqueryMobile的引用的情况下运行它时,页面不会更改,并且页面(code)中没有添加任何内容。

但是当我在iPad中添加对JqueryMobile的引用来运行它时,它总是添加新的页面大小(code)

对于多平台网络程序员来说,我认为这是JqueryMobile的一个非常重要的错误。我报告了here