﻿// SLIDE SHOW
// Copyright (c) 2011 EmeraldConnect (http://www.emeraldconnect.com)
// written by Casey Wasser
// last updated: 04/01/2011

// class parameters
// defaults can be over-ridden for the following:
//   slideshow container element - string(id)|element
//   theme - string
//   width - int, in pixels
//   height - int, in pixels
//   duration - int, in seconds

// slide parameters
//   href: required - string
//   src: required - string
//   title: optional - string
//   duration: optional - int, in seconds

// Example slides array:
// var slidesArr = [{
//    href: 'http://www.google.com',
//    src: 'include/media/images/duck1.jpg'//,
//    title: 'Duck number one',
//    duration: 2.5
//  },
//  {
//    href: 'http://www.news.google.com',
//    src: 'include/media/images/duck2.jpg'//,
//  }];

// html templates for use by the slideShow class
var slideShowHTML = {
  slideAnchor:
    '<a href="" class="slideAnchor">' +
      '<img src="/include/images/spacer.gif" class="slideImage" alt="" />' +
    '</a>',
  slideController:
    '<div class="slideController">' +
      '<div class="button slideBack">&#160;</div>' +
      '<div class="button slidePlayPause pause">&#160;</div>' +
      '<div class="button slideNext">&#160;</div>' +
      '<div class="selectSlideButtons"></div>' +
    '</div>',
  slideSelect: function(instanceID, i, title) {
    var t = new Template('<div class="button slideSelect" id="slideSelect_#{instanceID}_#{i}" title="#{title}">&#160;</div>');
    return t.evaluate({
      instanceID: instanceID,
      i: i,
      title: title
    });
  }
};

