/*******************************************************************************

Village application.js, version 1.0 (03/21/2009)
(c) 2009 BuzaMoto. All rights reserved.
Author: mud(tm) - Takashi Okamoto.

*******************************************************************************/

// ----------------------------------------------------------------------------
// GLOBALS
// ----------------------------------------------------------------------------
var MAX_ZINDEX = 0;
var rolloverImages = {};
var rolloffImages = {};
var lazyImageHandlers = {};
var scrollers = {};
var CONTACT_STATUS_TIMEOUT = 10000;
var CONTACT_SENT_TIMEOUT = 3000;
var offsetEST = isEST() ? 5 : 4;


// ----------------------------------------------------------------------------
// UTILITIES
// ----------------------------------------------------------------------------
Position.getWindowSize = function(w) {
  var width, height;
  w = w ? w : window;
  width = w.innerWidth || (w.document.documentElement.clientWidth || w.document.body.clientWidth);
  height = w.innerHeight || (w.document.documentElement.clientHeight || w.document.body.clientHeight);
  return { width: width, height: height };
}

Effect.Hide = function(element) {
  element = $(element);
  var options = Object.extend({
    from: element.getOpacity() || 1.0,
    to:   0.0,
    afterFinishInternal: function(effect) { 
      if (effect.options.to!=0) return;
    }
  }, arguments[1] || { });
  return new Effect.Opacity(element,options);
};

Element.addMethods({
  invisible: function(element) {
    return element.getStyle('opacity') <= 0;
  }
});

function toggleVisibility(element) {
  element = $(element);
  if (!element.visible()) {
    showElement(element);
  } else {
    hideElement(element);
  }
}

function hideElement(element) {
  new Effect.Parallel([
    new Effect.BlindUp(element, {sync: true}),
    new Effect.Fade(element, {sync: true})
  ], {duration: 0.4, queue: 'end'});
}

function showElement(element) {
  new Effect.Parallel([
    new Effect.BlindDown(element, {sync: true}),
    new Effect.Appear(element, {sync: true})
  ], {duration: 0.4, queue: 'end'});
}

function setSelected(element) {
  $(element).addClassName('selected');
}

function unsetSelected(elements) {
  elements.each(function(element) {
    element.up("div").removeClassName('selected');
  })
}

function isEST() {
  var gmt = new Date();
  var lsm = new Date();
  var lso = new Date();
  lsm.setMonth(2); // March
  lsm.setDate(31);
  var day = lsm.getDay();// day of week of 31st
  lsm.setDate(31-day); // last Sunday
  lso.setMonth(9); // October
  lso.setDate(31);
  day = lso.getDay();
  lso.setDate(31-day);
  return (gmt < lsm || gmt >= lso);
}


// ----------------------------------------------------------------------------
// Draggables Extension
// ----------------------------------------------------------------------------
Object.extend(Draggables, {
  dragging: function() {
    for (var i = 0, len = Draggables.drags.length; i < len; ++i) {
      if (Draggables.drags[i].dragging)
        return true;
    }
    return false;
  },
  
  find: function(element) {
    for (var i = 0, len = Draggables.drags.length; i < len; ++i) {
      if (Draggables.drags[i].element == element)
        return Draggables.drags[i];
    }
    return false;
  },
  
  registered: function(element) {
    return Draggables.find(element);
  }
});


// ----------------------------------------------------------------------------
// FUNCTIONS: Modules
// ----------------------------------------------------------------------------
function popupModule(module, x, y) {
  if (module.hasClassName('positioned') || module.hasClassName('autoload')) {
    x = (x) ? x : 0;
    y = (y) ? y : 0;
    new Effect.Parallel([
      new Effect.Move(module, { sync: true, x: x, y: y, mode: 'absolute' }), 
      new Effect.Appear(module, { sync: true, afterFinish: function() {
        initSliders(module);
      }})
    ], { duration: 0.25 });
    module.setStyle({zIndex: ++MAX_ZINDEX});
  } else {
    new Effect.Appear(module, {
      duration: 0.2,
      afterFinish: function(event) {
        initSliders(module);
      }
    });
  }
}

function initSliders(module) {
  if (!scrollers[module.id]) {
    var content = $(module.id+'-content');
    if (content && content.up(".content")) {
      // ------------ Temporarily show the module  ---------------- //
      var hidden = !module.visible();
      if (hidden) module.show();
      content.addClassName('scroll');
      var height = content.getHeight();
      var contentHeight = content.up(".content").getHeight();
      if (height > contentHeight) {
        var SCROLLBAR_TEMPLATE = new Template('<div id="#{id}-track" class="track" style="height: #{height};"><div id="#{id}-handle" class="track-handle" style="height: #{thumb_height}"></div></div>');
        var scrollbar = SCROLLBAR_TEMPLATE.evaluate({id: module.id, height: contentHeight+'px', thumb_height: contentHeight/height*contentHeight+'px'});
        module.down('.content').insert(scrollbar);
        
        var track   = $(module.id+'-track');
        var handle  = $(module.id+'-handle');
        
        scrollers[module.id] = new Control.Slider(handle, track, {
          axis:'vertical',
          minimum: 0,
          maximum: contentHeight,
          range: $R(0, height - contentHeight),
          wheelObserve: module,
          onChange: function(value) {
            content.setStyle({top: -Math.round(value)+'px'});
          },
          onSlide: function(value) {
            content.setStyle({top: -Math.round(value)+'px'});
          }
        });
      } else {
        content.removeClassName('scroll');
      }
      
      // ------------ Hide module again  ---------------- //
      if (hidden) module.hide();
    }
  }
}

function updateScrollbar(module) {
  if (scrollers[module.id]) {
    var content = $(module.id+'-content');
    if (content && content.up(".content")) {
      content.addClassName('scroll');
      var height = content.getHeight();
      var contentHeight = content.up(".content").getHeight();
      if (height > contentHeight) {
        if (!($(module.id+'-track').visible())) $(module.id+'-track').show();
        resizeScrollbar(module.id, contentHeight, height);
      } else {
        $(module.id+'-track').hide();
        content.removeClassName('scroll');
      }
    }
  }
}

function resizeScrollbar(id, contentHeight, height) {
  if ($(id) && scrollers[id]) {
    scrollers[id].maximum = contentHeight;
    scrollers[id].range = $R(0, height - contentHeight);
  }
}

function initModule(module, x, y) {
  if (module.down(".close")) {
    Event.observe(module.down(".close"), 'click', function(e) {
      var elt = $(Event.element(e)).up('.module');
      if (typeof panelPrefix == 'undefined' || elt.hasClassName('font') || elt.id == 'contact_module' || elt.id == 'add_to_cart_module' || elt.hasClassName('news_post')) {
        hidePanel(elt, false, true); 
      } else {
        hidePanel(elt.id.substring(panelPrefix.length)); 
      }
      Event.stop(e);
    });
  }

  if (module.hasClassName('positioned')) {
    x = (x) ? x : -100;
    y = (y) ? y : -(module.getHeight()+10);
    module.setStyle({left: x+'px', top: y+'px'});
    if (module.hasClassName('module')) {
      // set module to draggable
      new Draggable(module, {
        zindex: 1000,
        revert: function(element) {
          var p = element.cumulativeOffset();
          var headerHeight = $('header').getHeight();
          var headerWidth = $('header').getWidth();
          if (p.top < headerHeight || p.left < 0) {
            var m = Draggables.find(element);
            if (m) {
              if (p.top < headerHeight && p.left < 0) {
                m.delta[0] = 6;
                m.delta[1] = 0;
              }
              else if (p.left < 0) {
                m.delta[0] = 6;
                m.delta[1] = module.getStyle('top');
              }
              else if (p.top < headerHeight) {
                m.delta[0] = module.getStyle('left');
                m.delta[1] = 0;
              }
              return true;
            }
          }
        },
        beforeeffect: function(element) {
          module.setStyle({zIndex: ++MAX_ZINDEX});
          module.down('.content').setOpacity(1.0);
        },
        starteffect: function(element) {},
        endeffect: function(element) {}
      });
    }
  }
}

function initAndPopupModule(module, event, offsetX, offsetY) {
  if (Draggables.dragging()) return;
  
  offsetX = (offsetX) ? offsetX : 0;
  offsetY = (offsetY) ? offsetY : 0;
  var x = (event) ? Event.pointerX(event) + offsetX : offsetX;
  var y = (event) ? Event.pointerY(event) + offsetY : offsetY;
  
  if (!Draggables.registered(module)) {
    initModule(module, x, y);
  }
    
  if (!module.visible()) {
    popupModule(module, x, y);
  }
  
  Event.stop(event);
}


// ----------------------------------------------------------------------------
// FUNCTIONS: Panels
// ----------------------------------------------------------------------------

/*
* Displays input panel at the center of the browser window
*/
function initAndPopupInputPanel(module) {
  var windowSize = Position.getWindowSize();
  var windowCenter = {x: windowSize.width/2.0, y: windowSize.height/2.0};
  var moduleDimension = module.getDimensions();
  var x = windowCenter.x - moduleDimension.width/2.0;
  var y = windowCenter.y - moduleDimension.height/2.0 - 100;

  if (!Draggables.registered(module)) {
    initModule(module, parseInt(module.getStyle('left')), parseInt(module.getStyle('top')));
  }

  popupModule(module, x, y);
}

function setPanel(panel, target_element) {
  if (validPanels.indexOf(panel) < 0) return;
  var panelObject = (panelPrefix) ? $(panelPrefix+panel) : $(panel);
  if (panelObject.visible()) {
    hidePanel(panel, false, true);
  }
  showPanel(panel, target_element);
}

function showPanel(panel, target_element) {
  var panelName = (typeof panelPrefix == 'undefined') ? panel : panelPrefix+panel;
  var panelObject = $(panelName);
  var TG = (typeof TARGET_ELEMENT == "undefined") ? undefined : TARGET_ELEMENT;
  var target = target_element || TG;
  if (panelObject && !panelObject.visible()) {
      panelObject.remove();
      if(typeof target != "undefined"){
        $(target).insert({top: panelObject});
      }else{
        $('right_module-container').insert({top: panelObject});
      }
      panelObject.show();
  }
}

function hidePanel(panel, fade, ignoreHistory) {
  var panelName;
  var isPanel = true;
  
  if (typeof panelPrefix == 'undefined' || (typeof panel == 'object' && panel.hasClassName('positioned'))) {
    panelName = panel;
    isPanel = false;
  } else if (typeof panel == 'object' && panel.hasClassName('font')) { // fonts on foundry page doesn't have panelPrefix
    panelName = panel;
    isPanel = false;
  } else {
    panelName = panelPrefix + panel;
  }
  
  var panelObject = $(panelName);
  // if ($(panelName+'-button')) {
  //   $(panelName+'-button').removeClassName('selected');
  // }
  if (panelObject && panelObject.visible()) {
    if (!fade) {
      panelObject.hide();
    } else {
      panelObject.fade({duration: 0.4});
    }
  }

  if (ignoreHistory != true) {
    var openPanels = (History.get('panel')) ? History.get('panel').split("-") : [];
    if (openPanels.include(panel)) {
      openPanels[openPanels.indexOf(panel)] = null;
      openPanels = openPanels.compact();
    }
    History.set('panel', openPanels.join("-"));
  }
}

function showAllPanels(panels, target_element) {
  var panelName;
  panels.each(function(panel) {
    showPanel(panel, target_element);
  });
}

function hideAllPanels(panels) {
  var panelName;
  panels.each(function(panel) {
    panelName = (typeof panelPrefix == 'undefined') ? panel : panelPrefix+panel;
    if ($(panelName)) $(panelName).hide();
  });
}

function addPanel(panel, target_element) {
  if (typeof panelPrefix != 'undefined') {
    var panelObject = $(panelPrefix+panel);
    var openPanels = (History.get('panel')) ? History.get('panel').split("-") : [];
    if (openPanels.include(panel)) {
      openPanels[openPanels.indexOf(panel)] = null;
      openPanels = openPanels.compact();
    }
    openPanels.push(panel);
    History.set('panel', openPanels.join("-"));
    setPanel(panel, target_element);
  }
}


