javascript - 如何在window.load之前获取计算出的CSS样式?

标签 javascript jquery document-ready computed-style window-load

我有一个自定义幻灯片页面,其中包含数百张标记中的大图片。另外,还有一个布局的调整,光靠CSS是无法完成的,需要javascript。该调整取决于计算出的几个页面元素的 CSS 样式。

问题是:在 (document).ready 上获取计算的 CSS 样式似乎不起作用。这是完全有道理的,因为当 DOM 仅仅注册时,布局/绘制还没有发生。

(window).load 是这里显而易见的答案。但在这种情况下,(window).load 的等待时间长得令人发狂,因为下载所有 100 多个大图像实际上需要 30 秒(在慢速连接上更长!)。原则上这对于幻灯片来说没问题,因为一旦加载了前两个图像,幻灯片就开始可用,早在所有图像加载之前。问题是,我希望此时也能进行脚本化 CSS 布局修正。

要检查是否加载了 imgs,我使用 imageLoaded ,这很棒,并且解决了与 imgs 一起使用时 jquery 的 load 事件的问题。但是,如何检查页面元素(例如 div)上类似“加载”的事件(以及计算样式的可用性)? (我意识到 div 不会触发加载事件。)原则上,在 (document).ready(window).load 之间是否存在可靠的跨浏览器 DOM 事件> 我可以监听一组特定的元素,以获得计算的样式?或者我被迫在这两个极端时间之间做出选择?

最佳答案

CSS 加载

Source: https://stackoverflow.com/a/12570580/1292652

向您要检查的 CSS 文件添加独特的引用样式,如下所示:

#ensure-cssload-0 {
  display: none;
}

然后,使用 JS 函数 cssLoad() 反复检查 CSS 是否已下载(不确定这与 CSS 实际绘制/渲染时是否有显着差异):

var onCssLoad = function (options, callback) {
    var body = $("body");
    var div = document.createElement(constants.TAG_DIV);
    for (var key in options) {
        if (options.hasOwnProperty(key)) {
            if (key.toLowerCase() === "css") {
                continue;
            }
            div[key] = options[key];
        }
    }

    var css = options.css;
    if (css) {
        body.appendChild(div);
        var handle = -1;
        handle = window.setInterval(function () {
            var match = true;
            for (var key in css) {
                if (css.hasOwnProperty(key)) {
                    match = match && utils.getStyle(div, key) === css[key];
                }
            }

            if (match === true) {
                window.clearTimeout(handle);
                body.removeChild(div);
                callback();
            }
        }, 100);
    }
}

您可以将其用作:

onCssLoad({
    "id": <insert element CSS applies to>,
     css: <insert sample CSS styles>
}, function () {
    console.log("CSS loaded, you can show the slideshow now :)");
});


关于 CSS 计算

Source: http://atomicrobotdesign.com/blog/javascript/get-the-style-property-of-an-element-using-javascript/

之前的解决方案仅告诉 CSS 文件是否已“下载”,而在您的问题中,您提到您需要知道元素的样式何时“计算”“渲染”“绘制”。我希望这可以解决这个问题。

向您要检查的 CSS 文件添加独特的引用样式,如下所示:

#ensure-cssload-0 {
  ignored-property: 'computed';
}

现在,使用 getPropertyValuegetCompulatedStyle 检查 CSS:

function getStyle(elem, prop) {
    return window.getComputedStyle(elem, null).getPropertyValue(prop);
}

现在,只需使用带有回调的 while 循环即可:

function checkStyle(elem, prop, callback) {
    while ( getStyle(elem, prop) !== 'computed' ) {
        // see explanation below
    }
    callback()
}

JavaScript doesn't have a pass statement ( like in Python ),我们使用一个空代码块。

如果您想检索应用于元素的所有 CSS 样式(警告:这也会显示继承的样式),请查看 this SO answer .


避免 while() 循环

通常不建议使用 while 循环来检查任何内容,因为它挂起浏览器不会让 JavaScript 线程执行任何其他操作(现在所有浏览器都是多线程的,请参阅 this comic )。

这是Chuck suggested ,这个解决方案要好得多:

function checkStyle(elem, prop, callback) {
    if ( getStyle(elem, prop) !== 'computed' ) {
        // see explanation below
        window.setTimeout( function() {checkStyle(elem, prop, callback);}, 100 )
    } else {
        callback()
    }
}

这好多了。现在该函数每 100 毫秒异步检查一次(如果需要,您可以更改此值)。在设置超时时对函数进行包装是必要的,因为 setTimeout() 还不允许传递任何参数。

希望这有帮助。请参阅本文的源代码以获取更多链接...

关于javascript - 如何在window.load之前获取计算出的CSS样式?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12607894/

相关文章:

Javascript 过滤 Div 中的文本

javascript - 如何在另一个dom元素中找到一个dom元素?

javascript - BundleConfig 脚本不起作用

javascript - 重置 document.ready ($.getScript)

JavaScript私有(private)方法,异步访问

javascript - 如何使用正则表达式替换字符串的一部分

javascript - Ajax/Jquery 表单无法工作

jquery验证错误: .验证不是函数

JQuery:为什么使用不显眼的 JavaScript/Document Ready 函数而不是 OnClick 事件?

javascript - 如果 jquery 加载失败,如何停止进一步的 javascript 调用?