var INFO_WAIT_TIME = 500;

var gOperatableFlag = false;
var gTimeOut        = null;
var gIsOpenInfo     = {};
var gClassItem      = null;
var gTagDiv         = null;
var gBookmarkList   = {};

var confRootDir;
var gCompleteResults;
var gAllCompleteFlag;
var gUser;
var gOpenMode;

var gIdBookmarkHalfH;

Event.observe(window, 'load', function(){

	// ----------------
	// 値の初期化
	// ----------------

	confRootDir      = readArgs('confRootDir');					// ルートディレクトリパス
	gCompleteResults = parseInt(readArgs('completeResults'));	// 読み込み完了数
	gAllCompleteFlag = readArgs('allCompleteFlag');				// 全て読み込み完了フラグ
	gUser            = readArgs('user');						// ユーザ
	gOpenMode        = readArgs('openMode');					// 現在の表示モード

	gIsOpenInfo['tag']    = {};
	gIsOpenInfo['days']   = {};
	gIsOpenInfo['domain'] = {};

	$$('.dir-tag').each(function(obj){		gIsOpenInfo['tag'][obj.id.substr(4)]    = false;	});
	$$('.dir-days').each(function(obj){		gIsOpenInfo['days'][obj.id.substr(4)]   = false;	});
	$$('.dir-domain').each(function(obj){	gIsOpenInfo['domain'][obj.id.substr(4)] = false;	});

	setIdBookmarkHalfH();

	// ----------------
	// ブックマーク情報の保存
	// ----------------

	$$('.item-tag').each(function(obj){		obj.removeChild(getChildTag(obj, 1));	});
	$$('.item-domain').each(function(obj){	obj.removeChild(getChildTag(obj, 1));	});

	var bid = 0;

	$$('.item-days').each(function(obj){

		var tagDiv = getChildTag(obj, 1);
		var tagUl  = getChildTag(tagDiv, 0);

		var tmp = {};

		tmp['b_hatena']    = getChildTag(tagUl, 0).innerHTML;
		tmp['url']         = getChildTag(tagUl, 1).innerHTML;
		tmp['days']        = getChildTag(tagUl, 2).innerHTML;
		tmp['implodeTags'] = getChildTag(tagUl, 3).innerHTML;
		tmp['memo']        = getChildTag(tagUl, 4).innerHTML;

		gBookmarkList[bid++] = tmp;

		obj.removeChild(tagDiv);

	});

	// ----------------
	// 操作を許可する
	// ----------------

	gOperatableFlag = true;

	// ----------------
	// 各イベント関係
	// ----------------

	Event.observe(window,           'resize', function(){	setIdBookmarkHalfH();		});
	Event.observe($('all-open'),    'click',  function(){	allOpenClick();				});
	Event.observe($('all-close'),   'click',  function(){	allCloseClick();			});
	Event.observe($('mode-change'), 'click',  function(){	modeChangeClick();			});
	Event.observe($('config'),      'click',  function(){	configClick();				});
	Event.observe($('init-empty'),  'change', function(){	configChange(true,  true);	});
	Event.observe($('init-exists'), 'change', function(){	configChange(true,  false);	});
	Event.observe($('add-empty'),   'change', function(){	configChange(false, true);	});
	Event.observe($('add-exists'),  'change', function(){	configChange(false, false);	});
	Event.observe($('complete'),    'click',  function(){	completeClick();			});

	// ----------------

});

// ----------------
// ウィンドウがリサイズされたときの処理
// ----------------

function setIdBookmarkHalfH(){
	gIdBookmarkHalfH = ($('footer').offsetTop - $('header').offsetHeight) / 2;
}

// ----------------
// 『全部開く』押下時の処理
// ----------------

function allOpenClick(){

	for(var isOpenKey in gIsOpenInfo[gOpenMode]){
		if(!gIsOpenInfo[gOpenMode][isOpenKey]){
			open(isOpenKey);
		}
	}

}

// ----------------
// 『全部閉じる』押下時の処理
// ----------------

function allCloseClick(){

	for(var isOpenKey in gIsOpenInfo[gOpenMode]){
		if(gIsOpenInfo[gOpenMode][isOpenKey]){
			close(isOpenKey);
		}
	}

}

// ----------------
// タグ押下時の処理
// ----------------

function dirClick(relationalKey){
	if($('dir-' + relationalKey).parentNode.className != 'open'){
		open(relationalKey);
	}else{
		close(relationalKey);
	}
}

// ----------------
// フォルダ開閉の処理
// ----------------

function open(key){
	$('dir-' + key).parentNode.className = 'open';
	gIsOpenInfo[gOpenMode][key]          = true;
}

function close(key){
	$('dir-' + key).parentNode.className = '';
	gIsOpenInfo[gOpenMode][key]          = false;
}

// ----------------
// URL マウスオーバー・マウスアウト時の処理
// ----------------