// ----------------------------------------------------------------------------
// FUNCTIONS: Contact
// ----------------------------------------------------------------------------
function showContactPanel() {
  var module = $('contact_module');
  if (!module) {
    new Ajax.Request('/site/contact_module', {
      parameters: { authenticity_token: window._token },
      onSuccess: function(transport) {
        $('content').insert(transport.responseText);
        $('contact_module').setStyle({left: '400px', top: '-100px', visibility: 'visible'});
        // update GMT offset
        if ($('contactESTOffest')) {
          $('contactESTOffest').update(offsetEST);
        }
        initAndPopupInputPanel($('contact_module'));
      },
      onFailure: function() {
        alert('error.');
      }
    });
  } else {
    initAndPopupInputPanel($('contact_module'));
  }
}

function sendContactMessage() {
  var status = $('contact_status');
  var valid = false;
  
  if ($('contact_name').value != "" && $('contact_email').value.toUpperCase().match(/^[A-Z0-9._%+-]+@[A-Z0-9.-]+\.[A-Z]{2,4}$/)) {
    valid = true;
  }
  if (!valid) {
    status.update('Please make sure your name is not blank, your email is formatted properly and try again.');
    if (!status.visible()) {
      new Effect.Appear(status, {
        duration: 0.4,
        afterFinish: function() {
          window.setTimeout(function() { new Effect.Fade(status, {duration: 0.4}); }, CONTACT_STATUS_TIMEOUT);
        }
      })
    }
    return false;
  }
  
  new Ajax.Request('/js/sendEmail.php', {
    method: 'post',
    parameters: {
      name:    $('contact_name').value,
      email:   $('contact_email').value,
      message: $('contact_message').value,
      authenticity_token: window._token
    },
    onSuccess: function(transport) {
      var response = transport.responseText;
      if (response.match(/^ERROR/)) {
        status.update(response).setStyle({ backgroundColor: '#EC2155' });
      } else {
        status.update(response).setStyle({ backgroundColor: 'yellow' });;
        $('contact_name').value = "Your Name";
        $('contact_email').value = "Your Email";
        $('contact_message').value = "Your Message";
	    status.update('Email sent, thank you for contact Rios.');
      }
      if (!status.visible()) {
        new Effect.Appear(status, {
          duration: 0.4,
          afterFinish: function() {
            window.setTimeout(function() {
              new Effect.Fade(status.up('.module'), {
                duration: 0.4,
                afterFinish: function() {
                  status.hide();
                }
              });
            }, CONTACT_SENT_TIMEOUT);
          }
        })
      }
    }
  });
  return false;
}


// ----------------------------------------------------------------------------
// FUNCTIONS: Copyright
// ----------------------------------------------------------------------------
function showCopyrightPanel() {
  var module = $('copyright_module');
  if (!module) {
    new Ajax.Request('/site/copyright_module', {
      parameters: { authenticity_token: window._token },
      onSuccess: function(transport) {
        $('content').insert(transport.responseText);
        $('copyright_module').setStyle({left: '400px', top: '-100px', visibility: 'visible'});
        initAndPopupInputPanel($('copyright_module'));
      },
      onFailure: function() {
        alert('error.');
      }
    });
  } else {
    initAndPopupInputPanel($('copyright_module'));
  }
}


// ----------------------------------------------------------------------------
// FUNCTIONS: Rollovers
// ----------------------------------------------------------------------------
function preloadImage(src) {
  var image = new Image();
  image.src = src;
  return image;
}


// ----------------------------------------------------------------------------
// FUNCTIONS: Cart
// ----------------------------------------------------------------------------
function updateFontItem(fontItem, product, priceItemID, updateCart) {
  var updateFromCart = (updateCart == undefined); // we're updating from the cart page when updateCart is undef
  if (priceItemID == 0) return false;
  updateCart = (updateCart != undefined) ? updateCart : true;
  var url = (updateCart) ? '/store/font_set_update_cart' : '/store/font_set_update_price';
  if ($(fontItem+'-price')) $(fontItem+'-price').update("loading...");
  new Ajax.Request(url, {
    parameters: {
      id:                 product,
      price_item_id:      priceItemID,
      update_cart:        updateCart,
      authenticity_token: window._token
    },
    method: 'post',
    onSuccess: function(transport) {
      var response = transport.responseText.evalJSON();
      // update price
      if ($(fontItem+'-price')) $(fontItem+'-price').update(response.price);
      if ($('subtotal_price')) $('subtotal_price').update(response.subtotal_price);
      
      if (updateFromCart) {
        // turn off cart incomplete notification
        var cartNotification = $('cart-complete');
        if (response.complete == true && cartNotification.visible()) {
          new Effect.Fade(cartNotification, {duration: 0.2});
        }
      } else {
        if (updateCart) {
          // notify cart update
          new Effect.Highlight('cart_link', {duration: 0.5, beforeStart: function() {
            $('cart_link').update('Cart ('+response.cart_size+')');
          }});
          // close panel
          $(fontItem+'-content').update('<p>Added item to cart</p>');
          window.setTimeout(function() { hidePanel($('add_to_cart_module'), true); }, 2000);
        }
      }
    }
  });
  return false;
}

