// Can also take a third argument, which, if it exists will prevent offclick from occuring
function dropdown(link,menu) {
  if (typeof menu == 'string') menu = document.getElementById(menu);
  if (menu.style.display=='none') {
    // If it's ie, we have to undo it's relative positioning because it won't float over objects 
    if (window.ActiveXObject /*&& _elStyle(menu.parentNode, 'position') == 'relative'*/) {
      // menu._prevParentPos = [menu.parentNode.style.position, menu.style.left, menu.style.right, menu.style.top];
      var currentRightStyle = _elStyle(menu, 'right');
      menu._domVals = [menu.parentNode, menu.nextSibling, menu.style.left, menu.style.right, menu.style.top, menu.parentNode.style.position];
      menu.parentNode.style.position = 'static';
      
      menu.parentNode.removeChild(menu);
      document.body.insertBefore(menu, document.body.firstChild);

      // Position correctly, automatically handling a right-aligned menu
      var target = _elPos(link); //alert("WTF is wrong with the position: "+ target);
      menu.style.top = target[1] + link.offsetHeight + 3;
      if (currentRightStyle != 'auto') menu.style.left = target[0] + link.offsetWidth - parseInt(_elStyle(menu, 'width'));
      else menu.style.left = target[0];
    }

    menu.style.display='block';
    if (link) elAddClass(link, 'menu-active');
    
    if (!arguments[2]) {
      menu._bubbledThrough = false; // when you attach an event, to onclick, the click will bubble up
      menu.offclick = function(e) {hidedropdown(link,menu);};
      addEventBase(document,'click',menu.offclick,menu.id);
    }
    else {
      menu._bubbledThrough = true;
    }
  }
  return false;
}

function hidedropdown(link, menu) {
  if (typeof menu == 'string') menu = document.getElementById(menu);
  if (!menu._bubbledThrough) {
    menu._bubbledThrough = true;
    return;
  }
  menu.style.display='none';
  if(link) elRemoveClass(link, 'menu-active');
  
  // for ie, undo the changes we did by dropping it down
  if (menu._domVals) {
    // menu.parentNode.style.position = menu._prevParentPos[0];
    var domVals = menu._domVals;

    menu.parentNode.removeChild(menu); 
    domVals[0].insertBefore(menu, domVals[1]);
    // if (domVals[1]) domVals[0].insertBefore(menu, domVals[1]);
    // else domVals[0].appendChild(menu);
    menu.style.left = domVals[2];
    menu.style.right = domVals[3];
    menu.style.top = domVals[4];
    menu.parentNode.style.position = domVals[5];
    
    // menu._prevParentPos = null;
    menu._domVals = null;
  }
      
  if (menu.offclick) {
    removeEventBase(document,'click',menu.offclick,menu.id);
    menu.offclick = null;
  }
}

function _elStyle(el,styleProp) {
	if (el.currentStyle) return el.currentStyle[styleProp];
	else if (window.getComputedStyle)	return document.defaultView.getComputedStyle(el,null).getPropertyValue(styleProp);
	else return null;
}

function _elPos(el) {
	var curleft = curtop = 0;
	if (el.offsetParent) {
		curleft = el.offsetLeft;
		curtop = el.offsetTop;
		while (el = el.offsetParent) {
			curleft += el.offsetLeft;
			curtop += el.offsetTop;
		}
	}
	return [curleft,curtop];
}

function elAddClass(el, className){
	el.className = el.className + ' ' + className;
}

function elRemoveClass(el, className){
	el.className = el.className.replace(new RegExp('(^|\\s)' + className + '(?:\\s|$)'), '$1');
}

function addEventBase(obj,type,fn,name_hash) {
if(obj.addEventListener) obj.addEventListener(type,fn,false);
else if(obj.attachEvent) {
  obj["e"+type+fn+name_hash]=fn;
  obj[type+fn+name_hash]=function(){
    obj["e"+type+fn+name_hash](window.event);
  }
  obj.attachEvent("on"+type,obj[type+fn+name_hash]);
}}

function removeEventBase(obj,type,fn,name_hash) {
  if(obj.removeEventListener) obj.removeEventListener(type,fn,false);
  else if(obj.detachEvent) {
    obj.detachEvent("on"+type,obj[type+fn+name_hash]);
    obj[type+fn+name_hash]=null;obj["e"+type+fn+name_hash]=null;
  }
}