简体   繁体   中英

Replace contents of <div> in a loop while waiting

I'm having difficulty figuring out my issue, or even finding solutions for it, which leads me to believe I may be going in the wrong direction.

On a cshtml page I have an ajax function tied to a button click. That routes back to my controller and a json string array is returned back to the client.

On the page itself I have <pre id="replaceMe">***</pre> defined. I am attempting to iterate through the json array doing $("#replaceMe").replaceWith('<pre id="replaceMe">' + data[i] + '</pre>');

Technically speaking this works, but only in the sense that the last update is visible. I might as well just go straight to the last element of the array.

I've tried using setTimeout to no avail, no changes and then suddenly the last element is displayed. I've found some sleep like functions that mimic the same basic behavior, all with similar results. I did see some recommendations for an async sleep , but none of my browsers seem to like the async and give me an error about a missing ; .

I then thought I could do something like

function updateSection(data) {
    for (var i = 0; i < data.length; i++){
        var section = $("#replaceMe");
        section.fadeOut(500);
        section.replaceWith('<pre id="replaceMe">' + data[i] + '</pre>');
        section.fadeIn(500);
    }
}

That however has the same end result. No apparent change and then suddenly it's the last element in the array.

I'm clearly going about this wrong, otherwise I'd find an example fairly readily I think, so what should I be doing instead?

To clarify and sum up, I want to replace the content of the <pre></pre> with text that's contained in an array. I want each iteration to be visible long enough for a human to see it and observe the changes (~1000ms) before going to the next iteration.

If, for example the array contains "Tom", "Dick", "Harry" , then I would like for the page to have

<pre id="replaceMe">Tom</pre> for 1 second, then that element is replaced with

<pre id="replaceMe">Dick</pre> for 1 second, then that element is replaced with

<pre id="replaceMe">Harry</pre>

I am NOT looking for

<pre id="replaceMe">Tom</pre>
<pre id="replaceMe">Dick</pre>
<pre id="replaceMe">Harry</pre>

setTimeout in a for loop runs after the for loop execution completed. so, you always see the last value. to solve this, you can use $.each method which provides a callback function or use an Immediately Invoked Function Expression.

more detailed info: https://codehandbook.org/understanding-settimeout-inside-for-loop-in-javascript/

 var data=[]; for(var i=0; i<10; i++){ data.push(i+' lorem ipsum doloret'); } $.each(data, function(i, el){ setTimeout(function(){ $("#replaceMe").replaceWith('<pre id="replaceMe">' + data[i] + '</pre>'); },500 + ( i * 1000 )); }); 
 <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <pre id="replaceMe">***</pre> 

You can do that using setInterval function:

var words = ['interating', 'and', 'replacing', 'text'];
var replace = document.querySelector('#replace');
var count = 0;

function replaceText() {
  replace.innerHTML = words[count];
  if(count === words.length - 1)
    count = 0;
  else
    count++;
}

setInterval(replaceText, 1000);

Updating: You don't need to replace all the element, you can replace only the content, using the atribute innerText.

 //pass in the data to loop over, and the index to show function updateSection(data, index) { //get a reference to the section var $section = $('#replaceMe'); //fade out the section over 500 milliseconds, then perform callback on finish $section.fadeOut(500, () => { //change the text $section.text(data[index]); //fade in the section over 500 milliseconds, and then advance the index //use modulus to reset the index to 0 when it reaches beyond the array $section.fadeIn(500, () => updateSection(data, ++index % data.length)); }); } updateSection(['Tom', 'Dick', 'Harry'], 0); 
 <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <div id="replaceMe">***</div> 

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM