Search code examples
javascriptjqueryqueuetransitionsequential

Fade in arbitrary number of text lines sequentially with jquery queue


This gets pretty specific but I'd like to be able to fade in an arbitrary number of children sequentially and with delayed timing using jquery queue (though I'm open to other methods). Here is what I have working already.

This is the basic html block I'm working with

<header>
  <p class="copy">Thing one</p>
  <p class="copy">Thing two</p>
  <p class="copy">Cat in the Hat</p>
</header>

This current jquery works, but it feels hacky to me in that I need to know in advance how many nodes to expect.

var $screenHeader = $('header');
$screenHeader.queue(function () {
  $screenHeader.find('.copy:nth-child(1)').addClass('visible');
  $(this).dequeue();
})
.delay(1500)
.queue(function () {
  $screenHeader.find('.copy:nth-child(2)').addClass('visible');
  $(this).dequeue();
})
.delay(1500)
.queue(function () {
  $screenHeader.find('.copy:nth-child(3)').addClass('visible');
  $(this).dequeue();
})
.delay(1500);

I would love it if something like this worked

for (var i = 1; i < $screenHeader.children().length+1; i++) {          
  $screenHeader.queue(function () {
    $screenHeader.find('.copy:nth-child('+i+')').addClass('visible');
    $screenHeader.dequeue();
  }).delay(1500);
}

or better yet

$screenHeader.children().each(function (i) {
  $screenHeader.queue(function () {
    $screenHeader.find('.copy:nth-child('+i+')').addClass('visible');
    $screenHeader.dequeue();
  }).delay(1500); 
});

or even more betterer (then i'm done, I promise)

$screenHeader.children().each(function () {
  $screenHeader.queue(function () {
    $(this).addClass('visible');
    $screenHeader.dequeue();
  }).delay(1500); 
});

Now, I know there's some funkiness with how $(this) is passed around so that last one isn't a priority, but it would be really nice to get some sort of loop working. Listing them out and repeating all that code and being tied to the html kills me.

Help would be greatly appreciated. :)


Solution

  • Figured it out!

    $(this) inside the $screenHeader.queue(... loop was the header. I needed to store the child before entering the loop queue part.

    var delayTime = 1500,
        $screenHeader = $('#screen-'+screenIndex+' header'),
        $copyChildren = $screenHeader.children('.copy');
    
    $copyChildren.each(function () {
      var child = $(this);
      $screenHeader.queue(function () {
        child.addClass('visible');
        $screenHeader.dequeue();
      }).delay(delayTime); 
    });
    

    Feelin classy.