$.fn.dzipcode = function(opt) {
	opt = $.extend(true, {
		'zipcode': $('#zipcode'),
		'address0': $('#address0'),
		'address1': $('#address1'),

		'url': '/user/zipcode/',
		'loadingImage': '/img/basic/loading-large-eee.gif',
		'search': this
	}, opt);

	var _result = $('<div></div>').addClass('dzipcode-result');
	opt.search.after(_result);
	_result.hide();

	var _loading =
		$('<img src="'+opt.loadingImage+'" alt="Loading..." />')
			.addClass('dzipcode-loading');
	opt.search.after(_loading);
	_loading.hide();

	this.bind('dzipcode-query', function() {
		/* get data as json */
		opt.search.data('dzipcode-word', opt.search.val());
		$.get(opt.url + encodeURI(opt.search.val()), '',
			function(data) {
			if (data == null ||
				typeof data != 'object' ||
				typeof data.item != 'object')
				return;

			opt.search.removeData('dzipcode-word');
			_loading.hide();
			var table = $('<table></table>')
				.addClass('dzipcode-result-table');
			$(data.item).each(function() {
				var i = $(this).get(0);
				var tr = $('<tr></tr>').appendTo(table);
				var td = $('<td></td>').appendTo(tr);
				$('<a></a>').attr('href', '#')
					.html(i.address)
					.click(function() {
						opt.search.val('').blur();
						opt.zipcode.val(i.zipcode);
						opt.address0.val(i.address);
						_result.empty().hide();
						opt.address1.select();
						return false;
					}).appendTo(td);
				td = $('<td></td>')
					.addClass('zipcode')
					.html(i.zipcode)
					.appendTo(tr);
			});
			_result.slideDown().empty().append(table);
		}, 'json');
	});

	this.bind('dzipcode-show-loading', function() {
		/* show loading */
		_loading.show();
		_result.hide();
	});

	this.keyup(function() {
		if ($(this).val() == '')
			return;

		$(this).trigger('dzipcode-show-loading');

		clearTimeout(opt.search.data('dzipcode-timer'));
		if (opt.search.val() == '' ||
			opt.search.val() == opt.search.data('dzipcode-word'))
			return;

		opt.search.data('dzipcode-timer', setTimeout(function() {
			opt.search	
				.trigger('dzipcode-show-loading')
				.trigger('dzipcode-query');

		}, 800));
	}).blur(function() {
		if ($.isempty(opt.search.val()))
			_result.hide().empty();
	});
};