function updateProductQuantity(productItem, product, priceItemID, quantity) {
  if (priceItemID == 0) return false;
  if ($(productItem+'-price')) $(productItem+'-price').update("loading...");
  new Ajax.Request('/store/product_update_cart', {
    parameters: {
      id:                 product,
      price_item_id:      priceItemID,
      quantity:           quantity,
      authenticity_token: window._token
    },
    method: 'post',
    onSuccess: function(transport) {
      var response = transport.responseText.evalJSON();
      // update price
      $(productItem+'-price').update(response.price);
      $('subtotal_price').update(response.subtotal_price);
      ["usa", "canada", "international"].each(function(shipping) {
        $('shipping_'+shipping).update(response.shipping_prices[shipping]);
      });
    }
  });
}

function lazyLoadImageObserver(image) {
  if (image.cumulativeOffset()[1] < (document.viewport.getScrollOffsets()[1] + document.viewport.getHeight())) {
    Event.stopObserving(window, 'scroll', lazyImageHandlers[image.id]);
    new Effect.Opacity(image, {
      duration: 0.2,
      queue: 'end',
      from: 0,
      to: 1.0,
      afterSetup: function() {
        image.setOpacity(0);
        image.src = image.readAttribute('longdesc');
      }
    })
  }
}


// ----------------------------------------------------------------------------
// ONLOAD
// ----------------------------------------------------------------------------
Event.observe(window, 'load', function() {
  var windowSize = Position.getWindowSize();
  var pos;
  var count = 0;
  
  // set up all modules
  $$(".module").each(function(module) {
    if (module.hasClassName('random')) {
      window.setTimeout(function() {
        var x, y;
        var dim;
        dim = module.getDimensions();
        x = Math.random()*windowSize.width + 200 - dim.width;
        x = ((x+dim.width) > windowSize.width) ? (windowSize.width - dim.width) : x;
        y = Math.random()*(windowSize.height) - dim.height;
        y = (y < 36) ? 36 : y;
        popupModule(module, x, y);
        initModule(module);
      }, 50 * count++);
    } else if(module.hasClassName('positioned')) {
      window.setTimeout(function() {
        module.setStyle({visibility: 'visible'});
        popupModule(module, parseInt(module.getStyle('left')), parseInt(module.getStyle('top')));
        initModule(module);
      }, 50 * count++);
    } else {
      window.setTimeout(function() {
        if (module.hasClassName('autoload')) popupModule(module);
        else initSliders(module);
        initModule(module);
      }, 50 * count++);
    }
  });
  
  // set up all rollovers
  var viewportHeight = document.viewport.getHeight();
  $$('img').each(function(image) {
    if (image.hasClassName('rollover')) {
      if (image.readAttribute('longdesc')) {
        rolloffImages[image.id] = preloadImage(image.readAttribute('longdesc'));
      } else {
        rolloffImages[image.id] = preloadImage(image.src);
      }
      rolloverImages[image.id] = preloadImage(image.title);
      image.title = "";
    
      Event.observe(image, 'mouseover', function(e) { image.src = rolloverImages[e.target.id].src; });
      Event.observe(image, 'mouseout', function(e) { image.src = rolloffImages[e.target.id].src; });
    }
    
    if (image.readAttribute('longdesc')) {
      if (image.cumulativeOffset()[1] < viewportHeight) {
        image.src = image.readAttribute('longdesc');
      } else {
        lazyImageHandlers[image.id] = function() { lazyLoadImageObserver(image) };
        Event.observe(window, 'scroll', lazyImageHandlers[image.id]);
      }
    }
  });
  
  // update contact GMT
  if ($('contactESTOffest')) {
    $('contactESTOffest').update(offsetEST);
  }
});
