【问题标题】:Prevent browser from partially rendering the page while the document is being loaded [duplicate]防止浏览器在加载文档时部分呈现页面[重复]
【发布时间】:2019-07-12 05:59:04
【问题描述】:

Firefox 和 Chrome 都过早地渲染我的页面,这导致我在几个框架中首先看到页眉,然后是内容,然后是页脚。这是一个非常非常不愉快的页面加载体验。

我现在解决这个问题的方法是这样,我想避免这种愚蠢的解决方法。它还会导致页面在 Chrome 中闪烁白光。

<!DOCTYPE html>
<html>
<head>...</head>
<body>
    <div id="render-all-at-once" style="opacity:0; min-height:100%;">
        content
    </div>
    <script>
        document.getElementById("render-all-at-once").style.opacity = 1;
    </script>
</body>
</html>

问题基本上是这样的:

<script>
    function sleep(millis) {
        var date = new Date();
        var curDate = null;
        do { curDate = new Date(); }
        while (curDate - date < millis);
    }
</script>

<div>
    This will be rendered in the first frame.
</div>

<script>
    sleep(3000);
</script>

<div>
    And only after that first frame has been rendered will you see this line. You don't see the first line for 3 seconds as 
    you might, but you do see it flash, right before both lines are displayed.
</div>
<!---
    I would like the browser to not render anything until 
    the entire entire document has been processed.
--->

在独立测试中,上述代码似乎按预期工作 - 两行将在 3 秒后同时呈现。但是当我开始向页面添加几个随机样式表时,问题就开始出现了。

我似乎无法将其缩小到任何特定的样式表或样式。我不知道是什么原因造成的。我都尝试从 加载所有样式表,或者只是将它们全部内联到样式元素中。这没有任何区别。我正在使用 Chrome 对此进行测试,因为它似乎在那里更频繁地发生。

有没有人遇到过这类问题,或者知道是什么原因造成的,并且知道有什么方法可以预防?

【问题讨论】:

  • sleep 功能可能是您的某些问题的原因。这是一种存在严重缺陷的方法,在达到限制之前会消耗尽可能多的 CPU。
  • @RobG 只是为了模拟随机处理。即使没有涉及 javascript 并且只有很多元素需要处理,问题似乎也会出现。
  • @BjarkeCK——早在拨号上网的早期,一些浏览器在整个页面下载之前不会显示任何内容。用户不喜欢它,他们更愿意尽快看到内容并忍受刷新和布局“抖动”,而不是盯着空白页面想知道是否发生了任何事情。这就是我所知道的所有浏览器都进行渐进式显示的原因。最好采用一种将渐进式显示问题最小化的方法,而不是在页面加载之前隐藏页面。
  • @RobG 哦,这实际上是一个非常酷的见解,他们在过去会这样做是有道理的。但我强烈反对在今天逐步加载网站是一个好主意。如果您正在构建一个非常快速且快速的网站,那么天哪,浏览器决定通过显示未完成渲染网站的几帧来破坏体验,即使一切都在 10 毫秒后准备就绪,这很烦人。我认为我们应该始终为更好的网站和更好的用户体验而努力,而浏览器应该使我们能够做到这一点。
  • 不是每个人都有快速连接 移动连接可能参差不齐。还有农村社区(想想加利福尼亚北部的农村,比如奇科:山区的 Trinity,所有的连接仍然很慢,而且很难找到蜂窝信号,时期。)即使是圣克鲁斯也有许多蜂窝死区 - 它是 真的靠近硅谷。我明白你的意思。但你的经历可能是一种特权。祝您找到解决方案好运,但请记住为其他所有人提供良好的后备方案。地理位置可以在连接可用性和速度方面发挥作用。

标签: javascript html css


【解决方案1】:

我喜欢做的是将我的内容包装在一个 div 中并将其设置为display:none

然后,我推迟 CSS 加载并在我的 CSS 文件中,并将包装 div 设置为 display:block

我还将所有 CSS 文件压缩到一个文件中(以便更好地加载)。

<!DOCTYPE html>
<html>
    <head>
        <style>
            .wrap {
                display: none;
            }
        </style>
    </head>

    <body>
        <div class="wrap">
            content
        </div>
        <noscript id="deferred-styles">
            <link rel="stylesheet" type="text/css" href="compressed.css" />
        </noscript>
        <script>
            var loadDeferredStyles = function() {
                var addStylesNode = document.getElementById("deferred-styles");
                var replacement = document.createElement("div");
                
                replacement.innerHTML = addStylesNode.textContent;
                document.body.appendChild(replacement);
                addStylesNode.parentElement.removeChild(addStylesNode);
            };

            var raf = requestAnimationFrame || mozRequestAnimationFrame ||
                webkitRequestAnimationFrame || msRequestAnimationFrame;

            if(raf) {
                raf(function() {
                    window.setTimeout(loadDeferredStyles, 0);
                });
            } else {
                window.addEventListener('load', loadDeferredStyles);
            }

        </script>
    </body>
</html>

【讨论】:

  • 很高兴知道我不是唯一一个遇到这个问题的人!将尝试您的方法,看看是否效果更好。谢谢!仍然很烦人,你必须做那些技巧。
【解决方案2】:

使用开发者工具中的网络标签来查看每个请求的过程和响应。首先,浏览器完全接收和解析 HTML,然后自上而下查找要加载的远程对象:样式表、图像、javascript 等。

因此,要完全控制事物的显示方式,请发送一个看起来与您希望的初始视图完全相同的 HTML 文档(例如:一个空白的白色文档,使用内联 CSS 或 &lt;style&gt; 标签实现目标&lt;body&gt;)。然后使用一行 Javascript 来监听 load 事件并更新你的显示,例如:

<!doctype html>
<html>
    <link rel="stylesheet" type="text/css" href="https://cdn.sstatic.net/Sites/stackoverflow/primary.css">
    <body style="display: none;">
        <h1>Headline</h1>
    </body>
    <script>
        window.addEventListener("load", function(event) {
            document.querySelector("body").style.display = "block";
        });
    </script>
</html>

【讨论】:

  • 我已经复制了这个,没有引用任何东西,所有样式都被内联并且没有使用图像。这不排除所有与网络相关的错误吗?
  • 我有兴趣查看您的文件!具体来说,当您提到“页眉,然后是内容,然后是页脚”时——我从未见过浏览器会这样运行,除非服务器以块的形式发送响应或页面使用 Javascript 来中间更改 DOM。
  • 当然!希望这足够清楚:) imgur.com/a/1fgwI8a
猜你喜欢
  • 2012-05-21
  • 2015-05-21
  • 2012-06-11
  • 2022-01-18
  • 1970-01-01
  • 2016-11-15
  • 1970-01-01
  • 1970-01-01
  • 2011-06-09
相关资源
最近更新 更多