

var DNV_ComponentColumnsContainer = Class.create();
DNV_ComponentColumnsContainer.prototype = {
	
	bodyHeight : 100,
	
	initialize : function() {
		this.initHeights();
	},
		
	getBodyHeight : function() {
		return this.bodyHeight;
	},
	
	/**
	 * Adjust height of all component body elements to match the tallest one.
	 */
	initHeights : function() {
		var height = 0;
		var container = document.getElementsByClassName("ComponentColumns")[0];
		var footerHeight = 0;
		var footer = container.getElementsByClassName("footer")[0];
		if( footer != null ) { footerHeight = $(footer).getHeight(); }
		var elements = $A(container.getElementsByClassName("body"));
		elements.each( function( element ) { 
			element.setStyle( {display:"block"} );
			var h = element.getHeight();
			if( h > height ) { height = h };
			var contentHeight = 0;
			var contents = $A(element.getElementsByClassName("content"));
			contents.each(function(content){
				contentHeight += content.getHeight();
			});
			if( contentHeight > height ) {
				height = contentHeight;
			}
			element.setStyle( {display:""} );
		} );
		height += footerHeight * 2;
		elements.each( function( element ) { 
			element.setStyle( { height: height + "px" } );
		} );
		this.bodyHeight = height;
	},
	
	/**
	 * Adjust height of all component body elements by a delta value.
	 */
	adjustHeights:function(deltaHeight){
		var elements = document.getElementsByClassName("ComponentColumns")[0].getElementsByClassName("body");
		elements.each( function( element ) { 
			element.setStyle( {display:"block"} );
			var oldHeight = element.getHeight();
			element.setStyle( {display:"", height: (oldHeight+deltaHeight) + "px"} );
		} );
	}
}


/**
 * Component behavior that adds navigation to a component that has multiple bodies.
 */
var DNV_PagedComponentBehavior = Class.create();
DNV_PagedComponentBehavior._behaviors = [];
DNV_PagedComponentBehavior.findAndInit = function() {
	var containers = $A(document.getElementsByClassName( "ComponentContainer" ));
	containers.each( function( container ) {
		container.getElementsBySelector(".component.paged").each( 
			function( comp ) { 
				var b = new DNV_PagedComponentBehavior( comp ) ;
				DNV_PagedComponentBehavior._behaviors.push(b);
			}
		);
	} );
}
DNV_PagedComponentBehavior.getFirstPagedNumberedComponent = function() {
	var containers = $A(document.getElementsByClassName( "ComponentContainer" ));
	var componentToReturn = null;
	containers.each( function( container ) {
		container.getElementsBySelector(".component.paged").each( 
			function( comp ) { 
				if( comp.getElementsByClassName("numbers").length > 0 ) {
					componentToReturn = comp;
					return;
				}
			}
		);
	} );
	return componentToReturn;
}
DNV_PagedComponentBehavior.unload = function() {
	DNV_PagedComponentBehavior._behaviors.each(function(behavior){ behavior.unload() });
}

DNV_PagedComponentBehavior.prototype = {
	
	target:null,
	pages:null,
	navigationContainer:null,
	pagingControl:null,
	
	initialize:function( target ) {
		this.target = target;
		this.pages = this.target.getElementsByClassName( "body" );
		this.initNavigation();	
		this.createAccessorMethod();
	},
	
	unload:function() {
		this.target.getPagingControl = null;
		this.navigationContainer = null;
		this.target = null;
		this.pagingControl.unload();
		this.pagingControl = null;
	},

	initNavigation:function() {
		this.buildNavigationContainer();
		this.pagingControl = new PagingControl( this.pages, this.navigationContainer );
	},
	
	/** Create navigation DOM structure, unless it already exists. */
	buildNavigationContainer:function() {
		if( !this.hasNavigation() ) {
			var header = this.target.down( ".header" );
			new Insertion.Bottom( header, '<ol class="pageNavigation numbers"></ol>' );	
		}
		this.navigationContainer = this.target.down( ".pageNavigation" );
	},
	
	/** Check if the component already has a .pageNavigation element. */
	hasNavigation:function() {
		return this.target.down( ".pageNavigation" ) != null;
	},
	
	/** Create a local method on the target to access pagingControl */
	createAccessorMethod:function() {
		this.target.getPagingControl = function() {
			return this.pagingControl;
		}.bind( this );
	}
}



/**
 * Component behavior that extracts first link from text content and makes the whole content div clickable
 */
var DNV_LinkedComponentContentBehavior = {};
DNV_LinkedComponentContentBehavior._behaviors = [];
DNV_LinkedComponentContentBehavior.findAndInit = function() {
	var containers = $A(document.getElementsByClassName( "ComponentContainer" ));
	containers.each( function( container ) {
		container.getElementsBySelector(".content.text.linked").each( 
			function( content ) { 
				DNV_LinkedComponentContentBehavior._behaviors.push( new DNV_LinkedContentBehavior( content ) );
			}
		);
	} );
}
DNV_LinkedComponentContentBehavior.unload = function() {
	DNV_LinkedComponentContentBehavior._behaviors.each(function(b){b.unload()});
}

var DNV_LinkedContentBehavior = Class.create();
DNV_LinkedContentBehavior.prototype = {
	
	target:null,
	url:null,
	sourceLinkNode:null,
	disabled:false,
	VALID_LINK_PARENTS:$A(["H1","H2","H3","H4","H5","H6"]),
	
	initialize:function( target ) {
		this.target = target;
		this.initLinking();	
	},
	
	unload:function() {
		this.sourceLinkNode = null;
		this.target = null;
		this.url = "";
	},
	
	initLinking:function() {
		var a = $(this.target.getElementsByTagName("a")[0]);
		if( this.isValidSourceLink( a ) ) {
			this.sourceLinkNode = a;
			this.sourceLinkNode.addClassName("linkedSource");
			this.target.addClassName( "linkedActive" );
			this.url = a.href;
			Event.observe( this.target, "mouseover", this.handleMouseOver.bindAsEventListener( this ) );
			Event.observe( this.target, "mouseout", this.handleMouseOut.bindAsEventListener( this ) );
			Event.observe( this.target, "click", this.handleClick.bindAsEventListener( this ) );
		}
	},
	
	/**
	 * Only links contained in headings are valid.
	 */
	isValidSourceLink:function( linkNode ) {
		if( linkNode == null ) { return false; }
		return this.VALID_LINK_PARENTS.include( linkNode.up().tagName );
	},
	
	handleMouseOver:function(event) {
		this.target.addClassName( "hover" );
	},
	
	handleMouseOut:function(event) {
		window.setTimeout( this.doLateMouseOutCheck.bind(this), 30 );
	},
	
	doLateMouseOutCheck:function() {
		if( this.isMousePositionOutsideTarget() ) {
			this.target.removeClassName( "hover" );
		} else {
			window.setTimeout( this.doLateMouseOutCheck.bind(this), 100 );
		}
	},
	
	isMousePositionOutsideTarget:function() {
		var x = DNV_LinkedContentBehaviorMouseUtil.x;
		var y = DNV_LinkedContentBehaviorMouseUtil.y;
		return !Position.within( this.target, x, y );
	},

	handleClick:function(event) {
		if( this.disabled ) { return; }
		var clicked = Event.element(event);
		if( !this.isOtherLink( clicked ) ) {
			if( this.sourceLinkNode.click ) {
				this.disabled = true;
				this.sourceLinkNode.click();
				var _this = this;
				window.setTimeout( function(){_this.disabled=false;}, 100 );
			} else {
				window.location.href = this.url;
			}
		}
	},
	
	/**
	 * The linked content may contain other links. This behavior should leave them working normally.
	 * This method checks if the parameter is another link than the one used for this behavior.
	 */
	isOtherLink:function( clickedLink ) {
		if( clickedLink.tagName.toLowerCase() == "a" ) {
			return clickedLink != this.sourceLinkNode;
		} else {
			return false;
		}
	}
	
}


DNV_LinkedContentBehaviorMouseUtil = {
	x:0,y:0,
	handleMouseMove:function(event) {
		DNV_LinkedContentBehaviorMouseUtil.x = Event.pointerX(event);
		DNV_LinkedContentBehaviorMouseUtil.y = Event.pointerY(event);
	}
}
Event.observe( document, "mousemove", DNV_LinkedContentBehaviorMouseUtil.handleMouseMove.bindAsEventListener( this ) );




var DNV_ServiceSelector = Class.create();
DNV_ServiceSelector._selectors = [];
DNV_ServiceSelector.findAndInit = function() {
	var containers = $A(document.getElementsByClassName( "ComponentContainer" ));
	containers.each( function( container ) {
		container.getElementsBySelector(".component.serviceSelector").each( 
			function( component ) { 
				DNV_ServiceSelector._selectors.push( new DNV_ServiceSelector( component ) );
			}
		);
	} );
}
DNV_ServiceSelector.unload = function() {
	DNV_ServiceSelector._selectors.each(function(selector){selector.unload()});
}
DNV_ServiceSelector.prototype = {
	
	target:null,
	descriptions:[],
	data:[],
	currentDescription:"",
	currentUrl:"",
	doubleDropdown:null,
	
	initialize:function( target ) {
		this.target = target;
		this.importDescriptions();
		this.importData();
		this.initDropdowns();
		this.initEvents();
		this.updateDescription();
		if( this.data[0] != null && this.data[0].list[0] != null ) {
			this.currentUrl = this.data[0].list[0].value;
		}
	},
	
	unload:function() {
		this.doubleDropdown.unload();
		this.doubleDropdown = null;
		this.target = null;
		this.data = null;
	},
	
	importDescriptions:function() {
		var descriptions = this.descriptions;
		this.target.getElementsBySelector(".serviceDescriptionData div").each(
			function( div, index ) {
				descriptions[index] = div.innerHTML;
			} );
	},
	
	importData:function() {
		var select = $(this.target.down("select"));
		if( select == null ) { return; }
		var groups = select.getElementsByTagName("optgroup");
		var mainIndex = 0;
		for( var j = 0; j < groups.length; j++ ) {
			var group = $(groups[j]);
			var opt = group.getElementsByTagName("option");
			var list = [];
			for( var i = 0, len = opt.length; i < len; i++ ) {
				var o = opt[i];
				list[i] = { name:o.text, value:o.value, description:this.descriptions[mainIndex] };
				mainIndex++;
			}
			this.data[j] = { name:group.label, list:list };
		}
		select = null;
	},
	
	initDropdowns:function() {
		var industry = this.target.down(".dropdown.industry");
		var itemsPerIndustryColumn = parseInt(industry.down(".itemsPerColumn").innerHTML,10);
		var service = this.target.down(".dropdown.service");
		var itemsPerServiceColumn = parseInt(service.down(".itemsPerColumn").innerHTML,10);
		industry.innerHTML = "";
		service.innerHTML = "";
		this.doubleDropdown = new DoubleDropdownControl( industry, service, this.data, itemsPerIndustryColumn, itemsPerServiceColumn );
		this.doubleDropdown.addChangeListener( this.handleChangeEvent.bind( this ) );
	},
	
	initEvents:function() {
		Event.observe( this.target.down(".goButton"), "click", this.handleGoButtonClick.bindAsEventListener(this) );
	},
	
	handleChangeEvent:function( doubleDropdown ) {
		var d = doubleDropdown.getSelectedData();
		if( d != null ) {
			this.currentDescription = d.description;
			this.currentUrl = d.value;
			this.target.down(".goButton").show();
			this.updateDescription();
		} else {
			this.currentDescription = "";
			this.target.down(".goButton").hide();
			this.updateDescription();
		}
	},
	
	updateDescription:function() {
		this.target.down(".serviceDescription").update( this.currentDescription );
	},
	
	handleGoButtonClick:function( event ) {
		location.href = this.currentUrl;	
	}
	
}

















