jQuery addClass到多个元素显示意外延迟

时间:2014-09-24 10:25:09

标签: javascript jquery html css

我正在制作一个翻转计数器,它应该在达到目标数时改变颜色(示例中为1000)。但问题是柜台的不同部分同时不会改变颜色,我们可以清楚地看到构成柜台的瓷砖之间的延迟......

我正在使用一个简单的jQuery addClass来触发颜色更改:

$("#rhcounter .count").addClass("red");

任何想法可能导致什么?

这是小提琴:http://jsfiddle.net/ka6ke28m/6/

感谢您的帮助!

2 个答案:

答案 0 :(得分:0)

正在发生这种情况,因为您在更改文本之前更改了颜色。我只是转移了条件,我认为这就是你想要的DEMO

$(window).load(function() {
    var total = 1000, current = 950, timeout = 150, inc = 7,
        prevTiles = ["0","0","0","0"],
        interval = setInterval(function(){increase()}, timeout),
        increase = function () {
            current += inc;

            if (current >= total) { 
                clearInterval(interval);
                current = total;
            }



            var tiles = [false, false, false, false], 
                currStr = (current+"").split("").reverse().join("");

            for (var i = 0; i < currStr.length; i++) {
                if (currStr[i] !== prevTiles[i]) { 
                    tiles[i] = true; 
                    prevTiles[i] = currStr[i];
                }
            }

            tiles.forEach(function (tile, index) {
                if (!tile) { return; }

                $("#rhcounter > div[class~='tile"+index+"'] > span[class~='curr']").each(function() {
                    $(this).text($("#rhcounter > div[class~='tile"+index+"'] > span.count.next.top").text());
                });
                $("#rhcounter > div[class~='tile"+index+"']").removeClass("flip");
                setTimeout(function(){$("#rhcounter > div[class~='tile"+index+"']").addClass("flip");}, 5);

                var top = $("#rhcounter > div[class~='tile"+index+"'] > span.count.next.top"),
                    bottom = $("#rhcounter > div[class~='tile"+index+"'] > span.count.next.bottom"),
                    delay = (index === 0 ? timeout : 250);

                setTimeout(function(){ top.text(prevTiles[index]); }, delay/2);
                setTimeout(function(){ bottom.text(prevTiles[index]); }, delay/2);
            });
         if (current === total) { 
                $("#rhcounter .count").addClass("red");
            }};
});

答案 1 :(得分:0)

第一期:

有大量浪费的处理正在进行中。 jQuery选择器有一个开销,所以将它们减少到最小,复杂的选择器也是如此。我已经大大减少了。

第二期:

在某些浏览器上有一个令人讨厌的视觉故障,如下所示:

enter image description here

使用background-color:代替background:(试图完全重新渲染区域而不是仅填充背景颜色)可以消除这种情况。

第三个问题:

留下的蓝色是为了缓慢重新绘制屏幕。以上两个修复产生了巨大的影响,我还尝试添加仅适用于红色类的特定CSS动画。现在你知道慢速绘画的原因(例如有蓝色和红色的CSS动画吗?),这可能会有所改善:

http://jsfiddle.net/TrueBlueAussie/ka6ke28m/10/

$(function () {
    var total = 1000,
        current = 950,
        timeout = 150,
        inc = 7,
        prevTiles = ["0", "0", "0", "0"],
        interval = setInterval(function () {
            increase()
        }, timeout),
        increase = function () {
            current += inc;

            if (current >= total) {
                clearInterval(interval);
                current = total;
            }

            if (current === total) {
                $("#rhcounter .count").addClass("red");
            }
            // instant timer to delay css
            setTimeout(function () {
                var tiles = [false, false, false, false],
                    currStr = (current + "").split("").reverse().join("");

                for (var i = 0; i < currStr.length; i++) {
                    if (currStr[i] !== prevTiles[i]) {
                        tiles[i] = true;
                        prevTiles[i] = currStr[i];
                    }
                }

                tiles.forEach(function (tile, index) {
                    if (!tile) {
                        return;
                    }

                    // Get the current tile
                    var $tile = $("#rhcounter div.tile" + index);
                    $tile.children('span.curr').each(function () {
                        $(this).text($tile.text());
                    });
                    $tile.removeClass("flip");
                    setTimeout(function () {
                        $tile.addClass("flip");
                    }, 5);

                    var top = $tile.find("span.count.next.top"),
                        bottom = $tile.find("span.count.next.bottom"),
                        delay = (index === 0 ? timeout : 250);

                    setTimeout(function () {
                        top.text(prevTiles[index]);
                    }, delay / 2);
                    setTimeout(function () {
                        bottom.text(prevTiles[index]);
                    }, delay / 2);
                });
            }, 1);
        };
});