// TODO implement _t()
var i18n = i18n || {};

// language strings
jQuery.i18n.addDictionary({
	'RESULTTITLE': "Showing \"%s\""
});

;(function($) {
	
	$.fn.DemandMap_SearchBar = function(mapSelector, _options) { 
		var defaults = {
			'baseCountryCode': 'NZ', // @see http://www.iso.org/iso/country_codes/iso_3166_code_lists/english_country_names_and_code_elements.htm
			'addCountryKeyword': {
				'ifNotMatches': /New Zealand/i,
				'add': ', New Zealand'
			},
			'loadingIndicator': '<div class="loadingIndicator"><img src="cms/images/network-save.gif" /></div>'
		};
		
		return this.each(function(){
			var options = $.extend({}, defaults, _options);
			
			// Reference to this control
			var $this = $(this);
			
			// objects
			var map = $(mapSelector);
			var form;
			var geocoder; // GClientCoder
			
			geocoder = new GClientGeocoder();
			geocoder.setBaseCountryCode(options.baseCountryCode);
			
			// @todo: The DOM is contained in a form, not the other way around -
			//  ideally this logic would be outside of this component
			form = $(this).parents('form')[0];
			$(form).validate({
				submitHandler: submit.bind(this)
			});
			
			// trigger initial search if "q" param is present,
			// but avoid placemark queries if explicit bounds are given 
			// (e.g. from a "bookmarked" map view)
			if(
				$.jget['q'] && 
				!($.jget['bounds[sw]'] || $.jget['bounds[ne]'])
			) {
				search($.jget['q']);
			}
			
			$('input[name=action_search]', this).after(options.loadingIndicator);
			$('.loadingIndicator', this).hide();


			// Set up in-place heading for search field
			$('input[name=q]', this)
				.focus(function() { 
					if($(this).val() == 'Enter address to search for') {
						$(this).val('');
						$(this).removeClass('hasDefaultValue');
					}
				})
				.blur(function() { 
					if($(this).val() == '') {
						$(this).val('Enter address to search for');
						$(this).addClass('hasDefaultValue');
					}
				});
			if(!$('input[name=q]', this).val()) {
				$('input[name=q]', this).val('Enter address to search for');
			}

			
			// focus on first element
			//$(":input:first", this).focus();
			
			// url config
			if($.jget['hidesearchbar']) $this.hide();
		
			function submit(form) {
				var q = $('input[name=q]', form).fieldValue()[0];
				if(q && q.length) {
					search(q);
				}
				return false;
			}
			
			function search(q) {
				setLoading(true);
				
				// force results to be country-specific (e.g. "Hastings" to "Hastings, New Zealand")
				if(!q.match(options.addCountryKeyword.ifNotMatches)) q += options.addCountryKeyword.add;
				geocoder.getLocations(q, search_onGeocode.bind(this));
				
				$(document).trigger('DemandSearchBar:searchstart');
			}
			
			function search_onGeocode(response) {
				setLoading(false);
				// @todo add error handling
				if(!response || response.Status.code != '200') return false;
				
				var placemark = response.Placemark[0];
				
				var latLngBox = placemark.ExtendedData.LatLonBox;
				var latLngBound = new GLatLngBounds(
					new GLatLng(latLngBox.south, latLngBox.west), 
					new GLatLng(latLngBox.north, latLngBox.east)
				);
				var zoom = map.fn('getGmap').getBoundsZoomLevel(latLngBound);
				map.fn('setCenter', 
					new GLatLng(placemark.Point.coordinates[1], placemark.Point.coordinates[0]), 
					zoom
				);
				
				setKeyword(placemark.address);
				$(document).trigger('DemandSearchBar:searchend', [placemark.address]);
			}
			
			function setKeyword(str) {
				$('.resultLocationTitle', this).html($.i18n._t("RESULTTITLE", [str]));
			}
			
			function setLoading(isLoading) {
				if(isLoading) $('.loading', this).show();
				else $('.loading', this).hide()
			}
			
			function clear() {
				$('.resultLocationTitle', this).html('');
				$('input[name=q]', this).value = '';
			}
		
		});
	}
})(jQuery);