【问题标题】:Safari pauses all animation on redirect / form submissionSafari 在重定向/表单提交时暂停所有动画
【发布时间】:2015-04-29 05:55:55
【问题描述】:

我有一个在点击链接时触发的动画。这是一个放大 div 然后淡出的 jQuery 动画。为了确保速度,在点击链接的同时,重定向被触发。这必须发生,我不能将重定向放在 jQuery 的 animate() 的成功函数中。此重定向是通过表单提交完成的。在 Chrome、Firefox 和 IE 上,它按预期工作,动画播放,如果页面在动画完成之前完全加载,它会重定向但动画会播放。

在 Safari 上(主要在 iPad 上测试),一旦单击链接,页面似乎“冻结”并且动画无法执行。页面加载时屏幕上还有 GIF,如果我在这些 GIF 出现在屏幕上并制作动画时单击链接,它们也会暂停。我看过一篇帖子说要设置超时,应用样式,然后提交,但问题是虽然 HTML 会应用那个 CSS 样式,但它仍然会冻结屏幕,而且他们不处理动画,只是静态 CSS 样式.

这里是一些示例代码,展示了我是如何实现这一点的方法(它没有经过测试,只是为了说明我的观点,因此可能存在遗漏部分或语法错误):

var someData = 'foo'; //This value is irrelevant, just there for syntactical consistency.
$("#link").on("click", function() {
    var form = $("<form method='POST'></form>");
    form.attr("action", "http://someurl.com");
    var input = $("<input type='hidden'/>");
    input.val(someData);
    form.append(input);
    $(document.body).append(form);
    form.submit();
  
    //Form has been submitted, now run a short animation for the remaining life of the current page
    $(this).animate({width: "100px", height: "100px", opacity: "0"}, 150);
  });
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.8.3/jquery.min.js"></script>
<div id="link" style="width: 100px; height: 100px; background-color: #FFF">Click Me</div>

基本上,我需要确保一旦 Safari 浏览器开始加载新页面/链接,它不会停止更新当前页面。从我所看到的情况来看,这听起来像是 Safari 中的一个问题,但正如我所见,这个问题在网络上也不是很常见。有帖子处理 GIF 动画,但这是 CSS 样式的动画。

感谢您的帮助!

【问题讨论】:

  • 我在 safari 遇到类似的情况,你解决了吗?
  • 作为参考,我在寻找解决方案时发现了以下 web-kit 错误:bugs.webkit.org/show_bug.cgi?id=16177
  • 很抱歉耽误了任何人关注此事 - 我还没有找到解决方案。马特,非常感谢张贴。当我最初研究这个但无法再次打开它时,我发现了这一点。

标签: javascript jquery css animation safari


【解决方案1】:

我发现,只要浏览器开始加载新页面,只要触发 pagehide 事件,Safari 就会暂停所有动画。

在页面隐藏之后,它甚至不允许 CSS 更改,例如显示之前隐藏的微调器。

为了在 pagehide 事件触发之前显示微调器,我需要为 a[href] 点击和 ajaxComplete 事件添加侦听器。

我的猜测是 Safari 这样做是为了通过将所有可用的 CPU 和 GPU 能力集中在下一页的渲染上来提高性能。

我认为这有点极端,对于 UX 来说是不幸的,因为在许多移动 Web 应用程序中,我们在页面卸载时使用微调器动画来向用户展示在获取新页面时的几秒钟内发生的事情。

到目前为止,我还没有找到在页面卸载期间保留运动动画的方法;最好的情况是微调器看起来冻结但仍然显示......一种可能的解决方法是使用静态消息来指示它“正在加载......”