function urlOver(target, event, bid){

	gTimeOut = setTimeout(function(){

		var bookmark = gBookmarkList[bid];

		var tagH3 = target.parentNode;

		gClassItem = tagH3.parentNode;

		// ----------------
		// ポップアップ div 領域の作成
		// ----------------

		gTagDiv = document.createElement('div');

		if(Prototype.Browser.IE){
			gTagDiv.className = 'popup-bottom';
			gClassItem.appendChild(gTagDiv);
		}else if(event.clientY < gIdBookmarkHalfH){
			gTagDiv.className = 'popup-bottom';
			gClassItem.appendChild(gTagDiv);
		}else{
			gTagDiv.className = 'popup-top';
			gClassItem.insertBefore(gTagDiv, tagH3);
		}

		var tagUl = document.createElement('ul');
		gTagDiv.appendChild(tagUl);

		var tagLi = document.createElement('li');
		tagLi.innerHTML = '<span>はてブ数：</span><img src="' + bookmark['b_hatena'] + '" alt="" />';
		tagUl.appendChild(tagLi);

		var tagLi = document.createElement('li');
		tagLi.innerHTML = '<span>アドレス：</span>' + bookmark['url'];
		tagUl.appendChild(tagLi);

		var tagLi = document.createElement('li');
		tagLi.innerHTML = '<span>作成日時：</span>' + bookmark['days'];
		tagUl.appendChild(tagLi);

		if(bookmark['implodeTags'] != ''){
			var tagLi = document.createElement('li');
			tagLi.innerHTML = '<span>タグ：</span>' + bookmark['implodeTags'].escapeHTML();
			tagUl.appendChild(tagLi);
		}

		if(bookmark['memo'] != ''){
			var tagLi = document.createElement('li');
			tagLi.innerHTML = '<span>メモ：</span>' + bookmark['memo'].escapeHTML();
			tagUl.appendChild(tagLi);
		}

		// ----------------

	}, INFO_WAIT_TIME);

}

function urlOut(){

	if(gTimeOut != null){
		clearTimeout(gTimeOut);
		gTimeOut = null;
	}
	if(gClassItem != null && gTagDiv != null){
		gClassItem.removeChild(gTagDiv);
		gClassItem = null;
		gTagDiv    = null;
	}

}

// ----------------
// 『表示切替』押下時の処理
// ----------------

function modeChangeClick(){

	$('bookmark-' + gOpenMode).className = 'different-mode';

	if(gOpenMode == 'tag'){
		gOpenMode = 'days';
	}else if(gOpenMode == 'days'){
		gOpenMode = 'domain';
	}else if(gOpenMode == 'domain'){
		gOpenMode = 'tag';
	}

	if(gOpenMode != 'tag'){
		writeCookieImpValue('openMode', gUser, gOpenMode, true, '&', '=', null, '/');
	}else{
		writeCookieImpValue('openMode', gUser, '', true, '&', '=', null, '/');
	}

	$('bookmark-' + gOpenMode).className = '';

}

// ----------------
// 『設定』押下時の処理
// ----------------

function configClick(){

	if($('setting').style.display == ''){
		$('setting').style.display = 'block';
	}else{
		$('setting').style.display = '';
	}

}

// ----------------
// 設定変更時の処理
// ----------------

function configChange(initFlag, emptyFlag){

	if(initFlag && emptyFlag){
		writeCookieImpValue('config', 'initEmpty', Form.Element.Serializers.select($('init-empty')), true, '&', '=', null, '/');
	}else if(initFlag && !emptyFlag){
		writeCookieImpValue('config', 'initExists', Form.Element.Serializers.select($('init-exists')), true, '&', '=', null, '/');
	}else if(!initFlag && emptyFlag){
		writeCookieImpValue('config', 'addEmpty', Form.Element.Serializers.select($('add-empty')), true, '&', '=', null, '/');
	}else if(!initFlag && !emptyFlag){
		writeCookieImpValue('config', 'addExists', Form.Element.Serializers.select($('add-exists')), true, '&', '=', null, '/');
	}

}

// ----------------
// 『全 XXX 件中 XXX 件目まで読込完了』押下時の処理
// ----------------

function completeClick(){

	if(gOperatableFlag && gAllCompleteFlag == 0){

		gOperatableFlag = false;

		// ----------------
		// 要素の取得
		// ----------------

		var idLoading  = $('loading');

		// ----------------
		// ローディング状態の開始
		// ----------------

		idLoading.style.visibility = 'visible';

		// ----------------
		// 非同期通信を行なう
		// ----------------

		var ajax = new Ajax.Request(
			confRootDir + 'parts/asynchronous/index-asynchronous.php',
			{
				method: 'GET',
				parameters: 'user=' + gUser + '&completeResults=' + gCompleteResults,

				onSuccess: function(request){
					ajaxSuccess(request.transport.responseText);
				},

				onFailure: function(request){
					ajaxError(request.transport.responseText);
				},

				onException: function(request){
					ajaxError(request.transport.responseText);
				},

				onComplete: function(request){
					idLoading.style.visibility = '';
					gOperatableFlag            = true;
				}

			}
		);

		// ----------------

	}

}

// ----------------
// 非同期通信に成功したときの処理
// ----------------

