/**
* @desc Class that will create cross fade picture effect
* @author Boris Vujicic <24/12/2009 (dd/mm/yyyy)> 
* @author http://www.borisvujicic.com
* @version 1.3
* @params ssdiv Represents id from div in which slide show functions will be placed
* @params divone Represents id of div in which we will case/hold first photo
* @params divtwo Represents id of div which will case/hold second photo
* @params divthr Represents id of div which will case/hold navigation buttons
* ----------------------------------------------------------------------------------------
* v1.1 Update added posiblity to turn off/on navigation buttons.
* v1.2 Adjusted slidshow timing events. Slideshow now reacts more smother to io and step.
*      Added third layer which handels smooter picture changing whill picking new image durring fading.
*      Method: StopSlideshow stops slideshow of images
* v1.3 <03/04/2010 (dd/mm/yyyy)> Moved navigation to metod setNavigation
*/
function CrossFade(ssdiv, divone, divtwo, divthr, divsh){
  this.id = CrossFade.Instances.length;               // Singular instance of CrossFade object
  CrossFade.Instances[this.id] = this;                //
  this.step = 1;                                      // Amount for which opacity will go up/down (0-100).

  this.div = document.getElementById(ssdiv);          // Setting up object that will hold the whole package
  this.t1 = 1;                                        // Time to fade in picture into screen
  this.t2 = 1;                                        // Time to keep the photo still
  this.t3 = 1;                                        // Time to fade out picture from the screen
  if(divone == null) this.div1 = 'crossFade1';        // Assigning id from the first case hilder div
  else this.div1 = divone;                            // if div is not set, then default value is selected
  if(divtwo == null) this.div2 = 'crossFade2';        // Assigning id from the second case hilder div
  else this.div2 = divtwo;                            // if div is not set, then default value is selected
  if(divthr == null) this.div3 = 'navigation';        // Assigning id from the third case hilder div
  else this.div3 = divthr;                            // if div is not set, then default value is selected
  if(divsh == null) this.div4 = 'shifter';           // Assigning id from the third case hilder div
  else this.div4 = divsh;                            // if div is not set, then default value is selected
  
  
  this.divactive;                                     // Currently active DOM object
  this.divinactive;                                   // Currently inactive DOM object
  this.navigation;                                    // Navigation DOM object
  this.divshifter;                                    // Absolute picture shifiter
  
  this.microsoft = false;                             // Is this browser MICROSOFT. I know mine is not
  
  this.io = 0.2;                                      // Interlace spektrum. Moment when pictures will fade
                                                      // into each other. Default is 20%
  this.minop = 0;                                     // Minimum opacity
  this.maxop = 1;                                     // Maximum opacity (we dont need to see the full photo)
  
  this.pictures_amount = 0;                           // Current photo
  this.pictures = new Array();                        // Array of photos
  this.st1;                                           // setTimout instance
  this.st2;                                           // setTimout instance
  this.st3;                                           // setTimout instance
  this.st4;                                           // setTimout instance
  
  this.navDirection = false;
  this.navBtns = true;                                // Turn on/off navigation buttons
  this.playBtn = false;                               // Play button for script   
  this.playDirection = false;                         // Play button for script   
  
  this.fade = false;                                  // Fade is active
  
  this.opacity_up = 0.0;                              // Set opacity up to 0
  this.opacity_down = 0.0;                            // Set opacity down to 0
  this.opacity_downExtraImage = 0.0;                  // Set opacity of third holder to 0
  
  // Initializing metod to fade up the picture
  this.fade_up = function(){
   this.fade = true;
   // Is it microsoft? Hm lets set then opacity depending on which browser is in use                          
   this.microsoft?this.divactive.style.filter = "alpha(opacity: "+(this.opacity_up*100)+")":
   this.divactive.style.opacity = this.opacity_up;
   
   // Moving opacity up depending on defined step :) Up we go!  
   if(this.opacity_up < 1) this.opacity_up += this.step/100;
  };                              
  
  // Initializing metod to fade down the picture
  this.fade_down = function(){ 
    this.fade = true;
    // Is it microsoft? Hm lets set then opacity depending on which browser is in use                        
    this.microsoft?this.divinactive.style.filter = "alpha(opacity: "+(this.opacity_down*100)+")":
    this.divinactive.style.opacity = this.opacity_down;
    
    // Moving opacity up depending on defined step. Down we go :(
    if(this.opacity_down > 0)
      this.opacity_down -= this.step/100;
      
  };
  
  // Initializing metod to fade down extra picture
  this.fade_downExtraImage = function(){
    // Is it microsoft? Hm lets set then opacity depending on which browser is in use                        
    this.microsoft?this.divshifter.style.filter = "alpha(opacity: "+(this.opacity_downExtraImage*100)+")":
    this.divshifter.style.opacity = this.opacity_downExtraImage;
    
    // Moving opacity up depending on defined step. Down we go :(
    if(this.opacity_downExtraImage > 0)
      this.opacity_downExtraImage -= this.step/100;
    else{
      // Is it microsoft? Hm lets set then opacity depending on which browser is in use                        
      this.microsoft?this.divshifter.style.filter = "alpha(opacity: 0)":
      this.divshifter.style.opacity = 0;
      clearInterval(this.myInterval3);
    }
  }
  
  // Initializing metod to clear intervals update navigation and start second step.
  this.fade_stop = function(){
    // Lets clear all intervals, so that we have a clear situation.
    clearInterval(this.myInterval);
    
    this.opacity_down = 1;                            // Set opacity of second holder to 1
    this.opacity_up = 0;                              // Set opacity of first holder to 0
    
    // Lets ensure that each div has a right opacity level.
    if(this.microsoft){                               
      this.divinactive.style.filter = "alpha(opacity: 0)";  
      this.divactive.style.filter = "alpha(opacity: 100)";  
    }
    else{
      this.divinactive.style.opacity = 0;
      this.divactive.style.opacity = 1;
    }
    // Now it is time to switch divs and wait for next switch of images.
    var divswitch = this.divinactive;
    this.divinactive = this.divactive;
    this.divactive = divswitch;        
    this.fade = false;
    // Start second procedure
    this.start2();
  };
                          
  // Initializing metod that will start third step.                          
  this.fade_stop2 = function(){ 
    this.start3(); 
  };
  
  // Initializing metod to clear intervals.
  this.fade_stop3 = function(){
    clearInterval(this.myInterval2);
    this.opacity_down = 0;
    this.microsoft?this.divinactive.style.filter = "alpha(opacity: "+(this.opacity_down*100)+")":
    this.divinactive.style.opacity = this.opacity_down;
  };
  
  /* Initializing metod set up background image for active holder.
  // Creating 3 timers. 
  //   First timer defines speed of fadeup effect
  //   Second timer defines time that picture will be still 
  //   Third timer defines interval when opacity interlacing will start
  */
  this.start = function(){ 
    // if picture amount is same as size please reset it to 0
    if(this.pictures_amount == this.pictures.length) this.pictures_amount = 0;
    // Lets get that background image.
    this.divactive.style.backgroundImage = 'url('+this.pictures[this.pictures_amount++]+')';
    // Setting up timers
    this.recall_t1 = this.t1*1000/(100/this.step);
    this.recall_t2 = this.t2*1000;
    this.recall_t3 = this.t3*1000/(100/this.step);
    // If we have more then one picture lets start the procedure.
    if(this.pictures.length > 1){ 
      this.myInterval = setInterval('CrossFade.Instances['+this.id+'].fade_up()', this.recall_t1);
      // Additonal fixture of recall_t1 seconds to achive full length of overlay
      this.st1 = setTimeout('CrossFade.Instances['+this.id+'].fade_stop()', this.t1*1000+this.recall_t1);
    }
    this.setNavigation();
  }; 
  
  // Initializing metod that will initialize stop of fading and set opacity of visible div to 100.
  this.start2 = function(){
    this.st2 = setTimeout('CrossFade.Instances['+this.id+'].fade_stop2()', this.t2*1000);
    this.divinactive.style.opacity = 1;
    this.divinactive.style.filter = "alpha(opacity: "+(100)+")";
  };
  
  // Initializing metod that will initialize fade down, clear interval for fade down
  // and restart the whole procedure
  this.start3 = function(){   
    this.myInterval2 = setInterval('CrossFade.Instances['+this.id+'].fade_down()', this.recall_t3); 
    this.st4 = setTimeout('CrossFade.Instances['+this.id+'].start()', this.t3*1000*this.io);        
    this.st3 = setTimeout('CrossFade.Instances['+this.id+'].fade_stop3()', this.t3*1000+this.recall_t3);
  };
  
  // Metod that will setup divs and controls
  this.setup_divs = function(){
    var browser=navigator.appName;                      // Get browser name
    var b_version=navigator.appVersion;                 // Get browser version
    var version=parseFloat(b_version);                  // Parse version number(it is string) into number
    // Is it Microsoft??? Hope not
    if ((browser=="Microsoft Internet Explorer") && (version>=4)) this.microsoft = true;
    // Give me DOM object of first picture holder
    this.divactive = document.getElementById(this.div1);
    
    // Give me DOM object of second picture holder
    this.divinactive = document.getElementById(this.div2);
    
    // Give me DOM object of navigation holder
    this.navigation = document.getElementById(this.div3);

    // Give me DOM object of shifter holder
    this.divshifter = document.getElementById(this.div4);

    this.setNavigation();
    
    // How about some opacity? All divs should be reseted to 0 but navigation div.
    if(!this.microsoft){
      this.divinactive.style.opacity = '0.0';
      this.divactive.style.opacity = '0.0';
      this.divshifter.style.opacity = '0.0';
      this.navigation.style.opacity = '1';
    }else{
      this.divinactive.style.filter = "alpha(opacity:0)";
      this.divactive.style.filter = "alpha(opacity:0)";
      this.divshifter.style.filter = "alpha(opacity:0)";
      this.navigation.style.filter = "alpha(opacity:100)";
    }
    // is there less then 1 photo, remove navigation and show that one photo.
    if(this.pictures.length > 1){ 
    }else{
        this.divactive.style.backgroundImage = 'url('+this.pictures[0]+')';
        if(!this.microsoft){
          this.divactive.style.opacity = '1';
          this.navigation.style.opacity = '0';
        }
        else{
          this.divactive.style.filter = "alpha(opacity:100)";
          this.navigation.style.filter = "alpha(opacity:0)";
        }
    }
  };   
  
  // Add pictures to slideshow
  this.addPictures = function(url){
    this.pictures[this.pictures.length] = url;
    this.setup_divs();
  };
    // Add pictures to slideshow
  this.addPicturesInline = function(url){
    this.pictures[this.pictures.length] = url;
  };                      
  
  // Method to activate any selected photo
  this.currentPhoto = function(photo){
    // Set active picture
    this.pictures_amount = photo;
    // Clear all timeouts
    clearInterval(this.myInterval);
    
    clearTimeout(this.st1);
    clearTimeout(this.st2);    
    clearTimeout(this.st4);
    
    if(this.fade){
      if(!this.microsoft){
        this.divshifter.style.opacity = this.divactive.style.opacity;
      }else{
        this.divshifter.style.filter = this.divactive.style.filter;            
      }
      this.divshifter.style.backgroundImage = this.divactive.style.backgroundImage;            
        
      this.divactive.style.opacity = 0;
      this.opacity_downExtraImage = this.opacity_up;
      this.opacity_up = 0.0;                              // Set opacity up to 0
      this.start();
      this.myInterval3 = setInterval('CrossFade.Instances['+this.id+'].fade_downExtraImage()', this.recall_t3);         
    }else{
      clearInterval(this.myInterval2);
      clearTimeout(this.st3);             
      this.start3();  
    }                                                                                  
  }
  
  //Method to stop slideshow
  this.stopSlideshow = function(){
    // Clear all timeouts
    clearInterval(this.myInterval);
    
    clearTimeout(this.st1);
    clearTimeout(this.st2);    
        
    clearTimeout(this.st4); 
    this.setNavigation(true);
    
  }
  
  // Navigation 
  this.setNavigation = function(stopSlideshow){
    this.navigation.innerHTML = "";
    var k = 0;
    if(this.pictures_amount != 0) k = this.pictures_amount-1;
    if(this.playDirection) this.navigation.innerHTML += this.stopPlayNavigation(k, stopSlideshow);        
    if(this.navBtns){  
      if(this.navDirection ){
        for(i=0; i<this.pictures.length; i++)
          if(i!=k) this.navigation.innerHTML += "<div class=\"navbtns\" onmousedown=\"CrossFade.Instances["+this.id+"].currentPhoto("+i+");\">&nbsp;</div> ";   
          else this.navigation.innerHTML += "<div class=\"navbtns_active\">&nbsp;</div> ";
      }else{
        for(i=this.pictures.length-1; i>=0; i--)
          if(i!=k) this.navigation.innerHTML += "<div class=\"navbtns\" onmousedown=\"CrossFade.Instances["+this.id+"].currentPhoto("+i+");\">&nbsp;</div> ";   
          else this.navigation.innerHTML += "<div class=\"navbtns_active\">&nbsp;</div> ";
      }
    }
    if(!this.playDirection) this.navigation.innerHTML += this.stopPlayNavigation(k, stopSlideshow);        
  }
  
  // Play Stop button
  this.stopPlayNavigation = function(picture, stopSlideshow){
    return stopSlideshow?
    "<div class=\"pbtn\" onmousedown=\"CrossFade.Instances["+this.id+"].currentPhoto("+picture+");\">&nbsp;</div>":
    "<div class=\"sbtn\" onmousedown=\"CrossFade.Instances["+this.id+"].stopSlideshow();\">&nbsp;</div>";
  } 
}
CrossFade.Instances = new Array();