News Tickers

Edit

This tutorial is not on the use of marquee tag. The marquee tag is deprecated by the W3C and not advised for use in any HTML documents.

News ticker is a relatively more complicated animaiton in Javascript. It requires some steps of animation could be repeated again and again. In terms of the methods of iteration, there're 2 different ways. I will detail here how I've done. Once this is overcome, it will be easier to design vertical scoller, or add some more effects - delay, fade in or fade out to the ticker.

The demos will keep growing until I cover all possible cases in my mind. The codes here is highlighted with my simple script - syntax highlighter

HTML

The HTML of the ticker is just a list of list tags container in a div tag. It looks like,

<div class="container" >
  <ul id="newsticker"> 
      <li><a href="#"> </a></li>  
      <li><a href="#"> </a></li>  
      <li><a href="#"> </a></li>  
  </ul> 
</div>

CSS

There are 2 ways to make the list nodes horizontally displayed. One way is using {display: inline} and the other is using {float: left}. I tested both ways. {float: inline} did not work satisfactorily in Safari. So here I use {float:left}.

The width of <ul> element must be long enough to make the <li> element to float. In CSS, I just give a very large number. After the javascript is loaded, the precise width can be calculated with sum of offsetWidth values of all the <li> elements.

The width of <ul> element will be so long that it will triger horizontal scroller of the browser. Nevermind, using {overflow:hidden;} to hide the exceeded contents.

Of course, moving element <ul> will be positioned, here as relative.

.container {
    position:relative;
    width:600px;
    overflow:hidden;
    border: 1px dashed #445566;
    height:22px;
    margin: 10px 0;
}

.newsticker {
    margin:0;
    padding:0;
    width: 30000px;
    position:relative;
    list-style-type: none;
}
.newsticker li{
    float:left;
    background-color:#eea9ac;
    padding-left:10px;
}

Javascript

Before we start, let's go over some basic functions that could be used in the ticker object.

For the script of div move, coz the ticker just moves horizontally, the script can be simplified as,

var ttt = [];
function $(id) {
var $ =  (typeof id  =="string") ? document.getElementById(id) : id;

$.move = function(settings,callbk) {
           ... ...
            for (i = s; i <= d; i++) { 
              (function(j) { 
				 ... ...
                 ttt[j] = setTimeout(function() { 
                           ... ...
                           ... ...      
                          },delay); 
                })(i); 
            }     
    } 
};
$.stop = function(){
     for (i in ttt) {
        clearTimeout(ttt[i]);
     }
};

return $;
}

Note here I added a stop() method here. It's used to stop the div move when it's needed.

the ticker object

Now we have all we need to construct the ticker object. The ticker will move from the right end to the left end of the container, and return to the start postion. And then repeat the cycle again and again until mouseover to stop and mouseout to start the cycle.

I've said I would introduce 2 different methods. The difference is how we repeat the cycle. One is classic way. A setTimeout method is put at the end of the function.

...
movee: function() {
  
    $(_this.ul).move({delay:_this.delay,to:{left:-_this.width,top:0}},function(){
         _this.ul.style.left = _this.left+"px";

  });

_this.t =  setTimeout(_this.movee,_this.delay);  
},
...

The other way to repeat a cycle is using setInterval. The mechanism of setInterval is wait some time and then execute an expression or function, and then iterate the cycle again and again. But for the 1st cycle, the move must go seperately, or you will have to wait a time of delay at the beginning of the move.

...
go: function(){
    $(this.ul).move({delay:_this.delay,to:{left:-_this.width,top:0}},function(){       
        this.style.left = _this.left+"px";
    });     
    this.go_on();
},

go_on:function() {
    this.repeat(this.ticker1.bind(this),this.delay+10);
},

ticker1: function(){
    $(_this.ul).move({delay:_this.delay,to:{left:-_this.width,top:0}},function(){           
        this.style.left = _this.left+"px";      
    });
},
...

Attach event

Now we can add mouseover and mouseout event to the <ul> element. To stop the move, both div move and repeat methods have to be stopped. For mouseout, when the <ul> element starts to move again to the left end, the time of delay must be re-calculated to ensure the consistant moving speed.

For the 1st method,

...
too1: function(){
     left = _this.width;
     delay = Math.abs(parseInt((parseInt(_this.ul.style.left)+left)/_this.speed));
     $(_this.ul).move({delay:delay,to:{left:-left,top:0}},function(){   
         this.style.left = _this.left+"px";
         _this.movee();     
    });    
},

For the 2st method,

...
too2: function(){
     left = _this.left;
     delay = Math.abs(parseInt((parseInt(_this.ul.style.left)+left)/_this.speed));
     $(this.ul).move({delay:delay,to:{left:-left,top:0}},function(){
         this.style.left = _this.left+"px";
         _this.go();    
    });    
},

How to use ?

var tk1 = new ticker("nt");
tk1.go();

Demo

Demo of the 1st method using setTimeout to repeat.

Demo of the 2nd method using setInterval to repeat

Last updated on May.6, 2010
www.pagecolumn.com