function ajaxSuccess(response){

	// ----------------
	// 要素の取得
	// ----------------

	var idComplete = $('complete');

	// ----------------
	// 取得したデータの展開
	// ----------------

	var response       = eval('(' + response + ')');
	var bookmarkMeta   = response['bookmarkInfo']['meta'];
	var bookmarkList   = response['bookmarkInfo']['list'];
	var relationalInfo = response['relationalInfo'];

	// ----------------
	// ブックマーク情報の保存と、読込完了数の取得
	// ----------------

	var cnt = 0;

	for(var bid in bookmarkList){

		var bookmark = bookmarkList[bid];

		var tmp = {};

		tmp['b_hatena']    = bookmark['b_hatena'];
		tmp['url']         = bookmark['url'];
		tmp['days']        = bookmark['days'];
		tmp['implodeTags'] = bookmark['implodeTags'];
		tmp['memo']        = bookmark['memo'];

		gBookmarkList[bid] = tmp;

		cnt++;

	}

	gCompleteResults += cnt;

	// ----------------
	// DOM を組み立てる
	// ----------------

	for(var mode in relationalInfo){

		var idBookmark = $('bookmark-' + mode);

		for(var relationalKey in relationalInfo[mode]){

			var relational = relationalInfo[mode][relationalKey];

			if($('dir-' + relationalKey)){

				// ----------------
				// ディレクトリが表示済みの場合
				// ----------------

				var idDir  = $('dir-' + relationalKey);
				var idList = $('list-' + relationalKey);

				var idDirInner = idDir.innerHTML.trim();
				var ofsSt      = idDirInner.lastIndexOf('(') + 1;
				var ofsEd      = idDirInner.lastIndexOf(')');

				var count = parseInt(idDirInner.substring(ofsSt, ofsEd)) + relational['count'];

				idDir.innerHTML = relational['dirName'].escapeHTML() + ' (' + count + ')';

				// ----------------

			}else{

				// ----------------
				// 表示済みでない場合
				// ----------------

				gIsOpenInfo[mode][relationalKey] = false;

				var tagLi = document.createElement('li');

				if($('list-empty-' + mode)){
					idBookmark.insertBefore(tagLi, $('list-empty-' + mode).parentNode);
				}else{
					idBookmark.appendChild(tagLi);
				}

				var idDir = document.createElement('h2');
				idDir.id        = 'dir-' + relationalKey;
				idDir.className = 'dir-' + mode;
				idDir.innerHTML = relational['dirName'].escapeHTML() + ' (' + relational['count'] + ')';

				if(Prototype.Browser.IE){
					idDir.setAttribute('onclick',    new Function("dirClick('" + relationalKey + "')"));
					idDir.setAttribute('onkeypress', new Function("dirClick('" + relationalKey + "')"));
				}else{
					idDir.setAttribute('onclick',    "dirClick('" + relationalKey + "')");
					idDir.setAttribute('onkeypress', "dirClick('" + relationalKey + "')");
				}

				tagLi.appendChild(idDir);

				var idList = document.createElement('ul');
				idList.id = 'list-' + relationalKey;
				tagLi.appendChild(idList);

				// ----------------

			}

			for(var bidKey = 0; bidKey < relational['bidList'].length; bidKey++){

				var bid      = relational['bidList'][bidKey];
				var bookmark = bookmarkList[bid];

				var classItem = document.createElement('li');
				classItem.className = 'item-' + mode;
				idList.appendChild(classItem);

				var tagH3 = document.createElement('h3');
				tagH3.style.backgroundImage = 'url(' + bookmark['favicon'] + ')';
				classItem.appendChild(tagH3);

				var tagA = document.createElement('a');
				tagA.innerHTML = bookmark['title'].escapeHTML();
				tagA.setAttribute('href',        bookmark['url']);
				tagA.setAttribute('title',       '');
				tagA.setAttribute('target',      '_blank');

				if(Prototype.Browser.IE){
					tagA.setAttribute('onmouseover', new Function("urlOver(this, event, " + bid + ")"));
					tagA.setAttribute('onmouseout',  new Function('urlOut()'));
				}else{
					tagA.setAttribute('onmouseover', "urlOver(this, event, " + bid + ")");
					tagA.setAttribute('onmouseout',  'urlOut()');
				}

				tagH3.appendChild(tagA);

			}

		}

	}

	// ----------------
	// 読込完了数の更新
	// ----------------

	if(parseInt(bookmarkMeta['totalResults']) > gCompleteResults){
		idComplete.innerHTML  = '全 ' + bookmarkMeta['totalResults'] + ' 件中 ' + gCompleteResults + ' 件目まで読込完了';
	}else{
		idComplete.innerHTML  = '全ブックマークの読み込み完了 (全 ' + bookmarkMeta['totalResults'] + ' 件)';
		gAllCompleteFlag = 1;
	}

	// ----------------

}

// ----------------
// 非同期通信に失敗したときの処理
// ----------------

function ajaxError(response){
	if(response == 'Bad Request'){
		alert('Bad Request');
	}else if(response == 'Not Found'){
		alert('Not Found');
	}
}

