簡體   English   中英

jquery addClass 不會立即生效

[英]jquery addClass doesn't take effect immediately

我有一個加載數據的頁面(它將使用 AJAX),所以我想顯示“正在加載,請稍候”消息。 現在我正在使用循環模擬網絡延遲。 我使用 JQuery 設置和顯示消息,但直到循環完成后才會顯示。 我需要做什么來“刷新” JQuery 命令,以便在調用循環之前顯示消息?

我在下面提供了骨架 CSS、HTML 和 JQuery/JavaScript。

<!DOCTYPE html>
<html>
<head>
<style>
.ais-card-message {
    padding: 6px;
    margin-top: 6px;
    margin-bottom: 6px;
    text-align: left;
}
.ais-card-message-info {
    background-color: lightskyblue;
}
.ais-card-message-warn {
    background-color: lightpink;
}
</style>
</head>
<body>
    <div id="title">
        <p>Message "Loading, please wait ..." should appear below when button clicked.&nbsp;
        Followed by either "Error" or "Loaded" after a short delay.</p>
    </div>
    <div id="data">Data will be loaded here</div>
    <div id="msgBox" class="ais-card-message">Messages should display here</div>
    <div><button id="btnLoad">Load</button></div>

<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
<script type="text/javascript">
    $(document).ready(function(){
        function showMsg(msg, type) {
            // msg is message to display. type is either "info" or "warn"
            $('#msgBox').removeClass("ais-card-message-info ais-card-message-warn");
            $('#msgBox').addClass("ais-card-message-" + type);
            $('#msgBox').text(msg);
            $('#msgBox').show();
            return
        }
        $('#btnLoad').click(function(){
            // For some reason the following message doesn't display
            showMsg('Loading, please wait ...', 'info');
            if (!loadData()) {
                // But this message does display if loadData returns false
                showMsg('Error', 'warn');
                return
            }else{
                // and this message also displays if loadData returns true
                showMsg('Loaded', 'info');
                return
            }
        });
        function loadData() {
            // Just a loop to simulate network delay
            var i;
            for (i=0; i < 100000; i++) {
                var j;
                for (j=0; j < 100000; j++) {
                    var k = Math.sqrt(j);
                }
            }
            $('#data').text("Here is some dummy data");
            return true
        }
    });
</script>    
</body>
</html>

您的代碼中有幾個問題。 首先,在您的“模擬” AJAX 請求中,您正在使用循環。 這是一個同步操作,是導致 UI 無法更新的問題的原因; 循環正在停止執行任何其他操作(即更新 DOM 中的元素)。 因此,它似乎只在循環完成后更新。

Secondly, once you actually start using an AJAX request in the loadData() function you will run in to problems with synchronicity as you're expecting the boolean return value to indicate whether or no the AJAX request worked. 這對於異步邏輯是不可能的。 因此,您需要使用承諾和/或回調。

為此,您需要從loadData() function 中的$.ajax()返回 promise。 然后你可以使用done()fail()方法根據請求的結果更新 DOM。 它應該看起來像這樣:

$('#btnLoad').click(function() {
  showMsg('Loading, please wait ...', 'info');
  loadData().done(function() {
   showMsg('Loaded', 'info');
  }).fail(function() {
    showMsg('Error', 'warn');
  });
});

function loadData() {
  return $.ajax({
    url: '/yourpage',
    data: {
      foo: 'bar'
    }
  });
} 

下面是一個工作示例,它通過在 3 秒后手動解析延遲的 object 來模擬 AJAX 請求。 由於正確使用了異步邏輯,您現在可以看到加載消息正確顯示。

 $(document).ready(function() { function showMsg(msg, type) { $('#msgBox').removeClass("ais-card-message-info ais-card-message-warn").addClass("ais-card-message-" + type).text(msg).show(); } $('#btnLoad').click(function() { showMsg('Loading, please wait...', 'info'); loadData().done(function() { showMsg('Loaded', 'info'); }).fail(function() { showMsg('Error', 'warn'); }); }); function loadData() { // mock AJAX request, just for this demo var deferred = jQuery.Deferred(); setTimeout(function() { deferred.resolve(); }, 3000); return deferred; } });
 .ais-card-message { padding: 6px; margin-top: 6px; margin-bottom: 6px; text-align: left; }.ais-card-message-info { background-color: lightskyblue; }.ais-card-message-warn { background-color: lightpink; }
 <div id="title"> <p>Message "Loading, please wait..." should appear below when button clicked.&nbsp; Followed by either "Error" or "Loaded" after a short delay.</p> </div> <div id="data">Data will be loaded here</div> <div id="msgBox" class="ais-card-message">Messages should display here</div> <div><button id="btnLoad">Load</button></div> <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM