if (!SDNA) {
	var SDNA = {};
}

SDNA.global = function(){};
SDNA.user 	= function(){};
SDNA.ajax   = function(){};

SDNA.ajax.error = function(e, data ){
	
	if( !(data.xhr.status==0 && data.xhr.readyState==4) && data.xhr.status!=200 ){
	
		//setup a message
		var message = data.xhr.status + " " + data.xhr.statusText;
		
			//show the user an error happened
			Window.pop(
				message,
				{error:true}		
			);
		
		//publish the error
		SDNA.Event.publish('ajax.error', data);
	
	}else{
		data.event.stopImmediatePropagation();
	}
	
};

SDNA.ajax.error.bind = function(){

	$j().ajaxError( function(e, xhr, opts, err){
		
		SDNA.Event.trigger('ajax.error', { event: e, xhr: xhr, options: opts, error: err} );
		
	});
};

SDNA.ajax.complete = function(e, data ){
	
	//track this ajax request	
	Google.track( data.options.url  );
}

SDNA.ajax.complete.bind = function(){

	$j().ajaxComplete( function(e, xhr, opts){
		
		SDNA.Event.trigger('ajax.complete', { event: e, xhr: xhr, options: opts} );
		
	});
};

SDNA.ajax.Error = function(request, textStatus, a, b) {
	if(textStatus != 'timeout') {
		return;
	}
	
	alert("Sorry, the current action is taking to long. We'll need to reload the page and have you try again");
	
	var submitForm = document.createElement("FORM");
	document.body.appendChild(submitForm);
	submitForm.method = "POST";
	var timeoutElement = document.createElement("input");
	timeoutElement.name='timeoutRequest';
	timeoutElement.type='hidden';
	submitForm.appendChild(timeoutElement);
	timeoutElement.value = this.url;
	submitForm.action = window.location.href;
	submitForm.submit();
};

//setup a timeout for ajax calls
// jQuery.ajaxSetup( {"timeout":10000, "error":SDNA.ajax.Error} ); 

SDNA.tabs = function(){};
SDNA.tabs.setupHelpButtons = function( $area ){

	$area.find('.tabs_content ul.tabs')
		.each(function(){
			$tabs = $j(this);
			$help = $j('<a class="tabs_help" />').text('Help').attr('title','What are filters?').fadeIn('slow');
			$tabs.after($help);	
			$help.unbind('click.help').bind('click.help', function(){
				
				//build the list of help from the tabs' titles
				$tabs = $j(this).siblings('ul.tabs').find('li a');
				
				//build the tabs modal content
				$content = $j('<div />').append( '<h2>About these filters</h2>' );
				$info		 = $content.append( '<p class="instructions">Filters provide a of way of calming down the activity that you see. For instance, you might want to view only what the host has said about an event or maybe only the guests that are coming to an event. </p>' );
				$tabs.each(function(){
					var $this = $j(this);
					var title = $this.attr('title');
					
					if( title ){
						$title = $j('<strong />').text( $this.text() ).appendTo( $content );
						$par = $j('<p class="info"/>').text(title).appendTo( $content );
					}
				});
				
				//open the modal
				Window.pop( $content )
			});
		});	
};

SDNA.global.setupModals = function( oModalContent ){
	
}

SDNA.global.onModalOpen = function( oDialog, options ){
	
	var opts = { delay:200, modal: false };
	$j.extend( opts, options );
	opts.delay = opts.delay == 0? 1 : opts.delay;
	
	//create some custom handlers
	oDialog.container
		.unbind('modal.loading')
		.bind('modal.loading',
			function(){ 
				$j(this).addClass('dialog_loading').triggerHandler('modal.center'); 				
			}
		)
		.unbind('modal.loaded')
		.bind('modal.loaded',
			function(){ 
				$j(this).removeClass('dialog_loading');
				$j(this).triggerHandler('modal.center');
			}
		)
		.unbind('modal.center')
		.bind('modal.center',
			function(){ 
				$j(window).triggerHandler('resize');
			}
		);

	oDialog.overlay.fadeIn(opts.delay, function () {
		oDialog.container.fadeIn(opts.delay);
		oDialog.data.hide().fadeIn(opts.delay);
		
		//add sdna interactions and scripts to the content
		SDNA.global.onAreaLoad( oDialog.data );
		
		if( opts && opts.modal == false ){
			//register a click function on the modal overlay to close ala facebox
			oDialog.overlay
				.unbind('click.modal_close')
				.bind('click.modal_close', 
				function(){
					$j.modal.close();
				}	
			);
		}
		
		oDialog.container.triggerHandler('modal.center');
		
		//setup any interactions
		SDNA.global.setupModals(oDialog);
	});

}

SDNA.global.onModalShow = function( oDialog ){
	oDialog.container.triggerHandler('modal.center');
}

SDNA.global.reloadPage = function( oDialog ){
    window.location.reload();
}

SDNA.global.onModalClose = function( oDialog, options ){
	var opts = { delay:0 };
	$j.extend( opts, options );
	
	if( !isNaN(opts.delay) && opts.delay > 0 ){
	
		oDialog.data.fadeTo(opts.delay,0);
		oDialog.container.fadeTo(opts.delay,0, function () {
		  oDialog.overlay.fadeTo(opts.delay,0, function () {
		    $j.modal.close(); // must call this!
		  });
		});
	} else {
		$j.modal.close();
	}
}

//A global actions namespace
SDNA.global.actions = {};

SDNA.global.actions.rate = function(){}

//setup default action handlers
SDNA.global.actions.success = function(){
	$j(this)
		.css({backgroundColor:'#F5E792'})
		.animate({backgroundColor:'#FFFFFF'},1500,
			function(){
				$j(this).css('backgroundColor',null);
			}
		);
}

SDNA.global.actions.failure = function(){
	
}

SDNA.global.actions.loading = function(){
	$j(this).addClass('loading');
}

SDNA.global.actions.loaded = function(){
	$j(this).removeClass('loading');
}

SDNA.global.actions.bindDefaultHandlers = function( actions ){
	
	$actions = $j(actions);
		
	$actions.unbind('action.loading').bind('action.loading', SDNA.global.actions.loading )
	.unbind('action.loaded').bind('action.loaded', SDNA.global.actions.loaded )
	.unbind('action.failure').bind('action.failure', SDNA.global.actions.failure )
	.unbind('action.success').bind('action.success', SDNA.global.actions.success );
	
	return $actions;
}


SDNA.global.actions.bindJSONActions = function( $actions ){
	
	$actions
		.unbind('click.action')
		.bind( 'click.action', 
		
			function( e ){
			//stop this link from processing, we'll do it with ajax
			e.preventDefault();
			//make a reference to this action
			var $action = $j(this), vars;
			var sRequestType = 'get';
			var href = $action.attr('href');
			
			//hook up the json if its there
			var vars = $action.attr('json');
			if( vars != undefined){
				sRequestType = 'post';
			}
			if( href || vars ){
				//post the request
				$j[sRequestType]( 
					href,
					vars,
					function( response ){
						if( response.success == true ){
							//broadcast this success to all listeners
							$action.triggerHandler('action.success');
							$action.triggerHandler('action.finished');
							
							var $actions = $j('a[href=' + $action.attr('href') + ']');
							
							if( vars != undefined ){
									$actions = $action;
							}
							
							$actions.each(
								function(){
									$this = $j(this);                            
                                    // Hide Unfollows
                                    var $actionURL = $action.attr('href');
                                    var id = $this.closest("div").attr("id");
                                    var span_edit = $this.closest("span.follow").find('span.edit');
                                    if (($actionURL.search (/Location/) != -1)){
                                        if (id == "your_locations_following"){
                                            $this.closest('li').hide();
                                        } else{
                                            span_edit.hide();
                                        }
                                    } else if (($actionURL.search (/Event/) != -1)){
                                        if (id == "your_events_followed"){
                                            // Don't hide items attending or hosting.
                                            if (($this.closest('li').find('span.attending').length == 0) &&
                                                ($this.closest('li').find('span.hosting').length == 0)) {
                                                $this.closest('li').hide();                                                
                                            } else {
                                                // Otherwise hide the edit link
                                                span_edit.hide();                                                
                                            }
                                        } else {
                                            span_edit.hide();
                                        }
                                    } else if (($actionURL.search (/User/) != -1)){
                                        if (id == "your_people_following"){
                                            $this.closest('li').hide();
                                        } else {
                                            span_edit.hide();
                                        }
                                    }

									if( response.selected == true ){
										$this.addClass( 'selected' );
									} else if(response.selected == false ) {
										$this.removeClass( 'selected' );
									}
									if( response.dom_text ){
										
										$this.html( $j('<span/>').text(response.dom_text) );
									}
									if( response.undo_action ){
										$this.attr('href',response.undo_action);
									}
									
									if ($action.hasClass('delete_tag')) {
										$action.eq(0).parent().remove();
									}

									SDNA.global.setupActions( $this.parent() );									
								}
							);		
							
						//failure
						}else{
							
							//broadcast this failure to all listeners
							$action.triggerHandler('action.failure');
							$action.triggerHandler('action.finished');
							
						}//if success											
					},//function
					'json'
				);	
			}		
	});	

};

SDNA.global.actions.bindModalActions = function( $actions ){


	$actions.unbind('click.action').bind('click.action',
		
		function(e){
			//prevent this link from traveling, we'll load it in a modal instead			
			e.preventDefault();
				
			//set a ref to this link
			var oAction = $j(this);
			
			//show a loading indicator
			oAction.triggerHandler('action.loading');
			
			//if this action is set location or favorite, we can do it inline, NOT in a modal
          $j.ajax({ 
              url: 		oAction.attr('href') + '/force:' + Math.random().toString(),
              cache: 		false,
              error:		function ( xHR ) {
          		SDNA.ajax.errorModal(xHR);
          	    //remove loading
          	    oAction.triggerHandler('action.loaded');
          	},
              success: 	function( data ){
                  
                  //setup dialog options
                  var dialogOptions = { modal: false };
                  
                  if( oAction.hasClass('modal') ){
                      dialogOptions.modal = true;
                  }
                  
                  //open this content in a modal
                  $j.modal( 
                      data , 
                          {
                              onOpen: function( oDialog ){ 
                                  SDNA.global.onModalOpen(oDialog, dialogOptions);
                              }, 
                              onClose: function( oDialog ){ 
                                  SDNA.global.onModalClose(oDialog, dialogOptions);
                              },
                              onShow: function( oDialog ){
                                  SDNA.global.onModalShow( oDialog, dialogOptions );
                              },
                              close: !dialogOptions.modal
                          }
                      );
                  
                  //remove loading
                  oAction.triggerHandler('action.loaded');
              }
          });				
		}
	);
};//End SDNA.global.actions.bindModalActions


SDNA.global.setupActions = function( sArea ){
	
	var method = $j(sArea).length == 1 && $j(sArea).is('a')? 'filter' : 'find';
	
	var $actions = $j(sArea)[method]('a[href*=.jsn][href^=/ajax]').not('a.delete_fsm,a.rsvp,a.like,a.follow,a.dislike,a.unfollow,a.checkin,a.checkin_home');
	
	//setup generic ajax/JSON actions
	SDNA.global.actions.bindDefaultHandlers( $actions );
	SDNA.global.actions.bindJSONActions( $actions );

	//setup tag adding
	$j(sArea)[method]
		('form[action*=/ajax/][action*=/Tag.jsn]')
		.unbind('submit.tag')
		.bind('submit.tag',
		function(e){
			e.preventDefault();
			
			var $this 	= $j(this);
			var $tags	= $this.find('[name=tag]');

			if( !$this.hasClass('submitting') ){
			
				var	vars	= $this.sdnaSerialize();
				var action 	= $this.attr('action') + vars;
				
				//set a status spinner			
				$this.addClass('submitting');
				$this.find('.loading').remove();
				$this.append( '<span class="loading" />' );
				
				
				$j.get( 
					action,
					undefined,
					function( response ){
						if( response.success == false ){
							throw('Error adding tag');
						} else {
							$this.removeClass('submitting');
							$this.find('.loading').fadeOut();
							var tagType = response.type.substr(0, 1).toUpperCase() + response.type.substring(1, response.type.length);
							$j($tags.val().split(',')).each(
								function( i, val ){
									val = $j.trim(val);
									var $content =
										$j('<li />').append(
												$j('<a />').attr('href','/Search/Index/tag_id:' + response.tag_id).text( ' ' + val )
										).append(
											$j('<a />').attr({'className': 'delete_tag', 'href': '/ajax/' + tagType + '/DeleteTag.jsn/id:'+ response.tag_id + '/type_id:' + response.type_id}).text( 'x' )
										);

									$this.find('ul').append($content);
									SDNA.global.onAreaLoad($content);
								}
							);
							
							$tags.val('');
						}
					},
					'json'
				);
			}			
		}
	);	


	$j(sArea)
		.find('a.findme')
		.unbind('click.action')
		.bind('click.action',
			function(e){
                if (typeof SDNA.iphone != "undefined") {
                    SDNA.iphone.getLocationFromDevice();
                }
            }
        );
	
	//setup the actions menus
	var $modalActions = $j(sArea)[method]('a.block').not('[href*=.jsn]');
	SDNA.global.actions.bindDefaultHandlers( $modalActions );
	SDNA.global.actions.bindModalActions( $modalActions );

}//SDNA.global.setupActions


SDNA.global.onAreaLoad = function( $area ){
	
	var $area = $j($area || 'html');
	
	//setup the interactions working with forms
	//SDNA.forms.bind( $area );
	SDNA.global.setupActions( $area );
	
	//setup filter help bubbles
	SDNA.tabs.setupHelpButtons( $area );
		
	//create tabs of all lists with a class of tabs by default
	$area.find('ul.tabs').tabs(
		{
			onload: function( oTabContent ){
				SDNA.global.onAreaLoad( oTabContent );
				SDNA.Event.publish( 'tab_loaded' , { target: oTabContent });
			}
		}
	);	
					
	$area.find('button.show_more').setupShowMore();
	
	$area.find('input#friends_only[type=checkbox]').click(function() { $j(this).clickFriendsOnly(); });
	
	
}//SDNA.global.onAreaLoad

SDNA.global.loadShortUrl = function($area) {
    
    var $form = $area.find('.share_box form');
    
    var $checkboxes = $j(this);
    
    //get the short url to append to their comment
    $j.getJSON('/ajax/Shorten/Index.jsn', { 'url' : window.location.href }, function(data) {
        $form.append("<input type='hidden' id='shorturl' name='shorturl' value='" + data.url + "' />");
        $checkboxes.unbind('click.shorturl');
    });
}
	
SDNA.global.triggerAction = function( attrs ){
	
	$action = $j('<a/>').attr( attrs );
	SDNA.global.setupActions( $action );
	$action.triggerHandler('click.action');
	
}

SDNA.global.bindMoreLess = function(){
	
	//setup section toggles
	$j('a.toggle_details').live('click.toggle_more_less',
			function(e){
				e.preventDefault();
				
				//make a ref to this
				$this = $j(this).find('span');
				
				//make a ref to the details
				$section = $this.parents('.details').eq(0);
				
				if( $section.hasClass('less_details') ){
					$section.removeClass('less_details');
					$this.text('Less Details');
				}else {
					$section.addClass('less_details');
					$this.text('More Details');
				}
				
			}
		);
}

/**
 * Handle click events for all 'tracker' links.
 * Post the data to the tracking controller.
 * This is done asyncronously and without interupting
 * the user's click action
 * @author davidbjames
 */
SDNA.global.tracker = function (e) {
    // grab tracker data from click element
    var trackerData = $j(this).data('tracker');
    // post it to the tracking controller for this tracking type (click)
    $j.post('/Tracking/TrackClick', trackerData);
};

SDNA.global.bind = function(){

	SDNA.global.bindMoreLess();
	
	// bind click tracking
    $j('a.tracker').live('click.tracker', SDNA.global.tracker);

}


SDNA.ajax.errorModal = function(xHR) {
	var msg = xHR.status == '401' ? 'The requested resource requires you to be logged in. Please login <a href="/User/Login">here</a>' : xHR.statusText;
	var data = 
		'<div class="message error_message" style="float:none;width:auto;">' +                			
        '<div class="message_content"><h3>Error '+ xHR.status +'</h3>' +
        '<ul><li><span>'+ msg +'</span></li></ul>' +
		'</div></div>';
	var dialogOptions = { modal: false };
	$j.modal( 
        data , 
            {
                onOpen: function( oDialog ){ 
                    SDNA.global.onModalOpen(oDialog, dialogOptions);
                }, 
                onClose: function( oDialog ){ 
                    SDNA.global.onModalClose(oDialog, dialogOptions);
                },
                onShow: function( oDialog ){
                    SDNA.global.onModalShow( oDialog, dialogOptions );
                },
                close: !dialogOptions.modal
            }
    );    
}



//Global loaded/loading toggle indicators
//Converts an element into markup that will indicate that it is loading
SDNA.loading = function(el){
	
	if(!el){return;}
	
	var $this 		= $j(el);
	var $wrap 		= $this.parent('.' + SDNA.loading.className );
	
	if( $wrap.length < 1 ){
		$wrap = $j('<' + ($this.css('display')=='block'?'div':'span') + '/>').css( {display: $this.css('display') });	
	}
	$wrap.removeAttr('class').addClass(SDNA.loading.className ).addClass( $this.css('text-align') );			
	
	if( $this.parent('.' + SDNA.loading.className ).length < 1 ){
		$this.wrap( $wrap );
	}
	
}

SDNA.loaded = function(el){
	
	if(!el){return;}
	
	var $wrap = $j(el).parent('.' + SDNA.loading.className );
	if( $wrap.length > 0 ){
		$wrap.removeClass(SDNA.loading.className ).replaceWith( el );
	}
}

SDNA.loading.className = 'loading_wrap';