// slideShow class
var slideShow = Class.create({
  fade: 250,
  id: 0,
  fresh: true,
  container: null,
  slideAnchor: null,
  slideImage: null,
  slideController: null,
  theme: 'sphere',
  width: 230, // int to concat w/ 'px'
  height: 130, // int to concat w/ 'px'
  duration: 5, //seconds
  slides: null, // json array of slide objects
  currentSlide: null, // int 0,1,2...
  paused: false, // bool
  pause: function() {
    this.paused = true;
    var button = this.slideController.select('.slidePlayPause')[0];
    button.removeClassName('pause');
    button.addClassName('play');
  },
  play: function() {
    this.paused = false;
    var button = this.slideController.select('.slidePlayPause')[0];
    button.removeClassName('play');
    button.addClassName('pause');
    this.autoPlay();
  },
  autoPlay: function() {
    var duration = this.slides[this.currentSlide].duration ? this.slides[this.currentSlide].duration : this.duration;
    var SlideShow = this; // bind

    setTimeout(function() {
      if (!SlideShow.paused) {
        SlideShow.next();
        SlideShow.autoPlay();
      }
    }, duration * 1000);
  },
  back: function() {
    this.currentSlide = this.currentSlide > 0 ? this.currentSlide - 1 : this.slides.length - 1;
    this.draw(this.currentSlide);
  },
  next: function() {
    this.currentSlide = this.currentSlide < this.slides.length - 1 ? this.currentSlide + 1 : 0;
    this.draw(this.currentSlide);
  },
  draw: function(i) {
    this.currentSlide = i;
    var fade = 0;
    if (!this.fresh) {
      this.fadeOut();
      fade = this.fade;
    }

    var parentClass = this; // bind
    var t = setTimeout(function() {
      parentClass.slideAnchor.href = parentClass.slides[i].href;
      parentClass.slideAnchor.title = parentClass.slides[i].title ? parentClass.slides[i].title : '';
      parentClass.slideImage.style.backgroundImage = 'url(' + parentClass.slides[i].src + ')';
      parentClass.slideController.select('.slideSelect').each(function(slideSelect, j) {
        if (i == j) {
          slideSelect.addClassName('on');
        }
        else {
          slideSelect.removeClassName('on');
        }
      });
      if (parentClass.fresh) {
        parentClass.fresh = false;
      }
      else {
        parentClass.fadeIn();
      }
    }, fade);
  },
  fadeOut: function(opacity) {
    var image = this.slideImage;
    var parentClass = this; // bind
    opacity = opacity ? opacity : image.getOpacity();
    if (opacity > 0) {
      image.setOpacity(opacity - .2);
      setTimeout(function() {
        parentClass.fadeOut(opacity - .2);
      }, parentClass.fade / 5);
    }
  },
  fadeIn: function(opacity) {
    var image = this.slideImage;
    var parentClass = this; // bind
    opacity = opacity ? opacity : image.getOpacity();
    if (opacity < 1) {
      image.setOpacity(opacity + .2);
      setTimeout(function() {
        parentClass.fadeIn(opacity + .2);
      }, parentClass.fade / 5);
    }
  },
  setButtons: function() {
    var SlideShow = this; // bind

    $A(this.slides).each(function(slide, i) {
      var title = slide.title ? slide.title : '';
      SlideShow.slideController.select('.selectSlideButtons')[0].insert(slideShowHTML.slideSelect(SlideShow.id, i + 1, title));
    });

    this.container.select('.slideBack').each(function(slideBack) {
      slideBack.onclick = function() {
        SlideShow.pause();
        SlideShow.back();
      }
    });

    this.container.select('.slideNext').each(function(slideNext) {
      slideNext.onclick = function() {
        SlideShow.pause();
        SlideShow.next();
      }
    });

    this.container.select('.slidePlayPause').each(function(slideNext) {
      slideNext.onclick = function() {
        if (this.hasClassName('pause')) {
          SlideShow.pause();
        }
        else {
          SlideShow.play();
        }
      }
    });

    this.container.select('.slideSelect').each(function(slideSelect) {
      slideSelect.onclick = function() {
        SlideShow.pause();
        SlideShow.draw(Number(slideSelect.id.split('_')[2]) - 1);
      }
    });

    // open absolute paths in another window or tab
    this.container.select('a').each(function(a) {
      a.observe('click', function(event) {
        element = event.element();
        element = element.href ? element : $(element.parentNode);
        // attempt to override navigation
        try {
          var strA = location.href.split('//')[1].split('/')[0];
          var strB = element.href.split('//')[1].split('/')[0];
          if (strA != strB) {
            event.stop();
            window.open(element.href);
          }
        }
        catch (exp) {
          // do nothing
        }
      });
    });
  },
  init: function(element) {
    this.container = element;
    this.container.addClassName(this.theme);
    this.container.style.width = this.width + 'px';

    // slide Image and Anchor
    this.container.insert(slideShowHTML.slideAnchor);
    this.slideAnchor = this.container.select('.slideAnchor')[0];
    this.slideImage = this.container.select('.slideImage')[0];
    this.slideAnchor.style.height = this.height + 'px';
    this.slideImage.style.height = this.height + 'px';
    this.slideImage.style.width = this.width + 'px';

    // slide controller
    this.container.insert(slideShowHTML.slideController);
    this.slideController = this.container.select('.slideController')[0];

    this.setButtons();
    this.container.show();
    this.draw(0);
    this.play();
  }
});

// id to be incremented for multiple
// instances of slideShow class
var slideShowID = 0;

// function for adding an instance
var newSlideShow = function(slidesArr, element, width, height, duration, fade) {
  // new instance
  var SlideShow = new slideShow();

  // set the id
  SlideShow.id = slideShowID;
  // in case multiple instances,
  // increment the id
  slideShowID++;

  // get the element, 
  // even if they didn't pass one
  element = $(element);
  if (!element) {
    element = $$('.slideShow')[0];
  }
  // dimensions
  if (width) {
    SlideShow.width = width;
  }
  if (height) {
    SlideShow.height = height;
  }
  // slide duration
  if (duration) {
    SlideShow.duration = duration;
  }
  // slide duration
  if (fade) {
    SlideShow.fade = fade;
  }
  // slides array
  if (slidesArr) {
    SlideShow.slides = slidesArr;
  }

  SlideShow.init(element);

  return SlideShow;
};

