		$$ = cssQuery;
		
		var IPC = {};
		
		IPC.Grid = {
			DESCRIPTION : 'A tool to create complex grid layouts using layout.css', 
			VERSION : '0.0.0.1', 
			WRAPPER : 'container', 
			LAYOUT : {
				className : 'layout', 
				col : 'gr', 
				row : 'section' 
			}, 
			COLS : {
				style : [{standard : 'standard'}, {classic : 'classic'}], 
				num : { 
					standard : [
						{ 'a-b' : '2 Column (33/67)%' }, 
						{ 'b-c' : '2 Column (67/33)%' }, 
						{ 'a-c' : '2 Column (50/50)%' }, 
						{ 'a-b-c' : '3 Column (33/33/33)%' }, 
						{ 'a-b-c-d' : '4 Column (25/25/25/25)%' } 
					], 
					classic : [
						{ 'a-b' : '2 Column (25/75)%' }, 
						{ 'b-c' : '2 Column (75/25)%' }, 
						{ 'a-b-c' : '3 Column (25/75/25)%' } 
					]
				}
			}, 
			LIPSUM : 'Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.'
		};
		
		IPC.Grid.Builder = Class.create();
		IPC.Grid.Builder.prototype = {
			initialize : function()
			{
				if ( !/gecko/i.test(navigator.userAgent ) )
				{
					this._zRunSilencer.call( this );
					return false;
				}
					
				this.CONTAINER = $( IPC.Grid.WRAPPER );
				this.CONSOLE = {
					alignment : $( 'container-alignment' ), 
					size : $( 'container-size' ), 
				//	customSize : $( 'container-size-custom' ), 
					scale : $( 'container-scale' )
				};
				this.SOURCE = {
					container : $( 'source-container' ), 
					view : $( 'view-source' ), 
					hide : $( 'hide-source' )
				};
				
				Element.hide( this.SOURCE.container );
				
				this.CONSTRUCTOR = new IPC.Grid.Construct( this );
				this.CSS = new IPC.Grid.CustomCSS( this, 'custom-css' );
				
				$$( 'div.' + IPC.Grid.LAYOUT.row, this.CONTAINER ).each( function( element, i )
				{
					if ( i == 0 )
						this.sectionHTML = element.cloneNode( true );
						
					this._makeInteractive.call( this, element );
				}.bind( this ) );
				
			//	Event.observe( this.CONSOLE.alignment, 'change', this._handleBodyChange.bind( this ), false );
				Event.observe( this.CONSOLE.alignment, 'change', this._handleBodyChange.bind( this ), false );
				Event.observe( this.CONSOLE.size, 'change', this._handleContainerChange.bind( this ), false );
			//	Event.observe( this.CONSOLE.customSize, 'blur', this._handleCustomContainerChange.bind( this ), false );
				Event.observe( this.CONSOLE.scale, 'change', this._handleContainerChange.bind( this ), false );
				Event.observe( this.SOURCE.view, 'click', this.viewSource.bind( this ), false );
				Event.observe( this.SOURCE.hide, 'click', this.hideSource.bind( this ), false );
			}, 
			
			handleNewLayoutInsertion : function( element )
			{
				$$( '.gr', element ).each( function( node )
				{
					this._makeInteractive.call( this, node );
				}.bind( this ) );
			}, 
			
			hideSource : function( evt )
			{
				Effect.BlindUp( this.SOURCE.container ); 
				Event.stop( evt );
			}, 
			
			viewSource : function( evt )
			{
				$$( '.dp-highlighter' ).each( function( dp )
				{
					Element.remove( dp );
				} );
				
				$( 'source' ).value = new IPC.Grid.Source().SOURCE;
				
				dp.SyntaxHighlighter.HighlightAll( 'source' );
				
				Effect.BlindDown( this.SOURCE.container ); 
				Event.stop( evt );
			}, 
			
			_addSection : function( evt )
			{
				var element = Event.element( evt );
				var section = Element.up( element, 'div.section' );
				var newSection = this.sectionHTML.cloneNode( true );
				
				section.parentNode.insertBefore( newSection, section.nextSibling );
				this._makeInteractive.call( this, newSection );
			}, 
			
			_handleBodyChange : function( evt )
			{
				var element = Event.element( evt );
				if ( element.value != '' )
					document.body.className = $F( element );
			}, 
			
			_handleContainerChange : function( evt )
			{
				var element = Event.element( evt );
				var val = $F( element );
				
				if ( val )
				{
					if ( $F( this.CONSOLE.size ) == 'fluid' )
						this.CONTAINER.className = $F( this.CONSOLE.size );
					else
					{
						if ( $F( this.CONSOLE.scale ) && $F( this.CONSOLE.size ) )
							this.CONTAINER.className = $F( this.CONSOLE.scale ) + '-' + $F( this.CONSOLE.size );
					}
				}
			}, 
			
			_handleCustomContainerChange : function( evt )
			{
				var element = Event.element( evt );
				var val = $F( element );
				
				if ( /\d+/.test( val ) )
				{
					
				}
			}, 
			
			_makeInteractive : function( element )
			{
				Event.observe( element, 'dblclick', this._newLayoutInsertion.bind( this ), false );
				try { 
					Event.observe( $$( 'a[class~="section-add"]', element )[0], 'click', this._addSection.bind( this ), false );
					Event.observe( $$( 'a[class~="section-remove"]', element )[0], 'click', this._removeSection.bind( this ), false );
				} catch ( e ) { }
			}, 
			
			_newLayoutInsertion : function( evt )
			{
				var element = Event.element( evt );
				
				this.CONSTRUCTOR.newInsert( element );
			}, 
			
			_removeSection : function( evt )
			{
				var element = Event.element( evt );
				if ( $$( 'div.section', this.CONTAINER ).length > 1)
				{
					if ( confirm( 'are you sure you want to remove this section?' ) )
						Element.remove( Element.up( element, 'div.section' ) );
				}
				else 
					alert( 'you have to have at least one section in here baby!' )
					
			}, 
			
			_zRunSilencer : function()
			{
				document.body.innerHTML = '<h1>Sorry this is only working in Firefox for now!</h1>';
			}
		};
		
		IPC.Grid.Construct = Class.create();
		IPC.Grid.Construct.prototype = {
			initialize : function( parent )
			{
				this.PARENT = parent;
				this.WRAPPER = $( 'layout-constructor' );
				this.D_WRAPPER = new Draggable( this.WRAPPER );
				this.COL_STYLE = $( 'column-style' );
				this.COL_NUM = $( 'column-number' );
				this.COL_TIDY = $( 'column-tidy' );
				this.INSERT = $( 'insert-layout' );
				this.CLOSE = $( 'close-constructor' );
				this.WORK_AREA = $( 'working-layout' );
				this.A_COL_TIDY = [];
				
				this._loadSelectList.call( this, this.COL_STYLE, IPC.Grid.COLS.style );
				
				this.LIGHTBOX = new IPC.LightBox( this.WRAPPER );
				
				$$( 'option', this.COL_TIDY ).each( function( option )
				{
					if ( option.value != '' )
						this.A_COL_TIDY.push( option.value );
				}.bind( this ) );
				
				this.hide();
				
				Event.observe( this.COL_STYLE, 'change', this._changeColumnStyle.bind( this ), false );
				Event.observe( this.COL_NUM, 'change', this._changeColumnNumbers.bind( this ), false );
				Event.observe( this.COL_TIDY, 'change', this._changeColumnTidy.bind( this ), false );
				Event.observe( this.INSERT, 'click', this._insert.bind( this ), false );
				Event.observe( this.CLOSE, 'click', this._close.bind( this ), false );
			}, 
			
			hide : function()
			{
				this.LIGHTBOX.hide();
			}, 
			
			newInsert : function( element )
			{
				this.show();
				if ( !/div/i.test( element.tagName ) )
					element = Element.up( element, 'div' );
				this.currentElement = element;
				this.workingLayout = Builder.node( 'div' );
				
				this.WORK_AREA.appendChild( this.workingLayout );
				
				this.COL_STYLE.selectedIndex = 0;
				this.COL_NUM.selectedIndex = 0;
				this.COL_TIDY.selectedIndex = 0;
			}, 
			
			show : function()
			{
				this.LIGHTBOX.show();
			}, 
			
			_changeColumnNumbers : function( evt )
			{
				var element = Event.element( evt );
				var columnStyle = $F( element );
				
				if ( columnStyle )
				{
					this._resetWorkingLayout.call( this );
					var layout = Builder.node( 'div', { 'class' : IPC.Grid.LAYOUT.className } );
					Element.addClassName( layout, columnStyle );
					
					columnStyle.split( '-' ).each( function( col )
					{
						layout.appendChild( 
							Builder.node( 
								'div', 
								{ 'class' : IPC.Grid.LAYOUT.col + ' ' + col }, 
								this._insertLipsum.call( this )
							)
						);
					}.bind( this ) );
					
					this.workingLayout.appendChild( layout );
				}
			}, 
			
			_changeColumnStyle : function( evt )
			{
				var element = Event.element( evt );
				var layoutStyle = $F( element );
				
				if ( layoutStyle )
				{
					new Element.ClassNames( this.workingLayout ).set( layoutStyle );
					this._loadSelectList.call( this, this.COL_NUM, IPC.Grid.COLS.num[layoutStyle] );
				}
				else 
					this._loadSelectList.call( this, this.COL_NUM, [] );
			}, 
			
			_changeColumnTidy : function( evt )
			{
				var element = Event.element( evt );
				var tidyStyle = $F( element );

				this.A_COL_TIDY.each( function( className )
				{
					Element.removeClassName( this.workingLayout, className );
				}.bind( this ) );

				if ( tidyStyle )
					Element.addClassName( this.workingLayout, tidyStyle );
			}, 
			
			_close : function( evt )
			{
				this.hide( true );
				this.currentElement = null;
				this.workingLayout = null;
				
				Event.stop( evt );
			}, 
			
			_insert : function( evt )
			{
				this.currentElement.appendChild( this.workingLayout );
				
				if ( Element.hasClassName( this.currentElement, 'section' ) )
				{
					$$( 'br', this.currentElement ).each( function( br )
					{
						Element.remove( br );
					} );
					
					this.workingLayout.appendChild( Builder.node( 'br', { 'class' : 'shim' } ) );
				}
				
				this.PARENT.handleNewLayoutInsertion.call( this.PARENT, this.currentElement );
				this._close( false );
				
				Event.stop( evt );
			}, 
			
			_insertLipsum : function()
			{
				return IPC.Grid.LIPSUM;
			}, 
			
			_loadSelectList : function( element, obj )
			{
				$$( 'option', element ).each( function( option )
				{
					element.remove( option );
				} );
				
				element.appendChild( Builder.node( 'option', { 'value' : '' }, '' ) );
				
				obj.each( function( node )
				{
					element.appendChild( Builder.node(
						'option',
						{ 'value' : Object.keys( node )[0] }, 
						Object.values( node )[0]
					) );
				} );
				element.selectedIndex = 0;
			}, 
			
			_resetWorkingLayout : function( evt )
			{
				this.workingLayout.innerHTML = '';
			}
		};
		
//	Custom CSS Class - used to create the CSS for any custom width's the use has created
		IPC.Grid.CustomCSS = Class.create();
		IPC.Grid.CustomCSS.prototype = {
			initialize : function( styleTag )
			{
				this.CUSTOM_STYLES = $( styleTag );
			}, 
			
			createRule : function()
			{
			}, 
			
			updateStyleTag : function()
			{
			}
		};
		
//	View Source Class - used to display the source code of the grid layout the user has created
		IPC.Grid.Source = Class.create();
		IPC.Grid.Source.prototype = {		
			DOCTYPE_TRANS : '<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">',
			HEADER : '<head>',
			TITLE : '<title><?php print $head_title ?></title>',
			PRINT_HEAD : '<?php print $head ?>',
			PRINT_STYLES : '<?php print atck_styles() ?>',
			IF_IE6 : '<!--[if IE 6]>',
			IE6_STYLE : '<style type="text/css" media="all">@import "<?php print base_path() . path_to_theme() ?>/fix-ie-6.css";</style>',
			END_IE6 : '<![endif]-->',
			IF_IE7 : '<!--[if IE 7]>',
			IE7_STYLE : '<style type="text/css" media="all">@import "<?php print base_path() . path_to_theme() ?>/fix-ie-7.css";</style>',
			END_IE7 : '<![endif]-->',
			PRINT_SCRIPTS : '<?php print $scripts ?>',
			HEADER_CLOSE : '</head>',
			HTML_OPEN : '<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">',
			COMMENTS : '<!-- NOTE: YOU\'LL NEED TO MANUALLY GO THROUGH AND COPY AND PASTE THE SUPPORTING' + '\n' + 'PHP MARKUP FOUND IN THE DEFAULT PAGE.TPL.PHP THAT IS INCLUDED WITH ATCK IN ORDER TO' + '\n' + 'GET THIS GRID BUILDER OUTPUT TO FUNCTION AS YOU INTEND. (e.g., THE GRID BUILDER' + '\n' + 'JUST CREATES THE XHTML/CSS FOR YOUR SITE) -->',
			HTML_CLOSE : '</html>', 
			ELEMENTS_TO_REMOVE : ['[strip="true"]', 'script', '[href^="chrome"]', 'div[style]', '#injection_graph_css'],
			REGEXP : [
				[eval( '/' + IPC.Grid.LIPSUM + '/g' ),''], 
				[/[\t\n]/g,''], 
				[/<!--.*?-->/g, ''], 
				[/(<br class=\"shim\")(>)/g, '$1\/$2'], 
				[/(>)(<)/g, '$1\n$2']
			], 
			initialize : function()
			{
				this.SOURCE_OBJ = document.getElementsByTagName( 'html' )[0].cloneNode( true );
				this.ELEMENTS_TO_REMOVE.each( function( selector )
				{
					$$( selector, this.SOURCE_OBJ ).each( function( node )
					{
						Element.remove( node );
					} );
				}.bind( this ) );
				
				var source = this.SOURCE_OBJ.innerHTML;
				this.REGEXP.each( function( re )
				{
					source = source.replace( re[0], re[1] );
				} );
				
				this.SOURCE = this.DOCTYPE_TRANS + '\n'
									+ this.HTML_OPEN + '\n'
									+ this.HEADER + '\n'
									+ this.TITLE + '\n'
									+ this.PRINT_HEAD + '\n'
									+ this.PRINT_STYLES + '\n'
									+ this.IF_IE6 + '\n'
									+ this.IE6_STYLE + '\n'
									+ this.END_IE6 + '\n'
									+ this.IF_IE7 + '\n'
									+ this.IE7_STYLE + '\n'
									+ this.END_IE7 + '\n'
									+ this.PRINT_SCRIPTS + '\n'
									+ this.HEADER_CLOSE + '\n'
									+ this.COMMENTS + '\n'
									+ source + '\n' 
									+ this.HTML_CLOSE;
			}
		};
		
		Event.observe( window, 'load', function() { new IPC.Grid.Builder(); }, false );
		
		
/**
*	LightBox UI effect
*
*	@author     Chris Constandinou <chris@constantology.com>
*
**/

		IPC.LightBox = Class.create();
		IPC.LightBox.prototype = {
			initialize : function( obj, options )
			{
				this.options = $H( {
					center : true, 
					noScroll : false, 
					partial : false
				} ).merge( options || {} );
				
				this.LIGHTBOX = Builder.node( 
					'div', 
					{ 
						'class' : 'lightbox', 
						'style' : 'display : none ;'
					}
				);
				document.body.appendChild( this.LIGHTBOX );
				
				if ( this.options.extraClassNames )
					Element.addClassName( this.LIGHTBOX, this.options.extraClassNames );
				
				this.LIGHTBOX_COPY = $( obj );
		//	this is for IE mainly but we will use this also for a common centre effect
				document.body.appendChild( this.LIGHTBOX_COPY );
				
				this.LIGHTBOX.setAttribute( 'visible', 'false' );
				
				this.LIGHTBOX.style.height = this.getDimension()['docHeight'] + 'px';
				this.LIGHTBOX.style.width = this.getDimension()['docWidth'] + 'px';
				
		//	resize is crashing IE, so...
				if ( !window.attachEvent )
					Event.observe( window, 'resize', this.setDimensions.bind( this ), false );
				
				if ( this.options.partial && navigator.appVersion.match( /MSIE/i ) )
					document.body.appendChild( Builder.node( 'div', { id : 'ie-fix' } ) );
			},
			
			centerCopy : function()
			{
				if ( navigator.appVersion.match( /MSIE/i ) || document.defaultView.getComputedStyle( this.LIGHTBOX_COPY, null ) )
					this.LIGHTBOX_COPY.style.left = ( this.getDimension()['docWidth'] - parseInt( Element.getStyle( this.LIGHTBOX_COPY, 'width' ) ) ) / 2 + 'px';
				else
					this.LIGHTBOX_COPY.style.left = '15%';
			}, 
			
			getDimension : function()
			{
				return { 
					docHeight : document.body.clientHeight + 50, 
					docWidth : document.body.clientWidth, 
					winHeight : ( window.innerHeight || document.documentElement.offsetHeight ) - 50, 
					winWidth : ( window.innerWidth || document.documentElement.offsetWidth )
				};
			}, 
			
			hide : function( obj )
			{
				Effect.Fade( 
					this.LIGHTBOX_COPY, 
					{
						duration : 0.5, 
						afterFinish: function()
						{
							if ( this.options.extraClassNames )
								this.togglePageContainer.call( this, this.options.extraClassNames, 'remove' );
								
							Effect.Fade( this.LIGHTBOX,{duration : 0.5});
						}.bind(this) 
					} 
				);
				
				if ( this.options.partial && navigator.appVersion.match( /MSIE/i ) )
				{
					this.toggleIEPotisionFixed.call( this, false );
					this.toggleSelectLists.call( this, 'visible' );
				}
				
				this.LIGHTBOX.setAttribute( 'visible', 'false' );
				
				if ( obj )
					new Effect.ScrollTo( obj );
			}, 
			
			setDimensions : function()
			{
//			console.log( document.documentElement.offsetHeight );
				if ( this.options.partial )
				{
					this.LIGHTBOX_COPY.style.height = this.getDimension()['winHeight'] + 'px';
					
					this.LIGHTBOX.style.height = this.getDimension()['docHeight'] + 'px';
				}
				else
				{
					this.LIGHTBOX.style.height = ( this.getDimension()['winHeight'] + 50 ) + 'px';
					this.LIGHTBOX.style.width = this.getDimension()['winWidth'] + 'px';
				}
				
				if ( this.options.center )
					this.centerCopy.call( this );
			}, 

			show : function()
			{
				if ( this.options.partial )
				{
					if ( navigator.appVersion.match( /MSIE/i ) )
					{
						this.toggleSelectLists.call( this, 'hidden' );
						this.toggleIEPotisionFixed.call( this, true );
					}
					
					if ( this.options.extraClassNames )
						this.togglePageContainer.call( this, this.options.extraClassNames, 'add' );
				}
				this.setDimensions.call( this );
					
				Effect.Appear( 
					this.LIGHTBOX, 
					{ 
						duration : 0.5, 
						to: 0.8, 
						afterFinish: function()
						{
							if ( this.options.noScroll )
								this.LIGHTBOX_COPY.style.top = ( ( window.pageYOffset
															                || document.documentElement.scrollTop
															                || document.body.scrollTop
															                || 0 ) + 50 ) + 'px'; 
																			
							Effect.Appear( this.LIGHTBOX_COPY, { duration : 0.5 } );
						}.bind(this) 
					} 
				);
				
				this.LIGHTBOX.setAttribute( 'visible', 'true' );
				
				if ( !this.options.noScroll )
					new Effect.ScrollTo( document.body );
//				window.scroll( 0, 0 );
			}, 
			
			toggleIEPotisionFixed : function( showLightBox )
			{
				if ( showLightBox )
					$( 'ie-fix' ).appendChild( document.getElementsByTagName( 'div' )[0] );
				else
					document.body.insertBefore( $( 'ie-fix' ).getElementsByTagName( 'div' )[0], document.body.firstChild );
			}, 
			
			togglePageContainer : function( className, type )
			{
				Element[type + 'ClassName']( document.documentElement, className );
			}, 
			
			toggleSelectLists : function( visibility )
			{
				cssQuery( 'select' ).each( function( list )
				{
					list.style.visbility = visibility;
				} );
			}
		};