【讨论】:

    【解决方案2】:

    您可以在动画结束后使用 setTimeout 转到链接。

    var someData = 'foo'; //This value is irrelevant, just there for syntactical consistency.
    
    $("#link").on("click", function() {
        setTimeout(doThisAfterTimeExpires,2000);
        $(this).animate({width: "100px", height: "100px", opacity: "0"}, 150);
    });
    
    function doThisAfterTimeExpires(){
    
        var form = $("<form method='POST'></form>");
        form.attr("action", "http://someurl.com");
        var input = $("<input type='hidden'/>");
        input.val(someData);
        form.append(input);
        $(document.body).append(form);
        form.submit();
    
    }
    

    【讨论】:

    • 这是我考虑过的解决方法,但不是解决方案。我遇到的情况是某些链接需要一段时间才能加载,因为需要在页面提供之前完成长时间运行的后台查询。为了减轻等待时间,我会播放动画。在请求页面加载之前强制完成动画只会加剧问题。
    • 同样的问题...你碰巧找到解决办法了吗?
    • 我相信我上面提出的解决方案是我最终采用的解决方案,当我遇到问题时。@BegYourPardon
    【解决方案3】:

    Safari 抱怨它找不到变量someData,它试图将输入的值设置为不存在的变量的值,并停止执行该部分页面的 JavaScript。

    [Error] ReferenceError: Can't find variable: someData
    

    只需像这样创建变量:

    // [snip]
    var input = $("<input type='hidden'/>");
    var someData;
    input.val(someData);
    // [snip]
    

    它可以在 Safari 中运行。

    【讨论】:

    • 就像我说的,代码 sn-p 是不完整的,它只是为了说明我的观点。我用“someData”标记的变量实际上是实例化的。它适用于所有其他浏览器,只是当 Safari 尝试加载页面时,它基本上会冻结任何渲染。我希望动画在它仍在等待从下一页返回的数据时发生(因此在连接速度较慢的情况下,您可以更好地看到页面正在加载)
    • var someData; 添加到您的代码中可以使您的代码在Safari 中运行。这意味着您的代码 sn-p 实际上并不反映您遇到问题的真实代码。请编辑您的帖子并提供准确反映您真实代码的代码 sn-p。
    • 我不能发布真实代码,这是我工作的公司的机密。从我的观点来看,整个工作代码 sn-p 将是无关紧要的和外部的。请阅读我的整篇文章,你会发现这比简单的 JavaScript 语法和变量实例化更深层次,而是由于 Safari 的渲染引擎中的某些东西。请仅在您理解问题的情况下回答。
    • 我很抱歉我这样说,但这不是代码语法的问题。这是在 Mac 上的 Safari 浏览器中使用表单提交导致屏幕停止更新渲染。由于遇到这样的混乱,我什至对发布 sn-p 都犹豫不决。如果它可以帮助您更有效地回答我的问题,我将编辑代码 sn-p。如果您无视我想说的一切,很难相信您阅读了整篇文章。
    • 我已经在vimeo.com/129016130 提供了一个屏幕录像,它应该在提交此评论后约 30 分钟准备就绪。到目前为止,没有证据表明 Safari 确实暂停了动画,因为您编辑的问题中的代码在 iOS 和 OS X 上的 Safari 中都可以正常工作(即 not 是否暂停动画)。您可以编辑代码以便实际触发问题吗?您可能是正确的,Safari 在通过 JS 提交表单时存在 CSS 渲染/动画错误,但没有可用的可重复代码或证据,否则无法找到解决方案。
    【解决方案4】:

    在提交表单之前编写动画代码。一段时间后执行表单提交。那就是:

    var someData = 'foo'; //This value is irrelevant, just there for syntactical consistency.
    
    $("#link").on("click", function(e) {
    
    //Write your code for animation at first.
    $(this).animate({width: "100px", height: "100px", opacity: "0"}, 150);
    
    //write the code for form submission
    setTimeout(function() {
        var form = $("<form method='POST'></form>");
        form.attr("action", "http://someurl.com");
        var input = $("<input type='hidden'/>");
        input.val(someData);
        form.append(input);
        $(document.body).append(form);
        form.submit();
     }, 1000);
    
    });
    

    【讨论】:

      【解决方案5】:

      可能在动画仍在播放时使用一些 Ajax 在隐藏帧中加载新页面。完成加载后,正常重定向到相同的 URL。然后希望这将是一个即时重定向,因为新页面可能会被缓存并且其底层查询已经处理。

      【讨论】:

      • @sukanya-purushothaman 我一直在网上寻找有关如何使用 asp.net 执行此操作的示例。到目前为止,我还没有找到一个。你有没有机会给出一个简单的 aspx 例子来说明如何做到这一点?谢谢
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-10-02
      • 2023-04-03
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多