/* Dimitry -- I'm hacking this up at the moment, I apologize */
carouselObj = function() {
  return {
    
    // Vars
    
    data : null,
    intervalTimer : null,
    delayTimer : null,
    curItem : -1,
    maxItems : 0,
    rotationInterval : 7000,
    restartRotation : false,
    geocode : 'http://maps.google.com/maps/geo?q=ADDRESS&key=GMAP_KEY&itemId=ITEM_ID&oe=utf8&sensor=false&output=json&callback=?',
    gmap_key : null, // TODO: Use proper key for production
    isSwitching : false,
    
    // Methods
    
    init : function() {
      carouselObj.log('init', 'Begin initiation');

      // Lookup data

      if (carouselObj.data !== null) {
        carouselObj.log('init', 'Found Carousel Data. Loading...');
        carouselObj.maxItems = carouselObj.data.length;

        // Preload the images & Geocode the addresses

        var url;
        for (var i=0; i<carouselObj.maxItems; i++) {
          
          // Images
          
          carouselObj.data[i].imgObj = $('<img/>');
          carouselObj.data[i].imgObj.attr('src', carouselObj.data[i].image);
          
          // Geocode
          
          if (carouselObj.data[i].location_data && carouselObj.data[i].location_coordinates !== true) {
            carouselObj.data[i].location_longitude = null;
            carouselObj.data[i].location_latitude = null;

            url = carouselObj.geocode.replace('ADDRESS', encodeURI(carouselObj.data[i].location_data)).replace('ITEM_ID', i).replace('GMAP_KEY', carouselObj.gmap_key);

            $.getJSON(url, carouselObj.processGeocode);
          }

        }
      } else {
        carouselObj.log('init', 'Carousel Data not found! Terminating...');
        return;
      }

      // Init the DOM

      if ($('#carousel').size() === 0) {
        carouselObj.log('init', '#carousel div not found! Terminating...');
        return;
      }

      carouselObj.log('init', 'Found #carousel div. Adding elements...');
      $('#carousel').append($('<img/>').addClass('img').css('opacity', 0));
      $('#carousel').append($('<div title="See it on the map."/>').addClass('button_location').css({'opacity':0, 'display':'none'}).click(carouselObj.toggleLocation));
      //$('#carousel').append($('<div/>').addClass('button_info').css({'opacity':0, 'display':'none'}).click(carouselObj.toggleCaption));
      $('#carousel').append($('<div title="Hint"/>').addClass('button_info').click(carouselObj.toggleCaption));      
      //$('#carousel').append($('<div/>').addClass('caption').css({'opacity':0, 'display':'none'}).append($('<p/>')));
     
      $('#carousel').append($('<div/>').addClass('caption').css({'width': '550px', 'display': 'block'}).append($('<p/>')));
      $('#carousel').append($('<div/>').addClass('location').css({'opacity':0, 'display':'none'}).append(
        $('<div/>').addClass('shim')
      ).append($('<div/>').addClass('wrapper').append(
          $('<img/>')
        ).append(
          $('<h6/>').addClass('title')
        ).append(
          $('<p/>').addClass('description')
        )
      ));
      $('#carousel').append($('<div/>').addClass('nav').append(
        $('<div/>').addClass('next').click(carouselObj.gotoNext)
      ).append(
        $('<div/>').addClass('playpause').click(carouselObj.togglePlay)
      ).append(
        $('<div/>').addClass('prev').click(carouselObj.gotoPrev)
      ));

      // Start the rotation
      
      carouselObj.startRotation();
    },
    
    processGeocode : function(data) {
      if (data.Status.code == 200) {
        
        // Get the item id
        
        var pos = this.url.indexOf('itemId=');
        if (pos == -1) {
          return;
        }
        var itemId = this.url.substr(pos+7, 1000);
        pos = itemId.indexOf('&');
        if (pos == -1) {
          return;
        }
        itemId = parseInt(itemId.substr(0, pos), 10);
        
        // Save the coordinates
        
        carouselObj.data[itemId].location_longitude = data.Placemark[0].Point.coordinates[0];
        carouselObj.data[itemId].location_latitude = data.Placemark[0].Point.coordinates[1];
        carouselObj.log('init', 'Geocoded item: ' + itemId);

      }
    },

    rotate : function() {
      carouselObj.isSwitching = true;

      // Increment the item count

      carouselObj.curItem++;
      if (carouselObj.curItem >= carouselObj.maxItems) {
        carouselObj.curItem = 0;
      }

      carouselObj.log('rotate', 'Showing item: ' + carouselObj.curItem);
      var item = carouselObj.data[carouselObj.curItem];

      // Update the image
      /*
      if (carouselObj.isCaptionShown()) {
        carouselObj.hideCaption();
      }
      if (carouselObj.isLocationShown()) {
        carouselObj.hideLocation();
      }
      */
      
      $('#carousel .img').stop();
      $('#carousel .button_location, #carousel .button_info, #carousel .img').stop().animate({'opacity':0}, 333, function(e) {
        $('#carousel .img').attr('src', item.image).animate({'opacity':1}, 333, function(e) {
          carouselObj.isSwitching = false;
        });

        // Hide buttons
        
        $('#carousel .button_location, #carousel .button_info').css('display', 'none');
        
        // Show buttons: Location and/or Caption specified?
        
        var toShow = [];
        if (typeof item.location_data != 'undefined') {
          toShow[toShow.length] = '#carousel .button_location';
        }
        if (typeof item.caption != 'undefined') {
          toShow[toShow.length] = '#carousel .button_info';
        }
        
        if (toShow.length > 0) {
          $(toShow.join(', ')).css('display', 'block').stop().animate({'opacity':1}, 333);
        }
        
        /* short circuiting the show caption/location stuff here */
        $('#carousel .caption p').html(item.caption);
        
        $('#carousel .location h6.title').html(item.location_title ? item.location_title : '');
        $('#carousel .location p.description').html(item.location_description ? item.location_description : '');
        
        if (item.link && item.link_text) {
        $('#carousel .location p.description').append($('<a href="'+ item.link +'" target="new">'+ item.link_text +'</a>'));	
        }
    
	      if (!item.location_data) {
	        carouselObj.log('showLocation', 'No location data found!');
	      }
	      if (item.location_coordinates === false && (!item.location_latitude || !item.location_longitude)) {
	        carouselObj.log('showLocation', 'No location coordinates found!');
	      }

	      var latitude, longitude;
	      if (item.location_coordinates === true) {
	        var parts = item.location_data.split(',');
	        latitude = parts[0];
	        longitude = parts[1];
	      } else {
	        latitude = item.location_latitude;
	        longitude = item.location_longitude;
	      }

        var zoom = 16 + item.location_zoom;

        var imageUrl = 'http://maps.google.com/staticmap?center=' + latitude + ',' + longitude + '&zoom=' +zoom+ '&size=320x240&maptype=mobile&markers=' + latitude + ',' + longitude + ',red&key=' + carouselObj.gmap_key + '&sensor=false';
        $('#carousel .location img').attr('src', imageUrl);

        
      });
    },

    startRotation : function() {
      carouselObj.log('startRotation', 'Rotation started');
      if (carouselObj.intervalTimer) {
        window.clearInterval(carouselObj.intervalTimer);
      }
      carouselObj.intervalTimer = window.setInterval(carouselObj.rotate, carouselObj.rotationInterval);
      carouselObj.rotate();
    },
    
    delayStartRotation : function() {
      carouselObj.log('delayStartRotation', 'Delay-Starting the rotation');

      carouselObj.delayTimer = window.setTimeout(function() {
        carouselObj.startRotation();
      }, 500);
    },

    stopRotation : function() {
      if (carouselObj.intervalTimer) {
        carouselObj.log('stopRotation', 'Rotation stopped');
        window.clearInterval(carouselObj.intervalTimer);
        carouselObj.intervalTimer = null;
      }
    },

    toggleCaption : function() {
      if (carouselObj.isSwitching === true) {
        return;
      }

      if (!carouselObj.isCaptionShown()) {
        carouselObj.showCaption();
      } else {
        carouselObj.hideCaption();
      }
    },
    
    showCaption : function() {
      carouselObj.log('showCaption', 'Showing caption');
      var item = carouselObj.data[carouselObj.curItem];
      
      if (!item.caption) {
        carouselObj.log('showCaption', 'No caption found!');
      }
      
      // Pause the rotation
      
      if (carouselObj.intervalTimer) {
        carouselObj.restartRotation = true;
      }
      carouselObj.stopRotation();
      
      // Update text and show caption

      $('#carousel .caption p').html(item.caption);
      $('#carousel .caption').css('display', 'block').stop().animate({'opacity':1,'width':'550px'}, 333);
    },

    hideCaption : function() {
      carouselObj.log('hideCaption', 'Hiding caption');
      $('#carousel .caption').stop().animate({'opacity':0,'width':'0'}, 333, function(e) {
        $('#carousel .caption').css('display', 'none');
        
        // Restart rotation?
        
        if (carouselObj.restartRotation === true && !carouselObj.isLocationShown()) {
          carouselObj.restartRotation = false;
          carouselObj.delayStartRotation();
        }
      });
    },
    
    isCaptionShown : function() {
      return ($('#carousel .caption').css('display') == 'block');
    },

    toggleLocation : function() {
      if (carouselObj.isSwitching === true) {
        return;
      }

      if (!carouselObj.isLocationShown()) {
        carouselObj.showLocation();
      } else {
        carouselObj.hideLocation();
      }
    },
    
    showLocation : function() {
      carouselObj.log('showLocation', 'Showing location');
      var item = carouselObj.data[carouselObj.curItem];

      if (!item.location_data) {
        carouselObj.log('showLocation', 'No location data found!');
      }
      if (item.location_coordinates === false && (!item.location_latitude || !item.location_longitude)) {
        carouselObj.log('showLocation', 'No location coordinates found!');
      }
      
      var latitude, longitude;
      if (item.location_coordinates === true) {
        var parts = item.location_data.split(',');
        latitude = parts[0];
        longitude = parts[1];
      } else {
        latitude = item.location_latitude;
        longitude = item.location_longitude;
      }
      
      // Pause the rotation
      
      if (carouselObj.intervalTimer) {
        carouselObj.restartRotation = true;
      }
      carouselObj.stopRotation();
      
      // Update image, text and show caption

      $('#carousel .location h6.title').html(item.location_title ? item.location_title : '');
      $('#carousel .location p.description').html(item.location_description ? item.location_description : '');

      var zoom = 16 + item.location_zoom;      
      var imageUrl = 'http://maps.google.com/staticmap?center=' + latitude + ',' + longitude + '&zoom=' + zoom + '&size=320x240&maptype=mobile&markers=' + latitude + ',' + longitude + ',red&key=' + carouselObj.gmap_key + '&sensor=false';
      $('#carousel .location img').attr('src', imageUrl);
      
      $('#carousel .location').css('display', 'block').stop().animate({'opacity':1,'width':'550px'}, 333);
      $('#carousel .location .shim').stop().animate({'width':'550px'}, 333);
    },
    
    hideLocation : function() {
      carouselObj.log('hideLocation', 'Hiding location');
      $('#carousel .location').stop().animate({'opacity':0,'width':'0'}, 333, function(e) {
        $('#carousel .location').css('display', 'none');
        
        // Restart rotation?
        
        if (carouselObj.restartRotation === true && !carouselObj.isCaptionShown()) {
          carouselObj.restartRotation = false;
          carouselObj.delayStartRotation();
        }
      });
    },
    
    isLocationShown : function() {
      return ($('#carousel .location').css('display') == 'block');
    },
    
    gotoPrev : function() {
      carouselObj.log('gotoPrev', 'Going one item back');
      carouselObj.stopRotation();
      carouselObj.restartRotation = false;
      
      if (carouselObj.curItem > 0) {
        carouselObj.curItem = carouselObj.curItem - 2;
      } else {
        carouselObj.curItem = carouselObj.maxItems - 2;
      }
      
      if (carouselObj.paused === true) {
        carouselObj.rotate();
      } else {
        carouselObj.startRotation();
      }
    },
    
    gotoNext : function() {
      carouselObj.log('gotoNext', 'Going one item forward');
      carouselObj.stopRotation();
      carouselObj.restartRotation = false;

      if (carouselObj.paused === true) {
        carouselObj.rotate();
      } else {
        carouselObj.startRotation();
      }
    },
    
    togglePlay : function() {
      if ($('#carousel .nav .playpause').hasClass('paused')) {
        carouselObj.log('togglePlay', 'Re-starting rotation');
        carouselObj.paused = false;
        $('#carousel .nav .playpause').removeClass('paused');
        carouselObj.delayStartRotation();
      } else {
        carouselObj.log('togglePlay', 'Pausing rotation');
        carouselObj.paused = true;
        $('#carousel .nav .playpause').addClass('paused');
        carouselObj.stopRotation();
      }
    },
    
    log : function(func, msg) {
      try {
        //console.info('Carousel::' + func + '(): ' + msg);
      } catch(e) {}
    }
    
  };
}();
